GithubHelp home page GithubHelp logo

yiisoft / config Goto Github PK

View Code? Open in Web Editor NEW
31.0 21.0 11.0 428 KB

Configuration management

Home Page: https://www.yiiframework.com/

License: BSD 3-Clause "New" or "Revised" License

PHP 99.48% Smarty 0.52%
config composer-plugin yii3 hacktoberfest

config's Introduction

Yii Config

Yii Config


Latest Stable Version Total Downloads Build status Code Coverage Mutation testing badge static analysis type-coverage

This Composer plugin provides assembling of configurations distributed with composer packages. It is implementing a plugin system which allows to provide the configuration needed to use a package directly when installing it to make it run out-of-the-box. The package becomes a plugin holding both the code and its default configuration.

Requirements

  • PHP 8.0 or higher.
  • Composer 2.3 or higher.

Installation

composer require yiisoft/config

How it works?

The package consist of two parts: Composer plugin and config loader.

After composer updates its autoload file, and that happens after dump-autoload, require, update or remove, Composer plugin:

  • Scans installed packages for config-plugin extra option in their composer.json.
  • Writes a merge plan into config/.merge-plan.php. It includes configuration from each package composer.json.

In the application entry point, usually index.php, we create an instance of config loader and require a configuration we need:

use Yiisoft\Config\Config;
use Yiisoft\Config\ConfigPaths;

$config = new Config(
    new ConfigPaths(dirname(__DIR__)),
);

$web = $config->get('web');

The web in the above is a config group. The config loader obtains it runtime according to the merge plan. The configuration consists of three layers that are loaded as follows:

  • Vendor configurations from each vendor/package-name. These provide default values.
  • Root package configurations from config. These may override vendor configurations.
  • Environment specific configurations from config. These may override root and vendor configurations.

Please note that same named keys are not allowed within a configuration layer.

When calling the get() method, if the configuration group does not exist, an \ErrorException will be thrown. If you are not sure that the configuration group exists, then use the has() method:

use Yiisoft\Config\Config;
use Yiisoft\Config\ConfigPaths;

$config = new Config(
    new ConfigPaths(dirname(__DIR__)),
);

if ($config->has('web')) {
    $web = $config->get('web');
}

Config groups

Each config group represents a set of configs that is merged into a single array. It is defined per package in each package composer.json:

"extra": {
    "config-plugin": {
        "params": [
            "params.php",
            "?params-local.php"
        ],
        "common": "common.php",
        "web": [
            "$common",
            "web.php",
            "../src/Modules/*/config/web.php"
        ],
        "other": "other.php"
    }
}

In the above example the mapping keys are config group names and the values are configuration files and references to other config groups. The file paths are relative to the source-directory, which by default is the path where composer.json is located.

Markers

  • ? - marks optional files. Absence of files not marked with this marker will cause exception.

    "params": [
       "params.php",
       "?params-local.php"
    ]

    It's okay if params-local.php will not be found, but it's not okay if params.php will be absent.

  • * - marks wildcard path. It means zero or more matches by wildcard mask.

    "web": [
       "../src/Modules/*/config/web.php"
    ]

    It will collect all web.php in any sub-folders of src/Modules/ in config folder. However, if the configuration folder is packaged as part of the PHAR archive, the configuration files will not be uploaded. In this case, you must explicitly specify each configuration file.

  • $ - reference to another config by its group name.

    "params": [
       "params.php",
       "?params-local.php"
    ],
    "params-console": [
       "$params",
       "params-console.php"
    ],
    "params-web": [
       "$params",
       "params-web.php"
    ]

    The config groups params-console and params-web will both contain the config values from params.php and params-local.php additional to their own configuration values.


Define your configs like the following:

return [
    'components' => [
        'db' => [
            'class' => \my\Db::class,
            'name' => $params['db.name'],
            'password' => $params['db.password'],
        ],
    ],
];

A special variable $params is read from config (by default, group is named params).

Using custom group for $params

By default, $params variable is read from params group. You can customize the group name via constructor of Config:

$config = new Config(
    new ConfigPaths(__DIR__ . '/configs'),
    null,
    [],
    'custom-params' // Group name for `$params`
);

You can pass null as $params group name. In this case $params will empty array.

Using sub-configs

In order to access a sub-config, use the following in your config:

'routes' => $config->get('routes');

Options

A number of options is available both for Composer plugin and a config loader. Composer options are specified in composer.json:

