AJAX in TYPO3: TypoScript typeNum, Extbase und Middleware

AJAX in TYPO3: TypoScript typeNum, Extbase und Middleware

Moderne Websites setzen häufig auf AJAX (Asynchronous JavaScript and XML), um dynamische, reaktionsschnelle Benutzererlebnisse zu liefern, ohne die gesamte Seite neu zu laden. In TYPO3 können wir die Macht von AJAX nutzen, indem wir einen dedizierten typeNum-Endpunkt in TypoScript einrichten und asynchrone Aufrufe mit einem Extbase-Controller verarbeiten. Dieser Blog-Post führt Sie durch die einzelnen Schritte - von der Konfiguration von TypoScript für AJAX bis zur Rückgabe von JSON-Antworten und deren Verwendung in Ihrem Frontend-JavaScript. Kurz gesagt: Sie lernen, wie man AJAX in TYPO3 mit TypoScript und Extbase implementiert.

Was ist die kurze Antwort?

Für AJAX in TYPO3 stellen Sie einen Endpunkt bereit, der JSON liefert, und rufen ihn mit fetch() oder XMLHttpRequest auf. Nutzen Sie ein PAGE-Objekt mit eigener typeNum für einen schnellen Extbase-Endpunkt, eine PSR-15 Middleware für leichte Routen oder eine Extbase-Action mit jsonResponse(). Alle drei Wege funktionieren in TYPO3 v13.4 LTS und v14.

Das Wichtigste in Kürze

  • Eine typeNum erzeugt einen eigenen Seitentyp. Mit disableAllHeaderCode = 1 enthält die Antwort kein Seiten-HTML.
  • Setzen Sie config.no_cache = 1 nicht für den ganzen Seitentyp. Die TypoScript-Referenz empfiehlt, den Cache nur für das Objekt zu deaktivieren, das es braucht, zum Beispiel mit COA_INT.
  • Extbase-Actions müssen ein ResponseInterface zurückgeben. $this->jsonResponse() ist die dokumentierte Abkürzung für JSON.
  • Eine PSR-15 Middleware antwortet, bevor die Seite gerendert wird, bietet aber weder Extbase noch Fluid.
  • Prüfen Sie den Zugriff im Endpunkt. Seit TYPO3 14.2 bietet Extbase die Attribute #[Authorize] und #[RateLimit].

Getestet mit / gültig für: TYPO3 v13.4 LTS und v14. Aktualisiert: November 2026

Welche AJAX-Methode passt zu meinem TYPO3-Projekt?

Wählen Sie typeNum, wenn Sie bereits ein Extbase-Plugin haben, eine Middleware für kleine eigenständige Endpunkte und eine Extbase-JSON-Action, wenn die Logik in einen Controller mit Repositories gehört.

MethodeFunktioniert inAm besten fürEinschränkung
PAGE mit typeNum (TypoScript)v13.4 LTS und v14Ein vorhandenes Extbase-Plugin als JSON-Endpunkt nutzenLäuft durch das Frontend-Rendering. Caching pro Objekt (COA_INT) steuern, statt config.no_cache zu setzen.
PSR-15 Middlewarev13.4 LTS und v14Kleine, schnelle Endpunkte wie StatusabfragenKein Extbase, kein Fluid. Routing-Prüfung und Eingabevalidierung machen Sie selbst.
Extbase-Action mit jsonResponse()v13.4 LTS und v14Geschäftslogik mit Repositories und ModellenDie Action muss ein ResponseInterface zurückgeben.

Quellen: PAGE-Beispiele, Middlewares und ActionController in der offiziellen TYPO3-Dokumentation.

Warum AJAX in TYPO3 verwenden?

  1. Verbesserte Benutzerfreundlichkeit: Sie müssen nicht die gesamte Seite neu laden, sondern nur bestimmte Komponenten aktualisieren.
  2. Bessere Leistung: Holen Sie nur die erforderlichen Daten ab und reduzieren Sie so die Serverlast und die Ladezeiten der Seite.
  3. Modular und wartungsfreundlich: Halten Sie Ihre Logik übersichtlich, indem Sie AJAX-Aufrufe in einem eigenen Controller/Aktion isolieren.

1. Erstellen eines AJAX-Endpunkts mit TypoScript

Der erste Schritt besteht darin, ein spezielles PAGE-Objekt in TypoScript zu erstellen und eine eindeutige typeNum zuzuweisen, um Ihre AJAX-Anfragen zu bearbeiten.

