I'm using Typo 7.2 and am looking for an answer to the following question:
How to add a generated File as FileReference programmatically to an extension model?
First some infos regarding my achievements/tries.
DONE A command controller runs over folders, looks for a specific image and creates a blurred file via GraphicFunctions. The generated file is added to the storage as a standalone simple file and appears in the sys_file table.
$fileObject = $posterStorage->addFile(
$convertResult[3],
$posterStorage->getFolder($blurFolderName),
$newFileName);
PARTIALLY DONE. Now I need to add the generated file as a file reference to my model. The problem is, that I'm able to do this, but only by hacking core - not acceptable - and unable to do it the right way. The model says:
public function addPosterWebBlur(
\TYPO3\CMS\Extbase\Domain\Model\FileReference $posterWebBlur
) {
$this->posterWebBlur->attach($posterWebBlur);
}
So I succeeded by extending the FileReference class:
class FileReference extends \TYPO3\CMS\Extbase\Domain\Model\FileReference {
public function setFile(\TYPO3\CMS\Core\Resource\File $falFile) {
$this->$uidLocal = (int)$falFile->getUid();
}
}
The reference does not get established and I just get the following error in the backend:
Table 'db_name.tx_ext_name_domain_model_filereference' doesn't exist.
UPDATE
After integrating the data from Frans in ext_typoscript_setup.txt, the model can be saved, creates an sys_file_reference entry and acts nicely in the backend. But there are a few points open to fulfill all needs:
The sys_file_reference table does not contain a value for table_local, whereas all the entries generated by a backend user hold sys_file as value.
The same applies to l10n_diffsource which holds some binary large object. This entry gets inserted in the sys_file_reference table after saving the record manually via backend.
The pid of the file_reference has to be set via setPid($model->getPid()), is that okay?
The cruser_id is always set to zero. Is this the correct way?
When trying to delete a file (which was added to a model with the backend possibilities) via the file manager, I get a warning, that references to this file exist. This does not apply to the fileReference added programmatically. Also the references listed under the file (when clicking on "Info" for a generated file in the backend file manager) don't get listed. They get listed, when I enter the "sys_file" value in the sys_file_reference table by hand.
As Helmut Hummels example holds additional data, I'm wondering, if I just miss some stuff.
The file reference is used inside an object storage, but as the addImage function only calls objectStorage->attach I think this should be okay and no additional objectStorage actions are neccessary. Correct?
You have to tell the extbase persistence layer to use the correct table. See for instance this example https://github.com/helhum/upload_example/blob/master/ext_typoscript_setup.txt
gr. Frans
Trying to answer 1)
See
https://github.com/helhum/upload_example/blob/master/Configuration/TCA/tx_uploadexample_domain_model_example.php#L128
You should probably check the TCA definition for your posterWebBlur field. Second param of getFileFieldTCAConfig()
TT
Related
We are using Optimizely/Episerver CMS 11.20. When trying to export a page hierarchy from our production environment and then import the resulting ExportedFile.episerverdata file to our acceptance test environment I get the following error:
[Importing content 70725_133679] Exception: Object reference not set to an instance of an object.
I have no idea what 70725_133679 is referring to. Is there a way to look this up, e.g. via an SQL query against the "EPi" database?
It refers to a specific version of some content (which could be just about anything).
You could try to browse to https://yoursite/EPiServer/CMS/#context=epi.cms.contentdata:///70725_133679 (note the ID at the end) to see which content it is.
Got another answer on a Optimizely forum (thanks to Surjit Bharath):
The following SQL against the EPi database gives information about the referenced content:
select * from tblContent where pkID = 70725
select * from tblWorkContent where pkID = 133679
This too points to a submit button. I have yet to understand why that block would cause an exception during import, but now I at least have a place to start digging.
I want to make a copy of my TYPO3 CMS 6.2.18 website - what I did so far:
Copied the entire website folder (including the TYPO3 installation)
Copied the entire database (with a new name)
Created a new db user for the copied db
Adjusted the file /typo3conf/LocalConfiguration.php accordingly to the new DB+User
Now I'm receiving following errors when calling different urls of my copied TYPO3 website:
When I try calling the "Upgrade Wizard" from inside the install tool /typo3/install (which is the only page that currently works):
#1: PHP Warning: count(): Parameter must be an array or an object that implements Countable in /var/www/vhosts/<my-domain>/typo3/sysext/install/Classes/Service/SqlSchemaMigrationService.php line 409
When I call <my-domain>/typo3
#1: PHP Warning: count(): Parameter must be an array or an object that implements Countable in /var/www/vhosts/<my-domain>/typo3/sysext/backend/Classes/Utility/BackendUtility.php line 3022
4 count(NULL)
...
/var/www/vhosts/<my-domain>/typo3/sysext/backend/Classes/Utility/BackendUtility.php:
03020: $signals = array();
03021: $modData = $GLOBALS['BE_USER']->getModuleData('TYPO3\\CMS\\Backend\\Utility\\BackendUtility::getUpdateSignal', 'ses');
03022: if (!count($modData)) {
03023: return '';
03024: }
When I call <my-domain>
#1: PHP Warning: count(): Parameter must be an array or an object that implements Countable in /var/www/vhosts/<my-domain>/typo3/sysext/core/Classes/Database/PreparedStatement.php line 582
...after calling...
TYPO3\CMS\Core\Database\PreparedStatement::convertNamedPlaceholdersToQuestionMarks("SELECT * FROM fe_session_data WHERE hash = :hash", array, array)
What's interesting to me:
After copying the website the copy worked, only after referencing it to the copied db it showed these errors.
Anyone an idea what I could do / be looking for?
I tried deleting all cache, all tables shown in the "Cleanup" part of the install tool and all files in the typoe3temp folder already.
So, as I have said in the comment. Probably the issue with PHP version, because of all the mentioned errors (warning actually ;) ) reflect the incompatible PHP code.
The solution is pretty easy, switch your PHP version according to TYPO3's need :)
Am using $GLOBALS['TSFE']->cObj->typoLink to generate a link and I've an additional parameter like this: ext__pluginname[d64]=31511 and would like to return something like a/b/c. I would then want TYPO3 to give me back the link so I can resolve it when clicked. I've already tried PersistedAliasMapper but won't allow to return anything with a slash in it. I've even tried a custom aspect mapper. I get the error:
Parameter "tx_ext__pluginname__d64" for route "enhancer_tx_ext__pluginname000000003e62d21a000000000514759a" must match "[^/]++" ("a/c" given) to generate a corresponding URL.
Am able to generate and resolve the slugs(urls). I can store them in db and retrieve them for that matter. No problem.
Am generating them from root page (uid 1).
How can i get this to work?
I assume you already have created the desired path in a database table or view already, making use of the slug feature in the TYPO3 backend or creating it yourself.
You could then use the PersistedAliasMapper in your site config (config/sites/default/config.yaml).
If you need multiple values in a single path divided by slashes (not a combined slug field), take a look at the route configuration for the news extension. You just have to use database mappers instead of static ones, but keep in mind this may impact the performance of the routing!
As you did not provide much detail about your use case, I don't really understand why you need such a path structure with slashes.
I've tried three different ways to detect if a FileReference's original file is still existing (i.e. file has been deleted outside TYPO3 using SFTP or similar):
if($fileReference instanceof \TYPO3\CMS\Extbase\Domain\Model\FileReference) {
$isMissing = $fileReference->getOriginalResource()->getStorage()->getFile($fileReference->getOriginalResource()->getIdentifier())->isMissing();
$isMissing = $fileReference->getOriginalResource()->getOriginalFile()->isMissing();
$isMissing = $fileReference->getOriginalResource()->isMissing();
}
Only the first one give me the right isMissing() value.
The property isMissing is an database value, which is set if the storage detect an missing file. On getFile the storage check if the file is missing and set "isMissing" for the file. If you dont persist this to the database, the setting is get loose with the next call.
You can also call $isMissing = $fileReference->getOriginalResource()->getStorage()->hasFile($fileReference->getOriginalResource()->getIdentifier());
You can run the file indexer scheduler (TYPO3\CMS\Scheduler\Task\FileStorageIndexingTask) if you want to check frequently for deleted files. This should be required if you let change files externaly (like ftp).
I have a Windows Forms .NET application in Visual Studio. Making a form "Localizable" adds a Form1.resx file nested below the form. I also want to add a separate .resx file for each form (Form1Resources.resx). This is used for custom form-specific resources, e.g. messages generated using the code behind.
This is set up as follows:
It would be tidier to nest the custom .resx file beneath the form (see this question for details about nest how to do this), as follows:
However, this results in the following error when I build the application:
Two output file names resolved to the same output path:
"obj\Debug\WindowsFormsApp1.Form1.resources" WindowsFormsApp1
I'm guessing that MSBuild uses some logic to find nested .resx files and generate .resources file based on its parent. Is there any way that this can be resolved?
Note that it is not possible to add custom messages to the Form1.resx file - this is for design-specific resources only and any resources that you add get overwritten when you save changes in design mode.
The error comes from the GenerateResource task because the 2 resx files (EmbeddedResource items in msbuild) passed both have the same ManifestResourceName metadata value. That values gets created by the CreateManifestResourceNames task and assumingly when it sees an EmbeddedResource which has the DependentUpon metadata set (to Form1.cs in your case) it always generates something of the form '$(RootNamespace).%(DependentUpon)': both your resx files end up with WindowsFormsApp1.Form1 as ManifestResourceName. Which could arguably be treated as the reason why having all resx files under Form1 is not tidier: it's not meant for it, requires extra fiddling, moreover it could be confusing for others since they'd typcially expect to contain the resx fils placed beneath a form to contain what it always does.
Anyway: there's at least 2 ways to work around this:
there's a Target called CreateCustomManifestResourceNames which is meant to be used for custom ManifestResourceName creation. A bit too much work for your case probably, just mentioning it for completeness
manually declare a ManifestResourceName yourself which doesn't clash with the other(s); if the metadata is already present it won't get overwritten by
Generic code sample:
<EmbeddedResource Include="Form1Resources.resx">
<DependentUpon>Form1.cs</DependentUpon>
<ManifestResourceName>$(RootNamespace).%(FileName)</ManifestResourceName>
...
</EmbeddedResource>