"extra": {
    "config-plugin-options": {
      "source-directory": "config"
    },
    "config-plugin": {
        // ...
    }
}

source-directory

The source-directory option specifies where to read the configs from for a package the option is specified for. It is available for all packages, including the root package, which is typically an application. The value is a path relative to where the composer.json file is located. The default value is an empty string.

If you change the source directory for the root package, don't forget to adjust configs path when creating an instance of Config. Usually that is index.php:

use Yiisoft\Config\Config;
use Yiisoft\Config\ConfigPaths;

$config = new Config(
    new ConfigPaths(dirname(__DIR__), 'path/to/config/directory'),
);

$web = $config->get('web');

vendor-override-layer

The vendor-override-layer option adds a sublayer to the vendor, which allocates packages that will override the vendor's default configurations. This sublayer is located between the vendor and application layers.

This can be useful if you need to redefine default configurations even before the application layer. To do this, you need to create your own package with configurations meant to override the default ones:

"name": "vendor-name/package-name",
"extra": {
    "config-plugin": {
        // ...
    }
}

And in the root file composer.json of your application, specify this package in the vendor-override-layer option:

"require": {
    "vendor-name/package-name": "version",
    "yiisoft/config": "version"
},
"extra": {
    "config-plugin-options": {
        "vendor-override-layer": "vendor-name/package-name"
    },
    "config-plugin": {
        // ...
    }
}

In the same way, several packages can be added to this sublayer:

"extra": {
    "config-plugin-options": {
        "vendor-override-layer": [
            "vendor-name/package-1",
            "vendor-name/package-2"
        ]
    }
}

You can use wildcard pattern if there are too many packages:

"extra": {
    "config-plugin-options": {
        "vendor-override-layer": [
            "vendor-1/*",
            "vendor-2/config-*"
        ]
    }
}

For more information about the wildcard syntax, see the yiisoft/strings.

Please note that in this sublayer keys with the same names are not allowed similar to other layers.

merge-plan-file

This option allows you to override path to merge plan file. It is .merge-plan.php by default. To change it, set the value:

"extra": {
    "config-plugin-options": {
        "merge-plan-file": "custom/path/my-merge-plan.php"
    }
}

This can be useful when developing. Don't forget to set same path in Config constructor when changing this option.

build-merge-plan

The build-merge-plan option allows you to disable creation/updating of the config/.merge-plan.php. Enabled by default, to disable it, set the value to false:

"extra": {
    "config-plugin-options": {
        "build-merge-plan": false
    }
}

This can be useful when developing. If the config package is a dependency of your package, and you do not need to create a merge plan file when developing your package. For example, this is implemented in yiisoft/yii-runner.

package-types

The package-types option define package types for process by composer plugin. By default, it is "library" and "composer-plugin". You can override default value by own types:

"extra": {
    "config-plugin-options": {
        "package-types": ["library", "my-extension"]
    }
}

Environments

The plugin supports creating additional environments added to the base configuration. This allows you to create multiple configurations for the application such as production and development.

Note that environments are supported on application level only and are not read from configurations of packages.

The environments are specified in the composer.json file of your application:

"extra": {
    "config-plugin-options": {
        "source-directory": "config"
    },
    "config-plugin": {
        "params": "params.php",
        "web": "web.php"
    },
    "config-plugin-environments": {
        "dev": {
            "params": "dev/params.php",
            "app": [
                "$web",
                "dev/app.php"
            ]
        },
        "prod": {
            "app": "prod/app.php"
        }
    }
}

Configuration defines the merge process. One of the environments from config-plugin-environments is merged with the main configuration defined by config-plugin. In given example, in the dev environment we use $web configuration from the main environment.

This configuration has the following structure:

config/             Configuration root directory.
    dev/            Development environment files.
        app.php     Development environment app group configuration.
        params.php  Development environment parameters.
    prod/           Production environment files.
        app.php     Production environment app group configuration.
    params.php      Main configuration parameters.
    web.php         Мain configuration web group configuration.

To choose an environment to be used you must specify its name when creating an instance of Config:

use Yiisoft\Config\Config;
use Yiisoft\Config\ConfigPaths;

$config = new Config(
    new ConfigPaths(dirname(__DIR__)),
    'dev',
);

$app = $config->get('app');

If defined in an environment, params will be merged with params from the main configuration, and could be used as $params in all configurations.

Configuration in a PHP file

