Extender: Extbase class extending on steroids 

Extension key

extender

Package name

evoweb/extender

Version

11.1

Language

en

Author

Sebastian Fischer

License

This document is published under the Open Publication. license.

Rendered

Sat, 06 Dec 2025 19:59:48 +0000

Copyright

2014-2023


Makes extending classes fully transparent

The content of this document is related to TYPO3, a GNU/GPL CMS/Framework available from http://typo3.org


Table of Contents

Introduction 

This Documentation was written for version 7.0.x of the extension.

Extending classes 

The sole purpose of this extension is to fill a gap that extbase leaves open.

As it is not possible to extend classes in extbase directly its sometimes not possible to add properties and methods to a class. This is valid for all cases where the class is given as an type hint to an action.

Arguments of an action are mapped from the request to the concrete class by the argument mapper. The argument mapper does not take TypoScript object className mapping into account as the property mapper. Due to this its not possible to just extend the class and have the extends available.

To cope with this and be able to add custom properties to a class the extender registers a custom spl class loader. This kicks in for every configured class and required a compiled class from the class cache.

The class cache gets generated on every hit where an configured compilation is not available and after every clear system cache. In both cases the class cache manager rebuilds the complete class cache.

As the class cache is registered to the system cache group it gets cleared on every clear system cache or clear all caches. After that a hook gets called that rebuilds the class cache. Unless a huge amount of extends are configured there should be a prefilled class cache on every request.

Deep dive into an example 

The cache manager parses the base and extend files to gather the colored parts of the following images, generates a combined file as shown in the merged result and adds it to the cache.

  • Base class file

  • Extend class file

  • Merged result file

Explanation 

  • Namespace

    The Namespace is taken from the base file. The namespace of the extended file is ignored.

  • Uses

    All uses from base and extending file are taken uniquely. If an use appears with diverting as alias it is present twice in the merged file.

    example of uses appearing twice
    use Psr\Log\LoggerAwareTrait;
    use Psr\Log\LoggerAwareTrait as T;
    Copied!
  • Class

    The class name and the extends part is taken from the base class.

  • Implements

    Implements are used uniquely from the base and extend file

  • Traits

    All traits from base and extend file are taken uniquely.

  • Properties

    All properties from base and extend file are taken without check if they are not colliding.

  • Construct

    The __construct of base and extend file are taken with merged contents and arguments. Where arguments from base take priority. All line of code in the method are taken. If the __construct of the extend file contains a parent::__construct call it gets removed.

  • Methods

    All methods beside __construct from base and extend file are taken without check if they are not colliding.

  • Comment

    The comment is based on the base and extending files and display which files path were taken into account.

Example source 

The base file content could be found in EXT:extender/Tests/Fixtures/Extensions/base_extension/Classes/Domain/Model/Blob.php

The extend file content is derived from EXT:extender/Tests/Fixtures/Extensions/extending_extension/Classes/Domain/Model/BlobExtend.php

Important 

Correct 

As in both files shown, it's important to use the FQCN to extend of, else the usage of the class gets written to the merged file and result in two classes with the same name in the cache file.

Correct extending
namespace Fixture\ExtendingClass\Domain\Model;

class ExtendingModel extends \Fixture\BaseClass\Domain\Model\BaseModel
{
}
Copied!
Result with correct extending
namespace Fixture\ExtendingClass\Domain\Model;

class BaseModel
{
}
Copied!

Wrong 

While linting the file will not raise an error and the class is usable, it will definitely irritate editors like PHPStorm or Visual Code.

Wrong extension
namespace Fixture\ExtendingClass\Domain\Model;

use Fixture\BaseClass\Domain\Model\BaseModel;

class ExtendingModel extends BaseModel
{
}
Copied!
Result with wrong extension
namespace Fixture\BaseClass\Domain\Model;

use Fixture\BaseClass\Domain\Model\BaseModel;

class BaseModel
{
}
Copied!

Installation 

As EXT:extender is based on composer and its mechanisms the installation is only possible with composer methods.

WARNING In previous versions it was possible to use extender when installed via the Extension Manager. This is not possible anymore.

Require via command 

You can add extender with composer require.

composer require evoweb/extender
Copied!

Modify composer.json 

Additionally evoweb/extender can be added to the require in your composer.json, like in the following example and run 'composer install'.

composer.json
{
    "require": {
        ...
        "evoweb/extender": "*"
    }
}
Copied!

Configuration 

Configure the extend of a class 

Since version 10.0.0 the registration of class extends needs to be configured in services.yaml like in this example.

Services.yaml
services:
  Fixture\ExtendingExtension\Domain\Model\BlobExtend:
    tags:
      -
        name: 'extender.extends'
        class: Fixture\BaseExtension\Domain\Model\Blob
Copied!
  • FixtureBaseExtensionDomainModelBlob is the class that should be extended
  • FixtureExtendingExtensionDomainModelBlobExtend is the class that extends

Breaking change 

Change of command name 

The command was renamed from "extender:rebuild" to "extender:clearClassCache" to better reflect what the command is doing.

Change of extending configuration in 10.0.0 

Description 

Since version 10.0.0 the registration happens in services.yaml

Impact 

All class extending in ext_localconf.php needs to be replaced and converted

Migration 

Migrate configuration from array to yaml.

before ext_localconf.php
$GLOBALS['TYPO3_CONF_VARS']['EXTENSIONS']['base_extension']['extender'][
    \Fixture\BaseExtension\Domain\Model\Blob::class
]['extending_extension'] = 'EXT:extending_extension/Classes/Domain/Model/BlobExtend.php';
Copied!
after Services.yaml
Fixture\ExtendingExtension\Domain\Model\BlobExtend:
  tags:
    -
      name: 'extender.extends'
      class: Fixture\BaseExtension\Domain\Model\Blob
Copied!

Change of extending configuration in 7.0.0 

Description 

Since version 7.0.0 all usage of EXTCONF is replaced with EXTENSIONS.

Impact 

All class extending still using EXTCONF to not work anymore. So the code still fills the array but this array is not used anymore.

Affected Installations 

All extensions that use EXTCONF in registration of class extending like.

before ext_localconf.php
$GLOBALS['TYPO3_CONF_VARS']['EXTCONF']['store_finder']['extender'][
    \Evoweb\StoreFinder\Domain\Model\Location::class
]['sitepackage'] = 'EXT:sitepackage/Classes/Domain/Model/Location.php';
Copied!

Migration 

Replace the usage of EXTCONF with EXTENSIONS to have the class extended again.

Testing 

Setting up configuration for Functional Testing in PhpStorm

Sitemap