TYPO3 Inline element appearance configuration partially does not work - typo3

I have an own content element on my TCA/Overrides and i have some appearance settings configured. The problem is that i get these settings partially on my backend. This is my code:
$projectOptions = array(
'ak_website' => [
'exclude' => 1,
'label' => 'LLL:EXT:ak_website_base/Resources/Private/Language/locallang.xlf:website.items',
'config' => [
'type' => 'inline',
'foreign_table' => 'ak_website',
'foreign_field' => 'tt_content',
'maxitems' => 999,
'appearance' => [
'useSortable' => 1,
'collapseAll' => 1,
'levelLinksPosition' => 'bottom',
'enabledControls' => [
'info' => TRUE,
'new' => TRUE,
'dragdrop' => TRUE,
'sort' => TRUE,
'hide' => TRUE,
'delete' => TRUE,
'localize' => TRUE,
],
],
],
],
);
\TYPO3\CMS\Core\Utility\ExtensionManagementUtility::addTCAcolumns('tt_content',$projectOptions);
Now, everything works as it suppose to work BUT on the appearance settings the following settings do not work.
useSortable
new
dragdrop
sort
hide
delete
localize
Info works!
The way i see it, everything that has to do with the manipulation, do not work. I might have forgotten to set some rights, or include a TYPO3 function etc. I really have no idea what to do right now. It would be great for future references and for people who might come across the same problem to find the solution here.
Best regards,

Thanks to the TYPO3 community and specifically Carine LAVAL i found my answer.
I needed a sorting column on my database.
How this works:
ak_website.php (TCA)
Add 'sortby' => 'sorting',
<?php
return [
'ctrl' => [
'sortby' => 'sorting',
],
ext_tables.sql
Add this on your table:
sorting int(11) DEFAULT '0' NOT NULL,
And you are all set :)

Related

backend layout and drag&drop for custom content elements holding tt_content children | TYPO3 11

I've created a custom content element Box on TYPO3 11 core which has a field of type inline for further children elements of tt_content. The frontend works just fine so far, but the backend view gives me headache.
Creating the children elements on the parent Box, they're assigned colPos 0 and appear in that column of my backend layout.
What I'd like to achieve is having a backend layout inside my Box and being able to drag & drop tt_content elements in and out freely, looking like this:
The docs I followed appeared to not fit my desire and I want to solve this without any extensions.
Here's my TCA and SQL so far
$col = [
'content_relation' => [
'exclude' => true,
'label' => 'content',
'config' => [
'type' => 'inline',
'allowed' => 'tt_content',
'foreign_table' => 'tt_content',
'foreign_field' => 'content_relation',
'foreign_sortby' => 'sorting',
'minitems' => 0,
'maxitems' => 99,
'appearance' => [
'collapseAll' => true,
'expandSingle' => true,
'levelLinksPosition' => 'bottom',
'useSortable' => true,
'showPossibleLocalizationRecords' => true,
'showRemovedLocalizationRecords' => true,
'showAllLocalizationLink' => true,
'showSynchronizationLink' => true,
'enabledControls' => [
'info' => TRUE,
'new' => TRUE,
'dragdrop' => TRUE,
'sort' => TRUE,
'hide' => TRUE,
'delete' => TRUE,
'localize' => TRUE,
],
],
],
],
];
\TYPO3\CMS\Core\Utility\ExtensionManagementUtility::addToAllTCAtypes('tt_content', 'content_relation');
\TYPO3\CMS\Core\Utility\ExtensionManagementUtility::addTCAcolumns('tt_content', $col);
$GLOBALS['TCA']['tt_content']['types']['dg_template_box'] = [
'showitem' => '
--div--;LLL:EXT:core/Resources/Private/Language/Form/locallang_tabs.xlf:general,
--palette--;;general,
header;Internal title (not displayed),
content_relation;Elemente,
',
];
–
CREATE TABLE tt_content (
content_relation int(11) unsigned DEFAULT '0',
);
I assume you would need to change the colPos of your content_relation field. Assuming that Inhalt displays content elements from the tt_content table of the colPos 0. When creating a new content_relation record it'll (logically) display inside your normal (Inhalt) backend-layout since it represents records with a colPos which equals 0.
The easiest way is that you should make use of the b13/container package/extension.
You can simply create a new custom "box"-container with all your custom TCA configuration - and the best part is that the extension will take care of the children tt_content records itself. :)
For examples on how-to-use the b13/container extension take a look here b13/container-example.