You can define configuration in a PHP file. To do it, specify a PHP file path in the extra section of the composer.json:

"extra": {
    "config-plugin-file": "path/to/configuration/file.php"
}

Configurations are specified in the same way, only in PHP format:

return [
    'config-plugin-options' => [
        'source-directory' => 'config',  
    ],
    'config-plugin' => [
        'params' => [
            'params.php',
            '?params-local.php',
        ],
        'web' => 'web.php', 
    ],
    'config-plugin-environments' => [
        'dev' => [
            'params' => 'dev/params.php',
            'app' => [
                '$web',
                'dev/app.php',
            ],
        ],
        'prod' => [
            'app' => 'prod/app.php',
        ],
    ],
];

If you specify the file path, the remaining sections (config-plugin-*) in composer.json will be ignored and configurations will be read from the PHP file specified. The path is relative to where the composer.json file is located.

Configuration modifiers

Recursive merge of arrays

By default, recursive merging of arrays in configuration files is not performed. If you want to recursively merge arrays in a certain group of configs, such as params, you must pass RecursiveMerge modifier with specified group names to the Config constructor:

use Yiisoft\Config\Config;
use Yiisoft\Config\ConfigPaths;
use Yiisoft\Config\Modifier\RecursiveMerge;

$config = new Config(
    new ConfigPaths(dirname(__DIR__)),
    'dev',
    [
        RecursiveMerge::groups('params', 'events', 'events-web', 'events-console'),
    ],
);

$params = $config->get('params'); // merged recursively

If you want to recursively merge arrays to a certain depth, use the RecursiveMerge::groupsWithDepth() method:

RecursiveMerge::groups(['widgets-themes', 'my-custom-group'], 1)

Note: References to another configs use recursive modifier of root group.

Reverse merge of arrays

