Skip to content

Simplify puli.json #173

Description

@webmozart

Right now, we mostly recommend to use the Puli CLI for configuring Puli packages. Unfortunately, using CLI programs is a problem for many developers. Therefore I propose to simplify the puli.json schema in order to make it more accessible to a larger crowd of developers.

Thanks to our JSON migrations (#96), we can do this without breaking any existing projects.

One step in this direction is described in #167.

Furthermore, I think we should rename "path-mappings" (back) to "resources", which seems easier to understand:

{
    "resources": {
        "/app": "res",
        "/twig/twig/views/exceptions": "res/views/exceptions"
    },
    "override": ["twig/twig"]
}

In addition, a "resources-dev" key should be added for resources that are only loaded in the development environment.

The entry "bindings" should be renamed to "provide" and restructured as follows:

{
    "provide": {
        "My\\Demo\\DemoBundle": "Symfony\\Component\\Kernel\\BundleInterface",
        "My\\Demo\\MoneyType": "Doctrine\\Dbal\\Type",
        "/app/trans/*.xlf": "php-fig/xliff-translations"
    }
}

Equally, "provide-dev" should be added for development-only bindings.

When an artifact should be bound to multiple types, we can use an array:

{
    "provide": {
        "/app/trans/*.xlf": [
            "php-fig/xliff-translations",
            "some-translator/xliff-translations",
        ]
    }
}

If a binding type has parameters, we can change the simple type string to an object:

{
    "provide": {
        "/app/trans/*.xlf": {
            "type": "php-fig/xliff-translations",
            "parameters": { "domain": "messages" }
        }
    }
}

This will have a few consequences:

  • It will not be possible anymore to disable bindings, since we don't store UUIDs anymore by default. I don't think this feature is highly needed.

  • Each binding type will only accept one kind of artifact (e.g. class or resource or ...) that is defined with the binding type:

    {
        "binding-types": {
            "php-fig/xliff-translations": "resource",
            "Symfony\\Component\\Kernel\\BundleInterface": "class"
        }
    }

    Depending on the artifact accepted by a binding type, we can construct the right binding class (ResourceBinding, ClassBinding, ...) for the LHS of "provide". New artifacts types can be added by providing implementations of a new BindingFactory interface (replaces Add BindingSerializer interface #171) or similar:

    class ServiceBindingFactory implements BindingFactory
    {
        public function getName()
        {
            return 'my-service';
        }
    
        public function createBindingType($name, array $parameters)
        {
            // possibility e.g. to validate $name
            return new BindingType($name, ServiceBinding::class, $parameters);
        }
    
        public function createBinding($artifact, $typeName, array $parameterValues)
        {
            // $artifact could be the service name in the container
            return new ServiceBinding($artifact, $typeName, $parameterValues);
        }
    }
    {
        "provide": {
            "My\\ServiceBindingFactory": "Puli\\Discovery\\Api\\BindingFactory,
        }
    }

    Disclaimer: I don't think adding ServiceBindings is the best example, since containers usually offer better approaches to solve this problem. I can'think of any better though right now.

Opinions?

Metadata

Metadata

Assignees

No one assigned

    Labels

    Type

    No type

    Fields

    No fields configured for issues without a type.

    Projects

    No projects

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions