Skip to content

Latest commit

 

History

History
192 lines (145 loc) · 4.77 KB

README_PLUGINS.md

File metadata and controls

192 lines (145 loc) · 4.77 KB

POPO Plugins

POPO architecture is fully pluggable, meaning any new or existing functionality can be customized.

There is lots of default plugins, and new ones can be added very easily.

Plugin setup with POPO Schema:

Schema:

$:
  config:
    classPluginCollection:
      - \App\Plugin\ExampleMethodPopoPlugin::class
    
    namespacePluginCollection: []
    phpFilePluginCollection: []
    propertyPluginCollection: []
    mappingPolicyPluginCollection: []

Example:
  Foo:
    property:
      - name: title

Plugin:

namespace App\Plugin;

class ExampleMethodPopoPlugin implements \Popo\Plugin\ClassPluginInterface
{
  public function run(BuilderPluginInterface $builder): void
  {
    $builder->getClass()
      ->addMethod('example')
      ->setReturnType('int')
      ->setBody('return 10;');
  }
}

Output:

class Foo
  ...
  public function example(): int
  {
      return 10;
  }
  ...
}

Plugin setup from the command line:

vendor/bin/popo generate -s popo.yml  --classPluginCollection "App\\Plugin\\ExampleMethodPopoPlugin"
  -clp, --classPluginCollection[=CLASSPLUGINCOLLECTION]                 Collection of class names for plugins implementing \Popo\Plugin\ClassPluginInterface
  -mpp, --mappingPolicyPluginCollection[=MAPPINGPOLICYPLUGINCOLLECTION] Collection of class names for plugins implementing \Popo\Plugin\MappingPolicyPluginInterface
  -nsp, --namespacePluginCollection[=NAMESPACEPLUGINCOLLECTION]         Collection of class names for plugins implementing \Popo\Plugin\NamespacePluginInterface
  -pfp, --phpFilePluginCollection[=PHPFILEPLUGINCOLLECTION]             Collection of class names for plugins implementing \Popo\Plugin\PhpFilePluginInterface
  -ppp, --propertyPluginCollection[=PROPERTYPLUGINCOLLECTION]           Collection of class names for plugins implementing \Popo\Plugin\PropertyPluginInterface

Plugin setup with PHP:

$configurator = (new PopoConfigurator)
  ->addPhpFilePluginClass(PhpFilePluginClass::class)
  ->addNamespacePluginClass(NamespacePluginClass::class)
  ->addClassPluginClass(PluginClass1:class)
  ->addClassPluginClass(PluginClass2:class)
  ->addPropertyPluginClass(PluginProperty1::class)
  ->addPropertyPluginClass(PluginProperty2::class);
    
(new PopoFacade)->generate($configurator);

Extra functionality

Apart from the typical setters and getters POPO objects have additional helper methods which ease access to, and offer more insight about the data that they represent.

Some of the methods supported by class type plugins:

  • isNew
  • fromArray
  • fromMappedArray
  • toArray
  • toMappedArray
  • toArrayCamelToSnake
  • toArraySnakeToCamel
  • modifiedToArray
  • requireAll
  • listModifiedProperties
  • ...

Some of the methods supported by property type plugins:

  • set
  • get
  • require
  • has
  • addCollectionItem
  • ...

Note: Plugins can be disabled with:

$configurator = (new PopoConfigurator)
    ->setClassPluginCollection([])
    ->setPropertyPluginCollection([])
    ...

Generating Code with Plugins

POPO generation process is split into few parts:

  • PHP file header code generation
  • Namespace code generation
  • Class methods code generation
  • Properties and property methods code generation

Each has corresponding set of plugins.

  • Popo\Plugin\PhpFilePluginInterface

    Generates code related to PHP header, e.g. strict type, file comments.

      interface PhpFilePluginInterface
      {
          public function run(PhpFile $file, Schema $schema): PhpFile;
      }
  • Popo\Plugin\NamespacePluginInterface

    Generates code related to namespace, e.g. aliases, use statements.

    interface NamespacePluginInterface
    {
        public function run(BuilderPluginInterface $builder, PhpNamespace $namespace): PhpNamespace;
    }
  • Popo\Plugin\ClassPluginInterface

    Generates code related to class methods, e.g. toArray(), isNew(), extends or implements keywords.

    interface ClassPluginInterface
    {
        public function run(BuilderPluginInterface $builder): void;
    }
  • Popo\Plugin\PropertyPluginInterface

    Generates code related to properties and their methods, e.g. hasFoo(), getFoo(), setFoo().

    interface PropertyPluginInterface
    {
        public function run(BuilderPluginInterface $builder, Property $property): void;
    }

Mapping policy plugins

The plugins responsible for code related to schema key mapping, e.g. transforming foo_id to fooId.

interface Popo\Plugin\MappingPolicyPluginInterface
{
    public function run(string $key): string;
}

See src/Popo/Plugin.

More Examples

See fixtures and tests for more usage examples.