Result of reverse merge is being ordered descending by data source. It is useful for merging module config with base config where more specific config (i.e. module's) has more priority. One of such cases is merging events.

To enable reverse merge pass ReverseMerge modifier with specified group names to the Config constructor:

use Yiisoft\Config\Config;
use Yiisoft\Config\ConfigPaths;
use Yiisoft\Config\Modifier\ReverseMerge;

$config = new Config(
    new ConfigPaths(dirname(__DIR__)),
    'dev',
    [
        ReverseMerge::groups('events', 'events-web', 'events-console'),
    ],
);

$events = $config->get('events-console'); // merged reversed

Note: References to another configs use reverse modifier of root group.

Remove elements from vendor package configuration

Sometimes it is necessary to remove some elements of vendor packages configuration. To do this, pass RemoveFromVendor modifier to the Config constructor.

Remove specified key paths:

use Yiisoft\Config\Config;
use Yiisoft\Config\ConfigPaths;
use Yiisoft\Config\Modifier\RemoveFromVendor;

$config = new Config(
    new ConfigPaths(dirname(__DIR__)),
    'dev',
    [
        // Remove elements `key-for-remove` and `nested→key→for-remove` from all groups in all vendor packages
        RemoveFromVendor::keys(
            ['key-for-remove'],
            ['nested', 'key', 'for-remove'],
        ),
        
        // Remove elements `a` and `b` from all groups in package `yiisoft/auth`
        RemoveFromVendor::keys(['a'], ['b'])
            ->package('yiisoft/auth'),
        
        // Remove elements `c` and `d` from groups `params` and `web` in package `yiisoft/view`
        RemoveFromVendor::keys(['c'], ['d'])
            ->package('yiisoft/view', 'params', 'web'),
        
        // Remove elements `e` and `f` from all groups in package `yiisoft/auth`
        // and from groups `params` and `web` in package `yiisoft/view`
        RemoveFromVendor::keys(['e'], ['f'])
            ->package('yiisoft/auth')
            ->package('yiisoft/view', 'params', 'web'),
    ],
);

$params = $config->get('params');

Remove specified configuration groups:

use Yiisoft\Config\Config;
use Yiisoft\Config\ConfigPaths;
use Yiisoft\Config\Modifier\RemoveFromVendor;

$config = new Config(
    new ConfigPaths(dirname(__DIR__)),
    'dev',
    [
        RemoveFromVendor::groups([
            // Remove group `params` from all vendor packages
            '*' => 'params',
            
            // Remove groups `common` and `web` from all vendor packages
            '*' => ['common', 'web'],
            
            // Remove all groups from package `yiisoft/auth`
            'yiisoft/auth' => '*',
            
            // Remove groups `params` from package `yiisoft/http`
            'yiisoft/http' => 'params',
            
            // Remove groups `params` and `common` from package `yiisoft/view`
            'yiisoft/view' => ['params', 'common'],
        ]),
    ],
);

Combine modifiers

Config supports simultaneous use of several modifiers:

use Yiisoft\Config\Config;
use Yiisoft\Config\ConfigPaths;
use Yiisoft\Config\Modifier\RecursiveMerge;
use Yiisoft\Config\Modifier\RemoveFromVendor;
use Yiisoft\Config\Modifier\ReverseMerge;

$config = new Config(
    new ConfigPaths(dirname(__DIR__)),
    'dev',
    [
        RecursiveMerge::groups('params', 'events', 'events-web', 'events-console'),
        ReverseMerge::groups('events', 'events-web', 'events-console'),
        RemoveFromVendor::keys(
            ['key-for-remove'],
            ['nested', 'key', 'for-remove'],
        ),
    ],
);

Commands

yii-config-copy

The plugin adds extra yii-config-copy command to Composer. It copies the package config files from the vendor to the config directory of the root package:

composer yii-config-copy <package-name> [target-path] [files]

Copies all config files of the yiisoft/view package:

# To the `config` directory
composer yii-config-copy yiisoft/view

# To the `config/my/path` directory
composer yii-config-copy yiisoft/view my/path

Copies the specified config files of the yiisoft/view package:

# To the `config` directory
composer yii-config-copy yiisoft/view / params.php web.php

# To the `config/my/path` directory and without the file extension
composer yii-config-copy yiisoft/view my/path params web

In order to avoid conflicts with file names, a prefix is added to the names of the copied files: yiisoft-view-params.php, yiisoft-view-web.php.

yii-config-rebuild

The yii-config-rebuild command updates merge plan file. This command may be used if you have added files or directories to the application configuration file structure and these were not specified in composer.json of the root package. In this case you need to add to the information about new files to composer.json of the root package by executing the command:

composer yii-config-rebuild

yii-config-info

The yii-config-rebuild command displays application or package configuration details.

composer yii-config-info
composer yii-config-info yiisoft/widget

Documentation

If you need help or have a question, the Yii Forum is a good place for that. You may also check out other Yii Community Resources.

License

The Yii Config package is free software. It is released under the terms of the BSD License. Please see LICENSE for more information.

Maintained by Yii Software.

Credits

The plugin is heavily inspired by Composer config plugin originally created by HiQDev (https://hiqdev.com/) in 2016 and then adopted by Yii.

Support the project

Open Collective

Follow updates

Official website Twitter Telegram Facebook Slack

config's People

Contributors

arhell avatar cebe avatar darkdef avatar dependabot[bot] avatar devanych avatar kaznovac avatar luizcmarin avatar mister-42 avatar samdark avatar sankaest avatar stylecibot avatar terabytesoftw avatar viktorprogger avatar vjik avatar xepozz avatar yiiliveext avatar

Stargazers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

Watchers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

config's Issues

Make config path configurable

The idea is to make path where package config is written/read configurable such as:

config/packages/{vendorName}{configGroup}{fileName}

Related to #40

Split action onInstall and onUpdate

Need splitting action install and update.

For new packages (install) - copying config files
For existing packages (update) - only work with existing config files, if adding new file - be needs warning

Add support prevent run methods via null

For example:

SwaggerJson::class => [
        'withAnnotationPaths()' => $params['yiisoft/yii-swagger']['annotation-paths'] 
                ? [...$params['yiisoft/yii-swagger']['annotation-paths']] 
                : null,
],

This will prevent call of unnecessary methods and slightly improve performance.

Remove restriction for params prefixing in packages

Problem

Currenty there is a rule to prefix package parameters with a package name https://github.com/yiisoft/docs/blob/master/000-packages.md#configs-and-defaults. That's mostly great but not always convenient. There could be parameters shared by multiple services. For example, it is convinient when:

  • language parameter is shared for translator and view.
  • db parameter is shared for yiisoft/db and yiisoft/yii-cycle connection.

Proposal

  1. Remove such limitation from docs, leave it as suggestion.
  2. Choose common parameter names.

Improve error message when there is a conflict between configs from different groups

Redefinition does not work for the interface DataResponseFactoryInterface

What steps will reproduce the problem?

  1. Create project composer create-project --prefer-dist --stability=dev yiisoft/app yii-test
  2. add DataResponseFactoryInterface::class => DataResponseFactory::class to config/common/psr17.php

What is the expected result?

Worked app

What do you get instead?

ErrorException:

Duplicate key "Yiisoft\DataResponse\DataResponseFactoryInterface" in configs:
- $common
- config/common/psr17.php

Additional info

Q A
Version 1.1.0
PHP version 8.0, 8.1
Operating system Debian, MacOS

Interactive menu for changed configs [needs translation]

The idea is to make the console interface of the package more friendly and convenient similar to Linux:
IMG_20210507_163801_389

Для случаев апдейта конфигов можно сделать вариант примерно как для обновляемых конфигов пакетов в Линукс (скриншот выше), только ещё круче, благо возможность такая есть: после, например, composer update вывести список файлов, с которыми надо что-то сделать, чтобы между ними можно было переключаться кнопками вверх/вниз и выбирать, что с каждым конкретным файлом сделать. Плюс отдельно варианты применения ко всем оставшимся в списке файлам.

Example:

The following files have changes in both local and maintainer versions:
- file1.php
- file2.php
- file3.php
---------------------------
Batch actions for all the files above:
- Copy new versions as *.dist.php near the local ones
- Install maintainer versions
- Ignore all changes

В варианте выше юзер может кнопками вверх/вниз переключаться между шестью пунктами. Если выбран один из первых трех (какой-то файл), то задается вопрос, что с ним делать: игнорить, затереть локальную версию, скопировать новую версию в dist, показать изменения между локальной версией и новой, или же ничего не делать и вернуться в список. Если выбрано какое-то действие - возвращаемся обратно в список, из которого обработанный файл убираем. Если в списке файлов не осталось, то завершаем выполнение этого блока команд.

Пример инструмента для построения подобных менюшек: https://github.com/php-school/cli-menu

Store dist separately

Problem

  • Having dist in config makes structure too complicated.

Proposal

  • Placedist directory outside of config. For example, in data/config_dist.

Implement caching

Config caching should be done by exporting assembled configs to PHP files. By itself, it is a tricky task that should be considered overall. Variants:

  1. Use yiisoft/var-dumper. Dumper should be fixed to support more cases. See also yiisoft/var-dumper#43
  2. Use https://github.com/symfony/var-exporter. Need to check if it works well with configs.
  3. Another library? Are there more?
  4. Do not use caching. If caching won't show any significant performance difference, we are going to remove it.

Prepare config on first install

What steps will reproduce the problem?

  1. Prepare some configuration in a project, require some packages
  2. composer require yiisoft/config

What is the expected result?

All the previously installed package configurations are copied to the packages folder

What do you get instead?

Only merge_plan.php file is created

Improve config diff logic

In my opinion we can fully remove dist directories/files from a project instead of #42. Not just remove, but replace with another functionality.

I see 6 use-cases to activate this package as a composer plugin:

  1. composer install when composer.lock exists
  2. composer install when composer.lock does not exist
  3. composer update
  4. composer require an existing package, but in another version
  5. composer require a new package
  6. composer require yiisoft/config
  • In case 1 this package should do nothing. All the packages had been installed earlier, and their configs - too.
  • Cases 2-4 looks similar for me: it's about package(s) updating. In this case the config package should provide the choice for a user (read below about it).
  • In the cases 5 and 6 the config package should copy all the configurations from the vendor directory (for a single package in case 5 and for all the packages in case 6), and ask a user what to do when a file with the required name exists in a project.

Let's talk about the logic when the plugin sees some differences

When there are some differences, the plugin should ask a user what to do. All available variants are:

  • Show diff between a local (in -project) version and a new version (in the vendor directory after package updating/requiring).
  • Show diff between an old version (copied before package update) and a new version
  • Replace local version with a new version (default when there was no local version)
  • Copy a new version to a project with different name. This file shouldn't be included to the merge plan
  • Ignore, do nothing (default when there is a local config version)
  • 3 previous variants, but "For all" (ignore/copy/replace for this and all the future questions)

When a composer command is executed in a non-interactive mode, then the config package should automatically choose the default variant.

Swap files in diff

Exampl:

= Yii Config =

The local version of the "config/packages/yiisoft/view/common.php" config file differs with the new version of the file from the vendor.
Select one of the following actions:
  [1] Ignore, do nothing.
  [2] Replace the local version with the new version.
  [3] Copy the new version of the file with the ".dist" postfix.
  [4] Show diff in console.
 > 4
--- E:\xxx\vendor/yiisoft/view/config/common.php
+++ E:\xxx/config/packages/yiisoft/view/common.php
= Lines: -5,6 +5,6 =
-use Yiisoft\Definitions\DynamicReference;
+use Yiisoft\Factory\Definition\DynamicReference;
Select one of the following actions:
  [1] Ignore, do nothing.
  [2] Replace the local version with the new version.
  [3] Copy the new version of the file with the ".dist" postfix.

Now:

--- E:\xxx\vendor/yiisoft/view/config/common.php
+++ E:\xxx/config/packages/yiisoft/view/common.php
= Lines: -5,6 +5,6 =
-use Yiisoft\Definitions\DynamicReference;
+use Yiisoft\Factory\Definition\DynamicReference;

Better swap files being compared:

--- E:\xxx/config/packages/yiisoft/view/common.php
+++ E:\xxx\vendor/yiisoft/view/config/common.php
= Lines: -5,6 +5,6 =
-use Yiisoft\Factory\Definition\DynamicReference;
+use Yiisoft\Definitions\DynamicReference;

Do not copy default configs

Problem

Too many config files in the application.

Solution

Do not copy default configs right away:

  • If there's no file in the application, take one from vendor.
  • If there's a file in the application, read it and do not touch vendor.

Extra usability could be achieved with "copy default configs for package X" command.

Add configuration

Per package (composer.json)

  • Config source directory (prefixed to each config defintion). Default is configs.
  • Package configs directory. /config/packages now.

Config

  • Package configs directory. /config/packages now.
  • Cache path.

Explicitly name container configs

Problem

It's not obvious which config configures container and which is params.

Proposal

Rename configs:

  • common.php -> container-common.php
  • web.php -> container-web.php
  • console.php -> container-console.php

Different config grouping

Problem

  • Too complex configs structure. Hard to understand for beginner.
  • Hard to check all configs that are becoming a certain group, i.e. what will be used when loading web in index.php.

Idea

The idea is that files are placed differently when copied from packages to application.

For example, the following is in the maker and doer packages:

config
  common.php - common group in composer.json
  web.php - web group in composer.json
  params.php - params group in composer.json

will be copied to app as:

config
  common
    `maker-common.php`
    `doer-common.php`
  web
    `maker-web.php`
    `doer-web.php`
  params
    `maker-params.php`
    `doer-params.php`

Result

  • Easy to get an idea what configs form a group.
  • Likely lesss scary for beginners.
  • It is now harder to get an idea what configs a certain package provided (do we need it?)
  • Configs in the pacakge aren't grouped the same way.
  • In this approach app configs could be also moved to groups i.e. config/web/app.php. This way there will be a single "standard" way to place configs for both app and packages.

require-dev not taken into consideration

What steps will reproduce the problem?

composer.json:

{
    "minimum-stability": "dev",
    "prefer-stable": true,
    "require": {
        "yiisoft/config": "1.0.x-dev",
        "yiisoft/aliases": "^1.1"
    },
    "require-dev": {
        "yiisoft/log": "^1.0"
    }
}

What is the expected result?

Copied config for aliases & log

What do you get instead?

Copied config for aliases

Additional info

Q A
Version dev
PHP version 8.0.3
Operating system Debian 10

Check hook post-cmd-install

With hook post-cmd-install - config files shouldn't be copied!
This hook be triggering - if lock file exists and in cli user using command

composer install

It may means (way to recognize production evironment) - we execute install on production

Add merge plan builder by PHP array configuration and flag for disable composer plugin

Package yiisoft/config consists of two parts.

Part 1

Getting config $config->get('console') and syntax:

"common": "common/*.php",
"params": [
  "params.php",
  "?params-local.php"
],
"web": [
  "$common",
  "web/*.php"
],
"console": [
  "$common",
  "console/*.php"
],
"events": "events.php",
"events-web": [
  "$events",
  "events-web.php"
],
...

Part 2

Collect configs from vendor and generation of merge plan.

Suggestion

  1. Add flag to composer.json for disable work composer plugin.

  2. Create merge plan builder by PHP array:

<?php
return [
  'options' => [
    'source-directory' => 'config',
  ],
  'configs' => [
    'params' => [
      'params.php',
      '?params-local.php',
    ],
    'common' => 'common/*.php',
    'console' => [
      '$common',
      'console/*.php',
    ],
    ...
  ];
];
...

This approach will allow you to use two ways to configure the application:

  1. Configure yiisoft/config in composer.json and collect configs from vendor.

  2. Configure yiisoft/config by PHP array and manually create all configs in application.

Store vendor configs hash, use it to determine if file was changed

In order to improve experience we can store config hash in a file similar to composer.lock and then use it to determine if there were changes in vendor config. The goal is not to display any warnings if config is a custom one and vendor did not change since last time.

Duplicate keys

I have various duplicate keys reports. Since I am not sure in which packages the correction needs to be made, I will list them below.

Should application override keys regardless of the group?

Currently application overrides keys only for the matching group:

vendor
   package1
      [Group] web
          [Key] MyInterface
app
  [Group] common
      [Key] MyInterface

Would currently cause conflict as seen in #109.

Should application override keys regardless of the group?

Inconvenient use of the environment

Now when using an environment, prod, dev, test or stage, throws an exception if the environment is not specified in composer.json "config-plugin-environments". But if you just specify the environment with an empty value

"config-plugin-environments": {
        "test": {},
        "dev": {},
        "prod": {}
}

it does not get into the merge-plan, you need to include the config file.

I expect that if no environment exists, it will take the default "/", or add the ability to specify a group of environments that take the same configs, for example prod and stage.

Change message on first copy config file

On first copy config file now show:

Config file has been changed. Please review ".../config/packages/yiisoft/yii-web/config/web.php" and change it according with .dist file.

I think it would be better if in this case the message says "new config file added".

Implement config updates

In case package was updated and old config is already in the application, we need to:

  1. Add new keys from package config to application config.
  2. Comment-out keys that aren't present.
  3. Probably report on the differences?

$ - reference to another config broken when using source-directory

What steps will reproduce the problem?

  1. Add source-directory options
  2. Use variable

What is the expected result?

A working configuration

What do you get instead?

merge_plan

    'test' => [
        '/' => [
            'config/$common',
            'config/$web',
            'config/test.php',
        ],
    ],

Additional info

I'm guessing source-directory is added in front before isVariable is called

Q A
Version 9e8c7af
PHP version 8.0.3
Operating system Debian 10

Searching for incorrect packages folder location

What steps will reproduce the problem?

Run yii console command, but not from yii folder (commonly done in cron jobs for example)
~$ /opt/plesk/php/8.0/bin/php -f 'yii3/vendor/bin/yii' -- 'rss/retrieve'

What is the expected result?

Whatever the given command does

What do you get instead?

PHP Warning:  require(/home/user/config/packages/merge_plan.php): Failed to open stream: No such file or directory in /home/user/yii3/vendor/yiisoft/config/src/Config.php on line 53

It's not looking in a relative path from yii, but relative from current folder

Additional info

Q A
Version 1.0-dev
PHP version 8.0.3
Operating system Debian 10

Wildcards doesn't work when app is packed into PHAR

If you set file for config group using wildcards, no file will be loaded when the config folder is packed as part of PHAR archive.
For example having common group defined as this will result in no config file loaded for it.

"common": [
    "config/common/*.php",
]

This is because glob() function used to resolve wildcards can't deal with PHAR archives.

This can be resolved by explicitly mentioning each config file, but it would be nice if there is some warning about that in documentation.

Autocomplete for class configuration

Hi,
Yii2 has very useful plugin for best/most popular PHP IDE - PhpStorm, https://plugins.jetbrains.com/plugin/9388-yii2-support

Any chance to provide one for Yii3 to have autocomplete in config files - to set class properties, __construnct() etc. ?

Main goal is to type faster, do less typos and got mistakes highlighted.

Examples:

<?php

return [
    'components' => [
        'db' => [
            'class' => \my\Db::class,
            'name' => 'foo', // <-- autocomplete
            'password' => 'boo', // <-- autocomplete
        ],
    ],
];
return [
    LoggerInterface::class => [
        'class' => Logger::class,
        '__construct()' => [ // <-- autocomplete
            'targets' => ReferencesArray::from([ // <-- autocomplete
                FileTarget::class,
            ]),
        ],
    ],
];

Ignore line ending when compare dist-files

In user git repository can use different line endings (\n, \r, \r\n). Configs can different only line endings - in this case not need copy config file from package to dist.

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. 📊📈🎉

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google ❤️ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.