ajax_page = PAGE
ajax_page {
    typeNum = 123456  # Unique number for the AJAX call
    config {
        disableAllHeaderCode = 1
        additionalHeaders = Content-type:application/json
        xhtml_cleaning = 0
        admPanel = 0
        debug = 0
        no_cache = 1
    }

    10 = USER
    10 {
        userFunc = TYPO3\CMS\Extbase\Core\Bootstrap->run
        extensionName = YourExtension
        pluginName = YourPlugin
        vendorName = YourVendor
        controller = YourController
        action = yourAjaxAction
    }
}

Wichtige Punkte

1. typeNum: Weisen Sie eine eindeutige Ganzzahl zu, um diese AJAX-Anfrage von anderen TYPO3-Seitentypen zu unterscheiden.
2. disableAllHeaderCode: Stellt sicher, dass keine zusätzlichen HTML-Header enthalten sind - ideal für JSON-Antworten.
3. USER: Leitet die Anfrage an Ihren Extbase-Controller/die Aktion weiter, der/die die Anfrage verarbeitet und Daten zurückgibt.

2. Implementierung des Extbase-Controllers

Als nächstes erstellen (oder aktualisieren) Sie eine Extbase-Controller-Aktion speziell für die Bearbeitung der AJAX-Anfrage. Durch die Nutzung von JsonView kann TYPO3 automatisch eine JSON-Antwort zurückgeben, die leicht in Ihrem JavaScript zu verwenden ist.

namespace Vendor\YourExtension\Controller;

use TYPO3\CMS\Extbase\Mvc\Controller\ActionController;
use TYPO3\CMS\Extbase\Mvc\View\JsonView;

class YourController extends ActionController
{
    protected $defaultViewObjectName = JsonView::class; // Return JSON response

    public function yourAjaxAction()
    {
        // Your business logic here
        $data = [
            'message' => 'Hello, this is a response from the AJAX call',
            'status' => true,
        ];

        // Assign data to the view for JSON output
        $this->view->assign('value', $data);
    }
}

Wichtige Punkte

1. JsonView: Konvertiert das zugewiesene PHP-Array/Objekt automatisch in eine JSON-Ausgabe.
2. Geschäftslogik: Führen Sie hier alle serverseitigen Operationen durch, z. B. Datenbankabfragen, Validierungen oder benutzerdefinierte Geschäftsregeln.

3. Auslösen der AJAX-Anfrage aus JavaScript

Schließlich benötigen Sie eine Möglichkeit, den neu erstellten AJAX-Endpunkt von Ihrem Frontend aus aufzurufen. Im Folgenden finden Sie ein Beispiel für die Verwendung von einfachem JavaScript (XMLHttpRequest); Sie können jedoch auch fetch() oder $.ajax() von jQuery verwenden, wenn Sie dies wünschen.

// Create an XMLHttpRequest object
var xhr = new XMLHttpRequest();

// Define the URL (with the typeNum parameter)
var url = "/?type=123456"; // Replace '123456' with your actual typeNum

// Open the request
xhr.open("POST", url, true);
xhr.setRequestHeader("Content-Type", "application/x-www-form-urlencoded");

// On successful response
xhr.onload = function() {
    if (xhr.status >= 200 && xhr.status < 300) {
        // Parse JSON response
        var response = JSON.parse(xhr.responseText);
        console.log(response);  // Handle the server response data
    } else {
        console.error('Request failed. Status: ' + xhr.status);
    }
};

// On request error
xhr.onerror = function() {
    console.error('AJAX request failed');
};

// Data to send
var data = "param1=value1&param2=value2";

// Send the request
xhr.send(data);

Wichtige Punkte

1. xhr.open("POST", url, true): Legt die HTTP-Methode (GET oder POST), die Ziel-URL und das Asynchronitätsflag fest.
2. xhr.setRequestHeader(): (Optional) Verwenden Sie dies, um Inhaltstypen oder benutzerdefinierte Kopfzeilen festzulegen.
3. Antwort-Verarbeitung: JSON-Antworten können mit JSON.parse() geparst werden, um den Zugriff zu erleichtern.

Kostenlose TYPO3-Leitfäden

Lesen Sie unsere kostenlosen TYPO3-Leitfäden für Entwickler und Integratoren, direkt nutzbar im nächsten Projekt.

Kostenlose TYPO3-Leitfäden öffnen

4. (Optional) Konfigurieren Sie saubere URLs mit Routing

Für TYPO3 v9 und höher können Sie Ihren AJAX-Endpunkt benutzerfreundlicher gestalten, indem Sie Routenerweiterungen einrichten. Definieren Sie in Ihrer config.yaml eine Route für Ihre typeNum:

routeEnhancers:
  AjaxType:
    type: Simple
    defaultController: 'Vendor\YourExtension\Controller\YourController::yourAjaxAction'
    requirements:
      type: '\d+'
    default: ''

So können Sie hübsche URLs erstellen, anstatt /?type=123456 zu verwenden. Passen Sie Ihre JavaScript-Anfrage entsprechend an.

Beispiel aus der Praxis

Ein typisches Szenario ist die Auflistung von Datensätzen aus einer Extension, wie sie z.B. unser TYPO3 Extension Helpdesk verwendet:

listAction = PAGE
listAction {
    typeNum = 741852
    config {
        disableAllHeaderCode = 1
        additionalHeaders = Content-type:application/json
        xhtml_cleaning = 0
        admPanel = 0
    }

    10 = USER
    10 < styles.content.get
    10 {
        userFunc = TYPO3\CMS\Extbase\Core\Bootstrap->run
        extensionName = NsHelpdesk
        pluginName = Helpdesk
        vendorName = NITSAN
        controller = Tickets
        switchableControllerActions {
            Tickets {
                1 = list
            }
        }

        # Carry plugin settings along in the AJAX call
        stdWrap.trim = 1
        select {
            where = list_type = "nshelpdesk_helpdesk"
        }
        renderObj < tt_content.list.20.nshelpdesk_helpdesk
    }
}

Durch den Verweis auf /?type=741852 (oder Ihre ausgefallene Route, falls konfiguriert) können Sie asynchron eine Liste von Support-Tickets von Helpdesk abrufen und sie in Ihrem JavaScript-Code bearbeiten.

Wie gebe ich JSON aus einer Middleware oder Extbase-Action zurück?

Beide Alternativen umgehen den Seitentyp mit typeNum. Eine PSR-15 Middleware antwortet früh im Request, eine Extbase-Action liefert ihr JSON mit jsonResponse().

Option A: PSR-15 Middleware

TYPO3 setzt für eingehende Requests PSR-15 Middlewares ein. Dieses Beispiel aus der TYPO3-Dokumentation liefert JSON für den Pfad /check:

 

<?php

declare(strict_types=1);

namespace MyVendor\MyExtension\Middleware;

use Psr\Http\Message\ResponseFactoryInterface;
use Psr\Http\Message\ResponseInterface;
use Psr\Http\Message\ServerRequestInterface;
use Psr\Http\Server\MiddlewareInterface;
use Psr\Http\Server\RequestHandlerInterface;

class StatusCheckMiddleware implements MiddlewareInterface
{
    public function __construct(
        private readonly ResponseFactoryInterface $responseFactory,
    ) {}

    public function process(ServerRequestInterface $request, RequestHandlerInterface $handler): ResponseInterface
    {
        if ($request->getRequestTarget() === '/check') {
            $response = $this->responseFactory->createResponse()
                ->withHeader('Content-Type', 'application/json; charset=utf-8');
            $response->getBody()->write(json_encode(['status' => 'ok']));
            return $response;
        }
        return $handler->handle($request);
    }
}

 

Registrieren Sie sie im Frontend-Stack in EXT:my_extension/Configuration/RequestMiddlewares.php:

 

<?php

return [
    'frontend' => [
        'my-extension/status-check' => [
            'target' => \MyVendor\MyExtension\Middleware\StatusCheckMiddleware::class,
        ],
    ],
];

 

Option B: Extbase-Action mit jsonResponse()

Extbase-Controller-Actions müssen ein ResponseInterface zurückgeben, wie die Dokumentation zum ActionController beschreibt. Für JSON geben Sie die Abkürzung $this->jsonResponse() zurück, statt den JsonView aus dem Beispiel oben zu verwenden:

 

public function yourAjaxAction(): ResponseInterface
{
    $data = ['message' => 'Hallo aus dem AJAX-Aufruf', 'status' => true];
    return $this->jsonResponse(json_encode($data));
}

 

Aktualisierung zum TypoScript-Beispiel

Seit TYPO3 12.3 können Sie ein Extbase-Plugin mit dem Content-Objekt EXTBASEPLUGIN registrieren, statt USER mit Bootstrap->run zu verwenden. Der alte Weg funktioniert weiterhin, wie der Changelog festhält:

 

ajax_page.10 = EXTBASEPLUGIN
ajax_page.10.extensionName = YourExtension
ajax_page.10.pluginName = YourPlugin

 

Suchen Sie fertige Funktionen statt Eigenentwicklung? Sehen Sie sich unsere TYPO3 Extensions an. Weiterführend: benutzerdefinierte TYPO3 Middleware erstellen und Switchable Controller Actions in Extbase migrieren.

Wie sichere und cache ich einen AJAX-Endpunkt?

