Ajax in Extensions

Configure your Plugin and actions

You need two Controlleractions. One to start and the other for the AJAX-Call. In order to have your TS-Setup running you need two plugins.
In your ext_localconf.php:

 

ExtensionUtility::configurePlugin(
'Extensionname',
'ExtensionnameAjaxStart',
[
\Vendor\Extensionname\Controller\ExtensionnameController::class => 'listAjaxStart',
],
[
\Vendor\Extensionname\Controller\ExtensionnameController::class => 'listAjaxStart',
],
ExtensionUtility::PLUGIN_TYPE_CONTENT_ELEMENT
);

ExtensionUtility::configurePlugin(
'Extensionname',
'ExtensionnameAjax',
[
\Vendor\Extensionname\Controller\ExtensionnameController::class => 'listAjax',
],
[
\Vendor\Extensionname\Controller\ExtensionnameController::class => 'listAjax',
],
ExtensionUtility::PLUGIN_TYPE_CONTENT_ELEMENT
);

 

And in you Configuration/TCA/Overrides/tt_content.php:

$pluginKey = ExtensionUtility::registerPlugin(
       'Extensionname', // extkey
       'ExtensionnameList',  // Pluginname
       'Extensionname auflisten',  // Name in BE
       'Extensionname_svgicon2'
   );

   $pluginKey = ExtensionUtility::registerPlugin(
       'Extensionname', // extkey
       'ExtensionnameAjaxStart',  // Pluginname
       'Extensionname Ajax',  // Name in BE
       'Extensionname_svgicon2'
   );

Typoscript Setup

You need an Endpoint in order to call your AJAX-Controller. Also you must disable the header and for getting JSON-Data set the Content-type:

 


ajaxPage = PAGE
ajaxPage {
typeNum = {$pegelstandtypeNum}
config {
disableAllHeaderCode = 1
additionalHeaders = Content-type:application/json
xhtml_cleaning = 0
admPanel = 0
debug = 0
no_cache = 1
}

10 = USER_INT
10 {
userFunc = TYPO3\CMS\Extbase\Core\Bootstrap->run
extensionName = Extensionname
pluginName = ExtensionnameAjax
vendorName = vendorname
controller = Extensionname
action = listAjax
}
}

Your Controller

Implement your JS with the AssetCollector. Modules must have type => 'module'.
Data to start can set as arguments inside the script-tag. For example the pageid or typenum.

The AJAX-Action needs JsonResponse as return-type. Get data with json_decode(file_get_contents('php://input'),true); and return a JsonResponse.
These data where used in your javascript.

 

use TYPO3\CMS\Core\Page\AssetCollector;
use TYPO3\CMS\Core\Utility\GeneralUtility;
use Psr\Http\Message\ResponseInterface;
use TYPO3\CMS\Extbase\Mvc\Controller\ActionController;
use TYPO3\CMS\Core\Http\JsonResponse;
 class PegelstandController extends ActionController {public function listAjaxStartAction(): ResponseInterface {

$pageID = $GLOBALS['TSFE']->id;
GeneralUtility::makeInstance(AssetCollector::class)->addJavaScript( 'extensionname', 'EXT:extensionname/Resources/Public/Js/main.js', ['type' => 'module', 'data-uri' => '/index.php?id=' . $pageID, 'data-ajax-type' => $this->settings['typeNum']] );

return $this->htmlResponse();
}

public function listAjaxAction(): JsonResponse {
$input = json_decode(file_get_contents('php://input'),true);
return new JsonResponse([
'success' => true,
'data' => $data,
'values' => $values,
]);
}
}

Javascript

  • You have to import your modules.
  • Get your data inside the script-tag for starting, for example typeNum and pageId for your AJAX-Call.
  • You have to get your Data from your AJAX-Call with function fetch()
  • With $(document).ready() you can initialize your application
import { functionnames } from './helper.js';

const script = document.querySelector('script[data-uri]');
let uri = script.dataset.uri;
let type = script.dataset.ajaxType;

function fetchData(date, select) {
    return fetch(uri + '&type=' + type, {
        method: 'POST',
        headers: { 'Content-Type': 'application/json' },
        body: JSON.stringify({ date: date })
    }).then(res => res.json());
} function updateApplication(date, select) { fetchData(date).then(data => { if (!data.success) return; getApplication(data, select);
}); }$(document).ready(function () { select = document.getElementById('period'); // DOM-Element if (!select) selectedValue = 1; else selectedValue = select.value; select.addEventListener('change', function () { selectedValue = this.value; updateApplication(currentDate, selectedValue); });
updateApplication(currentDate, selectedValue);
});

 

See also: