Skip to content

Testbase::dumpClassLoadingInformation() writes into the real project root even in composer mode #725

Description

@p2media

Testbase::dumpClassLoadingInformation() (Classes/Core/Testbase.php:767-773) is called unconditionally from Resources/Core/Build/UnitTestsBootstrap.php (and internally from setUpBasicTypo3Bootstrap() for functional tests), with no check for composer mode:

public function dumpClassLoadingInformation(): void
{
    if (!ClassLoadingInformation::isClassLoadingInformationAvailable()) {
        ClassLoadingInformation::dumpClassLoadingInformation();
        ClassLoadingInformation::registerClassLoadingInformation();
    }
}

Every other caller of this functionality in typo3/cms-core (DumpAutoloadCommand, MaintenanceController, SetupService, ClassLoadingInformationUpdater) guards it with !Environment::isComposerMode(), since dumping classic-mode autoload info is meaningless when Composer's own autoloader is authoritative. This one call site doesn't, so every phpunit run using the shipped UnitTestsBootstrap.php (or any functional test) dumps autoload_classmap.php, autoload_psr4.php, autoload_files.php, autoload_classaliasmap.php into ClassLoadingInformation::getClassLoadingInformationDirectory().

In a composer-mode project using the "new directory structure" (project root ≠ public web root), that directory resolves to <project-root>/packages/autoload/ (TYPO3\CMS\Core\Core\Environment::$extensionsBasePath = $projectPath . '/packages/ext', and ClassLoadingInformation derives its dump dir from dirname() of that path). Many TYPO3 projects — including the pattern documented in TYPO3's own Composer best-practices guide — use exactly packages/ at the project root for their own local extensions (symlinked via a composer path repository), so every test run leaves an untracked, uncommitted packages/autoload/ directory sitting next to the project's real local extensions.

GuardDumpClassLoadingInformationInComposerMode.patch

Steps to reproduce

  1. Set up a TYPO3 14 project in composer mode with the "new directory structure" (extra."typo3/cms".web-dir set to e.g. public), with a local extensions folder at <project-root>/packages/.
  2. Require typo3/testing-framework and copy UnitTestsBootstrap.php per the documented setup.
  3. Run vendor/bin/phpunit -c <your-unit-tests-config>.xml, even with zero test cases.
  4. Observe <project-root>/packages/autoload/{autoload_classmap.php,autoload_psr4.php,autoload_files.php,autoload_classaliasmap.php} being created.

Expected behavior

No classic-mode autoload dump should happen in composer mode, consistent with how typo3/cms-core treats this everywhere else.

Suggested fix

Guard Testbase::dumpClassLoadingInformation() with Environment::isComposerMode(), mirroring the guard used in typo3/cms-core's own call sites. Patch attached / PR to follow:

     public function dumpClassLoadingInformation(): void
     {
+        if (Environment::isComposerMode()) {
+            return;
+        }
         if (!ClassLoadingInformation::isClassLoadingInformationAvailable()) {
             ClassLoadingInformation::dumpClassLoadingInformation();
             ClassLoadingInformation::registerClassLoadingInformation();
         }
     }

(plus use TYPO3\CMS\Core\Core\Environment;)

Specify some data of the environment

  • TYPO3 testing framework version: 9.5.0
  • TYPO3 version: 14.3.4
  • TYPO3 installation type: composer
  • PHP version: 8.4
  • Web server used + version: Apache 2.4.67 (Debian)
  • Operating system: Linux Debian

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Type

    No type

    Fields

    No fields configured for issues without a type.

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions