Способ организации конфигов

Обсуждение документации второй версии фреймворка. Переводы Cookbook и авторские рецепты.
Ответить
zelenin
Сообщения: 10596
Зарегистрирован: 2013.04.20, 11:30

Способ организации конфигов

Сообщение zelenin »

Пример удобной организации большого количества конфигов на примере advanced app.
Допустим, у нас есть приложение на базе advanced app с директориями common и backend. Каждая директория включает конфиги - общие (common) и специфические (backend) для приложения. Также конфиги приложения делятся на глобальные (main.php в терминологии yii2, main.global.php в моей терминологии) и локальные (main-local.php/main.local.php). Первые конфиги содержат настройки независящие от окружения, вторые же - перезаписывают глобальные настройки настройками локальными (например включая дебаг на машине разработчика).
Стандартная практика: мерджить глобальные конфиги с конфигами локальными. Неудобство: приходится в ручную проверять наличие конфигов вслед за ошибками require, при создании нового конфига вручную его мерджить в другой конфиг и прочее, с чем вы уже сталкивались. Плюс в большом приложении количество конфигов быстро растет (либо же растет кол-во строк в них) - за каскадом конфигов становится трудно следить.

По мотивам знакомства с Zend Expressive написал небольшой менджер, работающий с любой библиотекой имеющий конфигурирование массивами (точнее принимающей на вход конфиг в виде массива, т.к. написав свой провайдер можем иметь конфиги в каком угодно формате, например yml/xml/ini).

Код:

Код: Выделить всё

use yii\web\Application;
use Zelenin\Zend\Expressive\Config\Manager\Config;
use Zelenin\Zend\Expressive\Config\Provider\CacheProvider;
use Zelenin\Zend\Expressive\Config\Provider\PhpProvider;

defined('YII_DEBUG') or define('YII_DEBUG', true);
defined('YII_ENV') or define('YII_ENV', 'dev');
require(__DIR__ . '/../../vendor/autoload.php');
require(__DIR__ . '/../../vendor/yiisoft/yii2/Yii.php');

$manager = new Config(
    [
        new PhpProvider(__DIR__ . '/../../common/config/{{,*.}global,{,*.}local}.php'),
        new PhpProvider(__DIR__ . '/../config/{{,*.}global,{,*.}local}.php'),
    ],
    YII_DEBUG ? null : new CacheProvider(__DIR__ . '/../runtime/app-config.php')
);
(new Application($manager->getConfig()))->run();
- создаем менеджер, передаем первым аргументом массив провайдеров в данном случае два провайдера, загружающих по порядку конфиги из common и backend. Вторым аргументом передаем кэширующий провайдер, склеивающий все конфиги в один большой массив, что рекомендуется для продакшн-среды.
PhpProvider в качестве аргумента принимает паттерн для функции glob. Что делает паттерн из примера: загружает по порядку global.php, *.global.php, local.php, *.local.php и все это дело мерджит.
Также можно добавить конфиг в виде массива - new ArrayProvider(['components' => ['class' => 'MyNewComponent']]),, или создать конфиг для быстрого подключения своего модуля:

Код: Выделить всё

new MyModuleConfigProvider()

Код: Выделить всё

namespace MyModule;

use Zelenin\Zend\Expressive\Config\Provider\ModuleConfigProvider;

final class MyModuleConfigProvider extends ModuleConfigProvider
{
    /**
     * @return array
     */
    public function getConfig()
    {
        return [
            'modules' => [
                'myModule' => [
                    'class' => 'MyModule\Module',
                    'foo' => 'bar'
                ]
            ]
        ];

        // or

        return require_once 'fooModuleConfig.php';

        // or 

        return (new PhpProvider(__DIR__ . '/config/*.php'))->getConfig();
    }
}
PS Нюанс: любой метод php-сериализации (json, var_export, serialize) из коробки не поддерживает анонимнные функции, поэтому кэшировать такие конфиги не получится.

UPD: ну да, забыл https://github.com/zelenin/zend-expressive-config
Последний раз редактировалось zelenin 2016.02.23, 16:34, всего редактировалось 1 раз.
nepster
Сообщения: 838
Зарегистрирован: 2013.01.02, 03:35

Re: Способ организации конфигов

Сообщение nepster »

основная соль, в том что можно с помощью класса соединять конфиги и импортировать из любого хранилища возвращая в массив ?
zelenin
Сообщения: 10596
Зарегистрирован: 2013.04.20, 11:30

Re: Способ организации конфигов

Сообщение zelenin »

nepster писал(а):основная соль, в том что можно с помощью класса соединять конфиги и импортировать из любого хранилища возвращая в массив ?
предотвращая ошибки и предоставляя удобное апи. все верно. плюс кэширование.
nepster
Сообщения: 838
Зарегистрирован: 2013.01.02, 03:35

Re: Способ организации конфигов

Сообщение nepster »

только на примере адванседа получается достаточный геморой внедрить что-то нестандартное, так как там конфигов очнь много, на каждое приложение по 4 штуки и для тестов тоже самое. И все это из коробки, нужно будет потрудиться. А еще есть некое неудобство если хочется хранить некоторые конфиги в бд, а ничего не выйдет, так как приложение еще неинициализировано и доступ к драйверу мы не получим.
zelenin
Сообщения: 10596
Зарегистрирован: 2013.04.20, 11:30

Re: Способ организации конфигов

Сообщение zelenin »

nepster писал(а):только на примере адванседа получается достаточный геморой внедрить что-то нестандартное
специально перевел свое приложение на этот менеджер - потратил пару минут. Теперь одни профиты.
nepster писал(а):так как там конфигов очнь много, на каждое приложение по 4 штуки и для тестов тоже самое.
получится удобнее, т.к. можно будет именовать конфиги префиксами, а глоб-паттерн их элементарно подхватит. Иначе у нас ужасный каскад мерджей, в котором путаемся.
nepster писал(а):А еще есть некое неудобство если хочется хранить некоторые конфиги в бд, а ничего не выйдет, так как приложение еще неинициализировано и доступ к драйверу мы не получим.
это очевидно. для любого способа приложение еще не инициализировано. Зато я уже предлагаю понятное апи - реализовать свой DbProvider. Но вообще вряд ли кому-то это может пригодиться.
chesar
Сообщения: 514
Зарегистрирован: 2013.04.10, 17:49

Re: Способ организации конфигов

Сообщение chesar »

Спасибо.
Аватара пользователя
slavcodev
Сообщения: 3134
Зарегистрирован: 2009.04.02, 21:42
Откуда: Valencia
Контактная информация:

Re: Способ организации конфигов

Сообщение slavcodev »

Оставлю здесь похожий вариант, использую его уже пару лет, еще с Yii1.

https://gist.github.com/slavcodev/9323a5ad6a39db13d8d7
Жду Yii 3!
Ответить