Repository navigation
#276 - TransformerRegistry: lazy-load transformers through a service locator indexed by code - #293
Merged
Merged
Conversation
…locator indexed by code - New "code" attribute of the cleverage.transformer tag, and new #[AsTransformer(code: '...')] attribute (autoconfiguration) adding it. - New internal TransformerLocatorCompilerPass (replaces RegistryCompilerPass, deprecated): the transformers with a code go in a service locator given to TransformerRegistry (new optional constructor argument), and are only instantiated when used; duplicate / invalid codes fail the compilation. Without code, the transformer is still added eagerly with addTransformer(), deprecated since 5.4 (code required in v6.0, #280). - TransformerRegistry checks that the code of the locator is the one returned by getCode(), memoizes the fetched transformers; getTransformers() still returns every transformer. - The 37 bundle transformers and the generic transformers are tagged with their code. - Tests no longer use the deprecated addTransformer(); documentation updated. Co-Authored-By: Claude Opus 5.5 (1M context) <noreply@anthropic.com>
This was referenced Oct 14, 2026
- TransformerInterface::getCode(): @deprecated since 5.4 (the code is given by the "code" attribute of the cleverage.transformer tag or #[AsTransformer]), removed from the interface in v6.0 (#280). PHPDoc only: no runtime notice is possible for an interface method (nor reported by DebugClassLoader). - UnavailableServicesCompilerPass reads the code of the replaced transformer from its tag, getCode() (by reflection) only for a definition tagged without code. - Documentation: custom transformers (getCode() deprecation, paragraph split). Co-Authored-By: Claude Opus 5.5 (1M context) <noreply@anthropic.com>
The CI runs PHPUnit with code coverage (beStrictAboutCoverageMetadata): - testAsTransformerAttributeRegistersTheCode: declare AsTransformer as used; - the check of the transformer codes runs getCode() of every transformer of the bundle: moved to a #[CoversNothing] TransformerCodesTest. Co-Authored-By: Claude Opus 5.5 (1M context) <noreply@anthropic.com>
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Description
Fixes #276: until now, building
TransformerRegistryinstantiated every transformer (oneaddTransformer()call percleverage.transformerservice, added byRegistryCompilerPass), and asTransformerTaskand most transformers depend on the registry, running any process built all the transformers of the bundle, the bridges, the application and every generic transformer. They are now fetched lazily from a service locator indexed by code.Changes
codeattribute of thecleverage.transformertag, and new#[CleverAge\ProcessBundle\Attribute\AsTransformer(code: '...')]attribute (registered withregisterAttributeForAutoconfiguration(), adds the tag with its code).TransformerInterface::getCode()is unchanged (a static method would have been a BC break).config/services/transformer.yaml) and the generic transformers (CleverAgeProcessExtension) are tagged with their code (the bundle codes were read fromgetCode(); a test checks that every tag code is the one returned bygetCode()).TransformerLocatorCompilerPass(replacesRegistryCompilerPassfor the bundle): the tagged services with a code go in aServiceLocator(ServiceLocatorTagPass::register()), given to the registry. Duplicate codes now fail the container compilation (The transformer code "x" is used by the "a" and "b" services.) instead of the registry construction; an empty / non-string code too. A service with both a tag without code (autoconfiguration onTransformerInterface, DependencyInjection: add FQCN aliases and autoconfiguration for TaskInterface and TransformerInterface #272) and a tag with code (#[AsTransformer]) is registered by its code only.TransformerRegistry: new optional constructor argument?ServiceProviderInterface $locator.getTransformer()/hasTransformer()use the locator (fetched transformers memoized), check that the service is aTransformerInterfaceand that the locator code is the one returned bygetCode()(explicit exception otherwise);getTransformers()still returns every transformer (it instantiates the locator ones; not used by the bundles).codeis still registered eagerly withaddTransformer(), which is deprecated:Registering the transformer "x" (Class) with "…\TransformerRegistry::addTransformer()" is deprecated, tag its service with a "code" attribute ({ name: cleverage.transformer, code: x }) or use the #[AsTransformer] attribute instead, so that it is only instantiated when used. It will be required in v6.0.;RegistryCompilerPass(no longer used by the bundle);TransformerInterface::getCode(): the code now comes from the tag / attribute,getCode()only duplicates it; it will be removed from the interface in v6.0 (TransformerRegistry: require the code tag attribute and remove eager transformer registration (v6 step of #276) #280).@deprecatedPHPDoc only: neithertrigger_deprecation()(interface method) nor Symfony'sDebugClassLoader(it does not report the methods of an interface marked@deprecated) can give a runtime notice, it is visible to static analysis and IDEs. Until v6.0 transformers keep implementing it, returning the code of their tag (checked by the registry). In the bundle it is only still called by the deprecatedaddTransformer(), the registry check, andUnavailableServicesCompilerPassfor a definition tagged without code (it now reads the code of the tag).ServiceLocatorinstead of the deprecatedaddTransformer().#[AsTransformer], lazy loading, code check, deprecation), common setup (an_instanceofrule cannot give a code per transformer), generic transformer reference.Bridge bundles:
cleverage/soap-process-bundlehas a transformer (RequestTransformer,soap_request) tagged without code: it keeps working, with the deprecation, until it gets its code: cleverage/soap-process-bundle#45.Checks
trimis instantiated when a process uses it,trim#1works; a generic transformer (trim+ an application#[AsTransformer]one) works and instantiates its sub-transformers on use; with the serializer disabled,normalizegives the explicit message of CheckSerializerCompilerPass: do not fail the container compilation when the serializer is disabled #278.getTransformers(): 40 transformers.vendor/, then reverted):lint:containerOK,demo.transformer,demo.transformer_list,demo.transformers_edge.cached,demo.mapping_array_target_path,demo.file.csv_readerexecuted (demo.transformers_edge.slugifyfails on purpose, invalid transliterator, also without this change).UnavailableServicesCompilerPassTest(code of the tag, reflection fallback without code),TransformerRegistryTest(lazy instantiation, memoization, missing transformer, code mismatch, not a transformer,getTransformers(),addTransformer()deprecation, duplicate with the locator),TransformerLocatorCompilerPassTest(locator by code, tag with and without code, eager without code, duplicate / invalid code, no registry),CleverAgeProcessExtensionTest(every tagged transformer has the code returned bygetCode(), generic transformers,#[AsTransformer]),RegistryCompilerPassTest(deprecation).composer update(PHP 8.5): 944 tests OK, PHPStan, PHP-CS-Fixer, Rector OK. Lowest dependencies (PHP 8.2): 943 tests OK.Requirements
Breaking changes
None: transformers without code keep working (deprecated). Side effects (minor):
TransformerRegistryhas a new optional constructor argument.🤖 Generated with Claude Code