Behandeln Sie jeden Endpunkt wie eine öffentliche URL: Eingaben validieren, Aufrufer prüfen und nur Antworten cachen, die sich gefahrlos teilen lassen.

  • Nutzen Sie GET für lesende Requests und POST für Requests, die Daten ändern, und validieren Sie jeden Parameter auf dem Server.
  • Seit TYPO3 14.2 kann #[Authorize] für eine Extbase-Action einen Frontend-Login oder Benutzergruppen verlangen.
  • Seit TYPO3 14.2 begrenzt #[RateLimit] die Requests pro IP-Adresse. Es funktioniert nur für ungecachte Extbase-Actions.
  • Statt config.no_cache = 1 kapseln Sie nur das dynamische Objekt in COA_INT, wie die TypoScript-Referenz zeigt.

Häufige Fehler und Fehlersuche

  • HTML um das JSON: Setzen Sie config.disableAllHeaderCode = 1 am PAGE-Objekt.
  • Browser behandelt die Antwort als HTML: Senden Sie den Header Content-type:application/json oder nutzen Sie in Extbase jsonResponse().
  • Endpunkt liefert die normale Seite: Prüfen Sie, ob die typeNum eindeutig und das TypoScript geladen ist.
  • Alte Daten nach einer Änderung: Die Antwort wurde gecacht. Leeren Sie den Cache und machen Sie das dynamische Objekt ungecacht.
  • Action bricht mit Fehler ab: Stellen Sie sicher, dass die Action ein ResponseInterface zurückgibt.

Weitere Fragen

Was ist der Unterschied zwischen typeNum und Middleware?

Eine typeNum ist ein Seitentyp, den TYPO3 über das Frontend rendert, sodass Plugins und TypoScript wiederverwendbar sind. Eine Middleware läuft früher im Request und liefert direkt eine Antwort. Sie ist leichter, doch Routing und Validierung bauen Sie selbst.

Brauche ich Extbase für AJAX in TYPO3?

Nein. Eine PSR-15 Middleware kann JSON ohne Extbase liefern, wie die TYPO3-Dokumentation zeigt. Extbase lohnt sich, wenn Sie Repositories, Modelle und Validierung in einem Controller nutzen möchten.

Kann ich fetch() statt XMLHttpRequest verwenden?

Ja. fetch() ist eine Browser-API und funktioniert mit jedem TYPO3-Endpunkt, der JSON liefert. Rufen Sie dieselbe URL auf, zum Beispiel /?type=123456, und lesen Sie die Antwort mit response.json().

Ist config.no_cache = 1 für AJAX nötig?

Nein. Viele Tutorials setzen es, doch die TypoScript-Referenz rät, den Cache nur für das Objekt zu deaktivieren, das dynamisch bleiben muss, zum Beispiel mit COA_INT, und alle anderen Caches unangetastet zu lassen.

Upgrade-Leitfaden für TYPO3

Planen Sie den Wechsel auf eine aktuelle TYPO3-Version? Folgen Sie unserem Upgrade-Leitfaden Schritt für Schritt.

TYPO3 Upgrade-Leitfaden lesen

Schlussfolgerung

Die Implementierung von AJAX in TYPO3 mit TypoScripts typeNum und Extbase ist einfach und leistungsstark. Indem Sie Ihre AJAX-Logik in eine dedizierte Controller-Aktion auslagern, halten Sie das System sauber, modular und einfach zu pflegen. Egal, ob Sie kleine Komponenten aktualisieren oder eine komplette Single-Page-Anwendung erstellen, die Flexibilität von TYPO3 macht alles möglich.

Haben Sie Fragen oder besondere Anwendungsfälle? Schreiben Sie sie in die Kommentare oder wenden Sie sich an die T3Planet Community. Wir würden uns freuen zu hören, wie Sie AJAX in Ihren TYPO3 Projekten einsetzen!

Viel Spaß beim AJAX-Einsatz mit TYPO3!

Bevorzugen Sie eine fertige TYPO3-Extension oder eine individuelle Lösung?

Entdecken Sie fertige und individuell entwickelte TYPO3-Extensions im T3Planet Shop – entwickelt für Performance, Skalierbarkeit und konkrete Projektanforderungen.

  • 200+ Individuell entwickelte TYPO3-Extensions
  • 90+ Score bei TYPO3 SEO, Geschwindigkeit & Barrierefreiheit
  • 70+ Veröffentlichte kostenlose & Premium-TYPO3-Extensions
  • 15+ Jahre TYPO3-Erfahrung
  • 5+ Bestseller-TYPO3-Extensions (T3AI, Slider Revolution etc.)
TYPO3 Extension Gig
TYPO3 Extension