Skip to content

Commit

Permalink
feat!: allow TypeFactory to be injected
Browse files Browse the repository at this point in the history
resolves: #83
  • Loading branch information
brotkrueml committed Sep 18, 2023
1 parent 1b611db commit c691bd8
Show file tree
Hide file tree
Showing 34 changed files with 201 additions and 75 deletions.
6 changes: 6 additions & 0 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
Expand Up @@ -7,9 +7,15 @@ to [Semantic Versioning](https://semver.org/spec/v2.0.0.html).

## [Unreleased]

### Added
- Method TypeFactory->create() which should be used instead of TypeFactory::createType()

### Changed
- Type model classes need to be marked with the "Type" attribute (#107)

### Deprecated
- TypeFactory::createType(), instead inject TypeFactory via DI and call create() method (#83)

### Removed
- Compatibility with TYPO3 v10 (#73)
- Compatibility with PHP 7.4 and PHP 8.0
Expand Down
2 changes: 1 addition & 1 deletion Classes/Core/ViewHelpers/AbstractBaseTypeViewHelper.php
Original file line number Diff line number Diff line change
Expand Up @@ -33,7 +33,7 @@ abstract class AbstractBaseTypeViewHelper extends ViewHelper\AbstractViewHelper
private readonly TypeStack $stack;
private readonly SchemaManager $schemaManager;

public function __construct(TypeStack $typeStack = null, SchemaManager $schemaManager = null)
public function __construct(?TypeStack $typeStack = null, ?SchemaManager $schemaManager = null)
{
$this->stack = $typeStack ?? GeneralUtility::makeInstance(TypeStack::class);
$this->schemaManager = $schemaManager ?? GeneralUtility::makeInstance(SchemaManager::class);
Expand Down
13 changes: 9 additions & 4 deletions Classes/Core/ViewHelpers/AbstractTypeViewHelper.php
Original file line number Diff line number Diff line change
Expand Up @@ -21,11 +21,16 @@ abstract class AbstractTypeViewHelper extends AbstractBaseTypeViewHelper
protected const ARGUMENT_SPECIFIC_TYPE = '-specificType';

private readonly TypeInterface $modelTemplate;
protected readonly TypeFactory $typeFactory;

public function __construct(TypeStack $typeStack = null, SchemaManager $schemaManager = null)
{
public function __construct(
?TypeStack $typeStack = null,
?SchemaManager $schemaManager = null,
?TypeFactory $typeFactory = null,
) {
parent::__construct($typeStack, $schemaManager);
$this->modelTemplate = TypeFactory::createType($this->getType());
$this->typeFactory = $typeFactory ?? new TypeFactory();
$this->modelTemplate = $this->typeFactory->create($this->getType());
}

public function initializeArguments(): void
Expand Down Expand Up @@ -53,7 +58,7 @@ private function getSpecificTypeIfDefined(): ?TypeInterface
return null;
}

return TypeFactory::createType($specificTypeFromArguments);
return $this->typeFactory->create($specificTypeFromArguments);
}

protected function getType(): string
Expand Down
9 changes: 5 additions & 4 deletions Classes/EventListener/AddBreadcrumbList.php
Original file line number Diff line number Diff line change
Expand Up @@ -32,8 +32,9 @@ final class AddBreadcrumbList
];

public function __construct(
private readonly ContentObjectRenderer $contentObjectRenderer,
private readonly ContentObjectRenderer $contentObjectRenderer,
private readonly ExtensionConfiguration $extensionConfiguration,
private readonly TypeFactory $typeFactory,
) {
}

Expand Down Expand Up @@ -85,10 +86,10 @@ public function __invoke(InitialiseTypesEvent $event): void
*/
private function buildBreadCrumbList(array $rootLine): TypeInterface
{
$breadcrumbList = TypeFactory::createType('BreadcrumbList');
$breadcrumbList = $this->typeFactory->create('BreadcrumbList');
foreach (\array_values($rootLine) as $index => $page) {
$givenItemType = ($page['tx_schema_webpagetype'] ?? '') ?: 'WebPage';
$itemType = TypeFactory::createType($givenItemType);
$itemType = $this->typeFactory->create($givenItemType);

$link = $this->contentObjectRenderer->typoLink_URL([
'parameter' => (string)$page['uid'],
Expand All @@ -97,7 +98,7 @@ private function buildBreadCrumbList(array $rootLine): TypeInterface

$itemType->setId($link);

$item = TypeFactory::createType('ListItem')->setProperties([
$item = $this->typeFactory->create('ListItem')->setProperties([
'position' => $index + 1,
'name' => $page['nav_title'] ?: $page['title'],
'item' => $itemType,
Expand Down
3 changes: 2 additions & 1 deletion Classes/EventListener/AddWebPageType.php
Original file line number Diff line number Diff line change
Expand Up @@ -26,6 +26,7 @@ final class AddWebPageType

public function __construct(
private readonly ExtensionConfiguration $configuration,
private readonly TypeFactory $typeFactory,
) {
}

Expand All @@ -46,7 +47,7 @@ public function __invoke(RenderAdditionalTypesEvent $event): void

$tsfe = $this->getTypoScriptFrontendController();
$webPageType = ($tsfe->page['tx_schema_webpagetype'] ?? '') ?: self::DEFAULT_WEBPAGE_TYPE;
$webPageModel = TypeFactory::createType($webPageType);
$webPageModel = $this->typeFactory->create($webPageType);
if ($tsfe->page['endtime'] ?? 0) {
$webPageModel->setProperty('expires', \date('c', $tsfe->page['endtime']));
}
Expand Down
29 changes: 19 additions & 10 deletions Classes/Type/TypeFactory.php
Original file line number Diff line number Diff line change
Expand Up @@ -17,11 +17,7 @@

final class TypeFactory
{
private function __construct()
{
}

public static function createType(string ...$type): TypeInterface
public function create(string ...$type): TypeInterface
{
if ($type === []) {
throw new \DomainException(
Expand All @@ -32,13 +28,26 @@ public static function createType(string ...$type): TypeInterface

$type = \array_unique($type);
if (\count($type) === 1) {
return self::createSingleType($type[0]);
return $this->createSingle($type[0]);
}

return self::createMultipleType($type);
return $this->createMultiple($type);
}

/**
* @deprecated since 3.0.0, will be removed in 4.0. Inject the TypeFactory into your class and call the method create() on that object.
*/
public static function createType(string ...$type): TypeInterface
{
\trigger_error(
'Calling the static method TypeFactory::createType() is deprecated since version 3.0.0 and will be removed in version 4.0. Inject the TypeFactory into your class and call the method create() on that object.',
\E_USER_DEPRECATED,
);

return (new self())->create(...$type);
}

private static function createSingleType(string $type): TypeInterface
private function createSingle(string $type): TypeInterface
{
/** @var TypeProvider $typeProvider */
$typeProvider = GeneralUtility::makeInstance(TypeProvider::class);
Expand All @@ -53,10 +62,10 @@ private static function createSingleType(string $type): TypeInterface
/**
* @param string[] $types
*/
private static function createMultipleType(array $types): MultipleType
private function createMultiple(array $types): MultipleType
{
return new MultipleType(...\array_map(
static fn (string $type): TypeInterface => self::createSingleType($type),
fn (string $type): TypeInterface => $this->createSingle($type),
$types,
));
}
Expand Down
3 changes: 2 additions & 1 deletion Classes/TypoScript/TypeBuilder.php
Original file line number Diff line number Diff line change
Expand Up @@ -27,6 +27,7 @@ final class TypeBuilder

public function __construct(
private readonly LoggerInterface $logger,
private readonly TypeFactory $typeFactory,
) {
}

Expand Down Expand Up @@ -62,7 +63,7 @@ private function instantiateType(array $configuration): ?TypeInterface
$configuredType = (string)$this->cObj->stdWrapValue('type', $configuration);

try {
return TypeFactory::createType($configuredType);
return $this->typeFactory->create($configuredType);
} catch (DomainException) {
// Do not break production sites, catch exception and return nothing.
$this->logger->error(
Expand Down
7 changes: 4 additions & 3 deletions Classes/ViewHelpers/BreadcrumbViewHelper.php
Original file line number Diff line number Diff line change
Expand Up @@ -98,7 +98,8 @@ public static function renderStatic(

$siteUrl = GeneralUtility::getIndpEnv('TYPO3_SITE_URL');

$breadcrumbList = TypeFactory::createType('BreadcrumbList');
$typeFactory = new TypeFactory();
$breadcrumbList = $typeFactory->create('BreadcrumbList');
$itemsCount = \count($arguments[self::ARGUMENT_BREADCRUMB]);
for ($i = 0; $i < $itemsCount; $i++) {
$id = (string)$arguments[self::ARGUMENT_BREADCRUMB][$i]['link'];
Expand All @@ -114,10 +115,10 @@ public static function renderStatic(
$webPageTypeClass = $arguments[self::ARGUMENT_BREADCRUMB][$i]['data']['tx_schema_webpagetype'];
}
*/
$itemType = TypeFactory::createType($webPageTypeClass);
$itemType = $typeFactory->create($webPageTypeClass);
$itemType->setId($id);

$item = TypeFactory::createType('ListItem')->setProperties([
$item = $typeFactory->create('ListItem')->setProperties([
'position' => $i + 1,
'name' => $arguments[self::ARGUMENT_BREADCRUMB][$i]['title'],
'item' => $itemType,
Expand Down
2 changes: 1 addition & 1 deletion Classes/ViewHelpers/MultipleTypeViewHelper.php
Original file line number Diff line number Diff line change
Expand Up @@ -29,7 +29,7 @@ public function initializeArguments(): void
public function render(): void
{
$this->types = GeneralUtility::trimExplode(',', $this->arguments['types'], true);
$model = TypeFactory::createType(...$this->types);
$model = (new TypeFactory())->create(...$this->types);
$this->addTypeToSchemaManager($model);
}

Expand Down
12 changes: 12 additions & 0 deletions Documentation/Changelog/Index.rst
Original file line number Diff line number Diff line change
Expand Up @@ -11,12 +11,24 @@ to `Semantic Versioning <https://semver.org/spec/v2.0.0.html>`_.
`Unreleased <https://github.com/brotkrueml/schema/compare/v2.10.0...HEAD>`_
-------------------------------------------------------------------------------

Added
^^^^^


* Method TypeFactory->create() which should be used instead of TypeFactory::createType()

Changed
^^^^^^^


* Type model classes need to be marked with the "Type" attribute (#107)

Deprecated
^^^^^^^^^^


* TypeFactory::createType(), instead inject TypeFactory via DI and call create() method (#83)

Removed
^^^^^^^

Expand Down
25 changes: 16 additions & 9 deletions Documentation/Developer/Api.rst
Original file line number Diff line number Diff line change
Expand Up @@ -39,14 +39,21 @@ Starting with examples
Types
-----

.. deprecated:: 3.0.0
Before version 3.0 a type was created with the static method
:php:`TypeFactory::createType()`. This has been
:ref:`deprecated <api-deprecations>`, inject the :php:`TypeFactory` into the
constructor and use :php:`TypeFactory->create()` instead (like in the example
below).

Let's start with a simple example. Imagine you describe a `person`_ on a
plugin's detail page that you want to enrich with structured markup. First you
have to create the schema model:

.. literalinclude:: _Api/_MyController1.php
:language: php
:caption: EXT:my_extension/Classes/Controller/MyController.php
:emphasize-lines: 15
:emphasize-lines: 11-14,20

The schema type `Person` maps to the model
:php:`\Brotkrueml\Schema\Model\Type\Person`. You can use every accepted type
Expand All @@ -65,29 +72,29 @@ Surely you will need to add some properties:
.. literalinclude:: _Api/_MyController2.php
:language: php
:caption: EXT:my_extension/Classes/Controller/MyController.php
:emphasize-lines: 16-20
:emphasize-lines: 20-25

That was easy ... let's go on and define an event the person attends:

.. literalinclude:: _Api/_MyController3.php
:language: php
:caption: EXT:my_extension/Classes/Controller/MyController.php
:emphasize-lines: 15-22
:emphasize-lines: 20-27

Now we have to connect the two types together:

.. literalinclude:: _Api/_MyController4.php
:language: php
:caption: EXT:my_extension/Classes/Controller/MyController.php
:emphasize-lines: 20
:emphasize-lines: 25

The defined models are ready to embed on the web page. The schema manager does
that for you:

.. literalinclude:: _Api/_MyController5.php
:language: php
:caption: EXT:my_extension/Classes/Controller/MyController.php
:emphasize-lines: 12-15,25
:emphasize-lines: 13,26


That's it ... if you call the according page the structured markup is embedded
Expand Down Expand Up @@ -126,13 +133,13 @@ be, for example, a `Product` and a `Service` at the same time - which can be
useful in some cases.

The technical difference to a single type is only that you call
:php:`\Brotkrueml\Schema\Type\TypeFactory::createType()` with more than one
:php:`\Brotkrueml\Schema\Type\TypeFactory->create()` with more than one
argument:

.. literalinclude:: _Api/_MyControllerMultiple.php
:language: php
:caption: EXT:my_extension/Classes/Controller/MyController.php
:emphasize-lines: 21-28
:emphasize-lines: 22-29

The factory method returns an instance of the
:php:`\Brotkrueml\Schema\Core\Model\MultipleType` class which provides the
Expand Down Expand Up @@ -183,7 +190,7 @@ You can accomplish this with the help of the
.. literalinclude:: _Api/_MyControllerNodeIdentifier.php
:language: php
:caption: EXT:my_extension/Classes/Controller/MyController.php
:emphasize-lines: 22-36
:emphasize-lines: 23-37

As you can see in the example, you can also use a node identifier as an
argument for :php:`->setId()` instead of a string.
Expand All @@ -205,7 +212,7 @@ The above example can also be used with a blank node identifier:
.. literalinclude:: _Api/_MyControllerBlankNodeIdentifier.php
:language: php
:caption: EXT:my_extension/Classes/Controller/MyController.php
:emphasize-lines: 22-35
:emphasize-lines: 23-36

To use a blank node identifier instantiate the class
:php:`\Brotkrueml\Schema\Core\Model\BlankNodeIdentifier`. The identifier is
Expand Down
2 changes: 1 addition & 1 deletion Documentation/Developer/Breadcrumb.rst
Original file line number Diff line number Diff line change
Expand Up @@ -51,7 +51,7 @@ Now you can iterate over the pages:
.. literalinclude:: _Breadcrumb/_MyController.php
:language: php
:caption: EXT:my_extension/Classes/Controller/MyController.php
:emphasize-lines: 21-37
:emphasize-lines: 22-38

This results in the following schema markup:

Expand Down
14 changes: 14 additions & 0 deletions Documentation/Developer/Deprecations.rst
Original file line number Diff line number Diff line change
Expand Up @@ -8,6 +8,20 @@
Deprecations
============

.. option:: \Brotkrueml\Schema\Type\TypeFactory::createType()

Deprecated since version
3.0.0

Will be removed in version
4.0.0

Alternative
Inject the :php:`TypeFactory` into the constructor and use the
:php:`create()` method.
Have a look at the :ref:`migration <migration-type-factory>` section.


.. option:: \Brotkrueml\Schema\Core\Model\AbstractType->isEmpty()

Deprecated since version
Expand Down
3 changes: 1 addition & 2 deletions Documentation/Developer/Index.rst
Original file line number Diff line number Diff line change
Expand Up @@ -78,14 +78,13 @@ method:
.. literalinclude:: _Index/_MyController1.php
:language: php
:caption: EXT:my_extension/Classes/Controller/MyController.php
:emphasize-lines: 15-16

The schema manager connects the type models to the page:

.. literalinclude:: _Index/_MyController2.php
:language: php
:caption: EXT:my_extension/Classes/Controller/MyController.php
:emphasize-lines: 12-15,24
:emphasize-lines: 13,25

The chapter :ref:`api` describes in-depth how to use the models
and the schema manager.
Expand Down
2 changes: 1 addition & 1 deletion Documentation/Developer/MainEntity.rst
Original file line number Diff line number Diff line change
Expand Up @@ -38,7 +38,7 @@ example that specifies a product as the primary content:
.. literalinclude:: _MainEntity/_MyController.php
:language: php
:caption: EXT:my_extension/Classes/Controller/MyController.php
:emphasize-lines: 21-34
:emphasize-lines: 22-35

The above example is rendered as JSON-LD. Let's assume the `WebPage` type is
set to `ItemPage` - either in the page properties or via the API or a view
Expand Down
4 changes: 2 additions & 2 deletions Documentation/Developer/WebPage.rst
Original file line number Diff line number Diff line change
Expand Up @@ -53,15 +53,15 @@ schema for a page. The `WebPage` type is no exception to that. Define a
.. literalinclude:: _WebPage/_MyController1.php
:language: php
:caption: EXT:my_extension/Classes/Controller/MyController.php
:emphasize-lines: 21-22
:emphasize-lines: 22-23

That is it. But you can add one or more properties to it - let's define a page
with a product as primary content:

.. literalinclude:: _WebPage/_MyController2.php
:language: php
:caption: EXT:my_extension/Classes/Controller/MyController.php
:emphasize-lines: 21-40
:emphasize-lines: 22-41

The example is rendered as JSON-LD:

Expand Down
Loading

0 comments on commit c691bd8

Please sign in to comment.