Cascade delete TYPO3 inline records don't work

I have a TYPO3 extension for some products which uses inline records to add documentgroups to a product. Deleting the product should also delete the documentgroups (inline records).
The documentation says behaviour.enableCascadingDelete is set to true by default, but the documentgroups are not deleted. Setting this value in the TCA does not make a difference.
'documentgroups' => [
'exclude' => 1,
'label' => $ll . ".documentgroups",
'config' => [
'type' => 'inline',
'allowed' => 'tx_product_domain_model_docgroup',
'behaviour' => [
'allowLanguageSynchronization' => true,
'enableCascadingDelete' => true,
],
'foreign_table' => 'tx_product_domain_model_docgroup',
'MM' => 'tx_product_mm',
'MM_match_fields' => [
'tablenames' => 'tx_product_domain_model_docgroup',
'fieldname' => 'documentgroups',
'table_local' => $tableName,
],
'foreign_sortby' => 'sorting',
'minitems' => 0,
'maxitems' => 99,
]
],
enableCascadingDelete has no effect on MM related tables. In \TYPO3\CMS\Core\DataHandling\DataHandler->deleteRecord_procBasedOnFieldType the inline type is checked and only if it's of type field (foreign_field must be set in the TCA) or list (MM and foreign_field must not be set in TCA) child entries will be deleted.

Deletion of Inline Record is executed but a warning appears: Attempt to modify record without permission or non-existing page

On saving a record in Backend I'm using the TCEmainHook processDatamap_preProcessFieldArray. I'm creating, changing and deleting Inline Records there according to other fields in this records. Everything works as aspected, but there is still an Error/Warning on deletion of Inline Records, even the job is executed right. The Errors occur in TYPO3 7 and 8.
In Detail: I get the following Flash Message (in TYPO3 7 its only written in sys_log) for each Inline Record I deleted:
Attempt to modify record 'foo bar' (tx_datednews_domain_model_newsrecurrence:527) without permission. Or non-existing page.
In TYPO3 8 I could follow the problem to the typo3/sysext/core/Classes/DataHandling/DataHandler.php Method: recordInfoWithPermissionCheck.
There is an Deleted Restriction added. When I remove that, everything is fine. That leads me to the idea, that the records are deleted already, therefore it can not found the records anymore. But I'm not deleting it twice.
But as I mentioned above, at the end the deletion of this Inline Records has been executed perfectly.
These might be the relevant code snippets:
The deletion/removing of the inline records is done with the following way. Switching these two lines didn't help. Using only one of these leads to either an fatal error when I reopen the news and didn't remove oldRec from the news record or its removed but not deleted. So I'm sure I need to do both steps.
$this->newsRecurrenceRepository->remove($oldRec);
$news->removeNewsRecurrence($oldRec);
TCA of tx_datednews_domain_model_newsrecurrence:
return [
'ctrl' => [
'title' => 'LLL:EXT:dated_news/Resources/Private/Language/locallang_db.xlf:tx_datednews_domain_model_newsrecurrence',
'label' => 'eventstart',
'tstamp' => 'tstamp',
'crdate' => 'crdate',
'cruser_id' => 'cruser_id',
'default_sortby' => 'eventstart',
'versioningWS' => true,
'languageField' => 'sys_language_uid',
'transOrigPointerField' => 'l10n_parent',
'transOrigDiffSourceField' => 'l10n_diffsource',
'delete' => 'deleted',
...
TCA of Inline Element:
'newsrecurrence' => [
'config' => [
'type' => 'inline',
'foreign_table' => 'tx_datednews_domain_model_newsrecurrence',
'MM' => 'tx_datednews_news_newsrecurrence_mm',
'foreign_field' => 'parent_event',
'foreign_default_sortby' => 'eventstart DESC',
'maxitems' => 9999,
'appearance' => [
'collapseAll' => 1,
'levelLinksPosition' => 'top',
'showSynchronizationLink' => 1,
'showPossibleLocalizationRecords' => 1,
'useSortable' => 0,
'showAllLocalizationLink' => 1,
'enabledControls' => [
'info' => true,
'new' => false,
'dragdrop' => true,
'sort' => false,
'hide' => true,
'delete' => false,
'localize' => true,
],
],
],
]
Defaul QuerySettings in newsRecurrenceRepository:
$this->defaultQuerySettings = $this->objectManager->get('TYPO3\\CMS\\Extbase\\Persistence\\Generic\\Typo3QuerySettings');
$this->defaultQuerySettings->setIgnoreEnableFields(true);
$this->defaultQuerySettings->setEnableFieldsToBeIgnored(['hidden', 'deleted']);
$this->defaultQuerySettings->setRespectStoragePage(FALSE);
It would be so great to understand why that Warning appears and how to get rid of it.
The solution is, to use the DataHandler Object which is available in the hook as $pObj.
So instead removing the record with the repository, it needs to be removed using the DataHandler. I replaced the line
$this->newsRecurrenceRepository->remove($oldRec);
with this piece of code:
$cmd = [];
$cmd['tx_datednews_domain_model_newsrecurrence'][$oldRec->getUid()]['delete'] = true;
$pObj->start([], $cmd);
$pObj->process_cmdmap();

How to make file_reference in extbase extension in TYPO3 6.1 work?

I have set up a small extension with the extension builder containing a few fields, one of which is the internal_type: 'file_reference'.
'dokument' => array(
'exclude' => 0,
'label' => 'LLL:EXT:publikationen/Resources/Private/Language/locallang_db.xlf:tx_publikationen_domain_model_publikation.dokument',
'config' => array(
'type' => 'group',
'internal_type' => 'file_reference',
//'uploadfolder' => 'uploads/tx_publikationen',
'allowed' => '*',
'disallowed' => 'php',
'size' => 5,
),
),
The field appears in the backend, but the Element browser is unable to show any files to select:
If I remove the "bparams" parameter from the URL shown above, it is able to see the files that are there.
How can this be brought to work?
FAL fields require complicated configuration. To make that easier, there is a function returning the TCA config for such a field.
Its usage for a field that allows only one file looks like this:
'dokument' => array(
'label' => 'LLL:EXT:publikationen/Resources/Private/Language/locallang_db.xlf:tx_publikationen_domain_model_publikation.dokument',
'exclude' => 0,
'config' => \TYPO3\CMS\Core\Utility\ExtensionManagementUtility::getFileFieldTCAConfig(
'dokument',
array(
'maxitems' => 1,
'minitems' => 1,
'appearance' => array(
'enabledControls' => array(
'dragdrop' => FALSE,
'localize' => FALSE,
),
),
)
),
),
A look into the source code of that function makes me not want to do that manually.

How to validate a checkbox in ZF2

I've read numerous workarounds for Zend Framework's lack of default checkbox validation.
I have recently started using ZF2 and the documentation is a bit lacking out there.
Can someone please demonstrate how I can validate a checkbox to ensure it was ticked, using the Zend Form and Validation mechanism? I'm using the array configuration for my Forms (using the default set-up found in the example app on the ZF website).
Try this
Form element :
$this->add(array(
'type' => 'Zend\Form\Element\Checkbox',
'name' => 'agreeterms',
'options' => array(
'label' => 'I agree to all terms and conditions',
'use_hidden_element' => true,
'checked_value' => 1,
'unchecked_value' => 'no'
),
));
In filters, add digit validation
use Zend\Validator\Digits; // at top
$inputFilter->add($factory->createInput(array(
'name' => 'agreeterms',
'validators' => array(
array(
'name' => 'Digits',
'break_chain_on_failure' => true,
'options' => array(
'messages' => array(
Digits::NOT_DIGITS => 'You must agree to the terms of use.',
),
),
),
),
)));
You could also just drop the hidden form field (which I find a bit weird from a purist HTML point of view) from the options instead of setting its value to 'no' like this:
$this->add(array(
'type' => 'Zend\Form\Element\Checkbox',
'name' => 'agreeterms',
'options' => array(
'label' => 'I agree to all terms and conditions',
'use_hidden_element' => false
),
));
I had the same problem and did something similar to Optimus Crew's suggestion but used the Identical Validator.
If you don't set the checked_value option of the checkbox and leave it as the default it should pass in a '1' when the data is POSTed. You can set it if you require, but make sure you're checking for the same value in the token option of the validator.
$this->filter->add(array(
'name' => 'agreeterms',
'validators' => array(
array(
'name' => 'Identical',
'options' => array(
'token' => '1',
'messages' => array(
Identical::NOT_SAME => 'You must agree to the terms of use.',
),
),
),
),
));
This won't work if you use the option 'use_hidden_element' => false for the checkbox for the form. If you do this, you'll end up displaying the default NotEmpty message Value is required and can't be empty
This isn't directly related to the question, but here's some zf2 checkbox tips if you're looking to store a user's response in the database...
DO use '1' and '0' strings, don't bother trying to get anything else to work. Plus, you can use those values directly as SQL values for a bit/boolean column.
DO use hidden elements. If you don't, no value will get posted with the form and no one wants that.
DO NOT try to filter the value to a boolean. For some reason, when the boolean value comes out to be false, the form doesn't validate despite having 'required' => false;
Example element creation in form:
$this->add([
'name' => 'cellPhoneHasWhatsApp',
'type' => 'Checkbox',
'options' => [
'label' => 'Cell phone has WhatsApp?',
'checked_value' => '1',
'unchecked_value' => '0',
'use_hidden_element' => true,
],
]);
Example input filter spec:
[
'cellPhoneHasWhatsApp' => [
'required' => false,
],
]
And here's an example if you want to hide some other form fields using bootstrap:
$this->add([
'name' => 'automaticTitle',
'type' => 'Checkbox',
'options' => [
'label' => 'Automatically generate title',
'checked_value' => '1',
'unchecked_value' => '0',
'use_hidden_element' => true,
],
'attributes' => [
'data-toggle' => 'collapse',
'data-target' => '#titleGroup',
'aria-expanded' => 'false',
'aria-controls' => 'titleGroup'
],
]);
I'm a ZF2 fan, but at the end of the day, you just have to find out what works with it and what doesn't (especially with Forms). Hope this helps somebody!
Very old question, but figured it might still be used/referenced by people, like me, still using Zend Framework 2. (Using ZF 2.5.3 in my case)
Jeff's answer above helped me out getting the right config here for what I'm using. In my use case I require the Checkbox, though leaving it empty will count as a 'false' value, which is allowed. His answer helped me allow the false values, especially his:
DO NOT try to filter the value to a boolean. For some reason, when the boolean value comes out to be false
The use case is to enable/disable certain entities, such as Countries or Languages so they won't show up in a getEnabled[...]() Repository function.
Form element
$this->add([
'name' => 'enabled',
'required' => true,
'type' => Checkbox::class,
'options' => [
'label' => _('Enabled'),
'label_attributes' => [
'class' => '',
],
'use_hidden_element' => true,
'checked_value' => 1,
'unchecked_value' => 0,
],
'attributes' => [
'id' => '',
'class' => '',
],
]);
Input filter
$this->add([
'name' => 'enabled',
'required' => true,
'validators' => [
[
'name' => InArray::class,
'options' => [
'haystack' => [true, false],
],
],
],
])