Extending an Extbase model 

Once you have added a new field to the TCA it will be displayed in the backend forms.

However, if the extension you are trying to extend is based on Extbase the new field is not available in the frontend out of the box. Further steps are needed to make the fields available. These steps will not work in all cases.

Quick overview 

Follow these steps:

  1. Is your extension the only extension trying to extend the original model in your installation?
  2. Find the original model. If the model has the final modifier, refer to the extension documentation on how to display additional fields.
  3. Find the original repository. If the repository is final, refer to the extension documentation on how to display additional fields.
  4. Extend the original model in your extension or sitepackage.
  5. Register your extended model with the corresponding database table in EXT:my_extension/Configuration/Extbase/Persistence/Classes.php.
  6. Extend the original repository in your extension or sitepackage.
  7. Register your extended repository so that it is used instead of the original one.

Step by step 

Are you the only one trying to extend that model? 

Search for other classes in your installation that extend the original model or repository (see below).

If the model is already extended but you only need to create the fields for your current installation you can proceed by extending the extended model. In the rest of this tutorial use the extended model as the original model.

If the model has different record types you can add a new type and only extend that one type. This is commonly done when extending the georgringer/news model.

If you are planning to publish this extension, search Packagist and the TER (TYPO3 extension repository) for extensions that also extend the original model. If necessary, put them in the conflict sections of your extension's composer.json and ext_emconf.php.

Finding the original model 

The model should be located in the original extension in EXT:original_extension/Classes/Domain/Model/ or a subdirectory. If the model is not there it might:

  • be located in a different extension
  • not be an Extbase model (then you cannot follow this tutorial)

You can also try debugging the model with a Fluid template that outputs the model:

Some Fluid template that uses the model
<f:debug>{someModel}</f:debug>
Copied!

If you debugged the correct object, the fully qualified PHP name of the model will appear in the debug output. This will give you further hints on where to find the associated class. You could, for example, do a full text search for the namespace of the class.

If the class of the model is final:

EXT:original_extension/Classes/Domain/Model/SomeModel.php
final class SomeModel {
    // ...
}
Copied!

it cannot be extended using the instructions in this tutorial. Refer to the documentation of the original extension.

Finding the original repository 

In Extbase the repository of a model usually has the same class name as the model, prefixed with "Repository". It is located in the same domain directory as the model, but in the Repository subfolder.

For example, if the model is Classes/Domain/Model/SomeModel.php the repository is located in Classes/Domain/Repository/SomeModelRepository.php.

  • If you can't find the repository but have found the model, the extension might not be using an Extbase repository. This tutorial will not help you in this case as it is only relevant for Extbase repositories.
  • If you find a repository according to this naming scheme but it does not extend
    the class

    \TYPO3\CMS\Extbase\Persistence\Repository directly or indirectly, it is also not an Extbase repository.

  • If the repository is final it cannot be extended.

In all these cases refer to the extension documentation on how to extend it.

Extend the original model 

We assume that you have already extended the database table and TCA (table configuration array) as described in Extending TCA. Extend the original model in your extension using a class:

EXT:my_extension/Classes/Domain/Model/MyExtendedModel.php
<?php

declare(strict_types=1);

namespace MyVendor\MyExtension\Domain\Model;

use OriginalVendor\OriginalExtension\Domain\Model\SomeModel;

class MyExtendedModel extends SomeModel
{
    protected string $txMyExtensionAdditionalField;

    public function getTxMyExtensionAdditionalField(): string
    {
        return $this->txMyExtensionAdditionalField;
    }

    public function setTxMyExtensionAdditionalField(string $txMyExtensionAdditionalField): void
    {
        $this->txMyExtensionAdditionalField = $txMyExtensionAdditionalField;
    }
}
Copied!

Add all the additional fields that you require. By convention the database fields and the model names are prefixed with the name of your extension.

Register the extended model 

The extended model needs to be registered for Extbase persistence in files Configuration/Extbase/Persistence/Classes.php and ext_localconf.php.

EXT:my_extension/Configuration/Extbase/Persistence/Classes.php
<?php

declare(strict_types=1);

use MyVendor\MyExtension\Domain\Model\MyExtendedModel;

return [
    MyExtendedModel::class => [
        'tableName' => 'tx_originalextension_somemodel',
    ],
];
Copied!
EXT:my_extension/ext_localconf.php
<?php

declare(strict_types=1);

use MyVendor\MyExtension\Domain\Model\MyExtendedModel;
use OriginalVendor\OriginalExtension\Domain\Model\SomeModel;

defined('TYPO3') or die('Access denied.');

$GLOBALS['TYPO3_CONF_VARS']['SYS']['Objects'][SomeModel::class] = [
    'className' => MyExtendedModel::class,
];
Copied!

Extend the original repository (optional) 

Similarly, extend the original repository:

EXT:my_extension/Classes/Domain/Repository/MyExtendedModelRepository.php
<?php

declare(strict_types=1);

namespace MyVendor\MyExtension\Domain\Repository;

use OriginalVendor\OriginalExtension\Domain\Repository\SomeModelRepository;

class MyExtendedModelRepository extends SomeModelRepository
{
    /* Unless you need additional methods you can leave the class body empty */
}
Copied!

The rule that a repository must follow the naming schema of the model also applies when extending model and repository. So the new repository's name must end with "Repository" and it must be in the Domain/Repository directory.

If you don't need additional repository methods you can leave the body of this class empty. However, for internal Extbase reasons you have to create the repository even if you don't add additional functionality.

Register the extended repository 

The extended repository needs to be registered with Extbase in your extension file EXT:my_extension/ext_localconf.php. This tells Extbase to use your repository instead of the original one whenever the original repository is requested via Dependency Injection in a controller or service.

EXT:my_extension/ext_localconf.php
<?php

declare(strict_types=1);

use MyVendor\MyExtension\Domain\Repository\MyExtendedRepository;
use OriginalVendor\OriginalExtension\Domain\Repository\SomeRepository;

defined('TYPO3') or die('Access denied.');

$GLOBALS['TYPO3_CONF_VARS']['SYS']['Objects'][SomeRepository::class] = [
    'className' => MyExtendedRepository::class,
];
Copied!

Alternative strategies to extend Extbase models 

There is a TYPO3 extension that extends models and functions to classes by implementing the proxy pattern: Extbase Domain Model Extender (evoweb/extender).

This extension can be used to extend models of tt_address, for example.

The popular extension EXT:news (georgringer/news) has a special generator that can be used to add new fields to news models.