yii1tech / config
Provides support for Yii1 application runtime configuration
Fund package maintenance!
klimov-paul
Patreon
Requires
- php: >=7.1
- yiisoft/yii: ~1.1.0
Requires (Dev)
- phpunit/phpunit: ^6.0 || ^7.0 || ^8.0 || ^9.3 || ^10.0.7
This package is auto-updated.
Last update: 2024-11-13 11:00:39 UTC
README
Application Runtime Configuration Extension for Yii 1
This extension introduces persistent configuration repository for Yii 1. Its usage in particular provides support for application runtime configuration, loading config from database.
For license information check the LICENSE-file.
Installation
The preferred way to install this extension is through composer.
Either run
php composer.phar require --prefer-dist yii1tech/config
or add
"yii1tech/config": "*"
to the "require" section of your composer.json.
Usage
This extension allows reconfiguring already created Yii application instance using config extracted from external storage
like relational database. It allows to reconfigure any application property, component or module.
Configuration is performed by \yii1tech\config\Manager
component, which should be added to the application configuration.
For example:
[ 'behaviors' => [ 'configFromManagerBehavior' => [ 'class' => yii1tech\config\ConfiguresAppFromConfigManager::class, ], // ... ], 'components' => [ 'configManager' => [ 'class' => yii1tech\config\Manager::class, 'items' => [ 'appName' => [ 'path' => 'name', 'label' => 'Application Name', 'rules' => [ ['required'], ], ], 'dateFormat' => [ 'path' => 'components.format.dateFormat', 'label' => 'HTML representing not set value', 'rules' => [ ['required'], ], ], ], ], ... ], ];
In order to apply configuration defined via \yii1tech\config\Manager
- yii1tech\config\ConfiguresAppFromConfigManager
application
behavior is used. It automatically updates the application configuration before request processing begins.
You can apply config manually to the application or any \CModule
descendant, using following code:
$configManager = Yii::app()->get('configManager'); $configManager->configure(Yii::app());
Heads up! Behavior yii1tech\config\ConfiguresAppFromConfigManager
automatically suppresses any error or exception, which appears during values
restoration. This is done to avoid application blocking in case storage is not yet ready for usage, for example: database table does not yet exist.
Storage failure error will appear only at the application log. You should manually test value restoration is working at your application
to avoid unexpected behavior.
Configuration items specification
Application parts, which should be reconfigured are determined by \yii1tech\config\Manager::$items
, which is a list
of \yii1tech\config\Item
. Each configuration item determines the configuration path - a list of keys in application
configuration array, which leads to the target value. For example: path 'components.format.dateFormat' (or
['components', 'format', 'dateFormat']
) points to the property 'dateFormat' of \CFormatter
component,
path 'name' points to \CApplication::$name
and so on.
Note: if no path is specified it will be considered as a key inside
\CModule::$params
array, which matches configuration item id (name of key in\yii1tech\config\Manager::$items
array).
Configuration item may also have several properties, which supports creation of web interface for configuration setup. These are:
- 'path' - array|string, application component config path.
- 'label' - string, input label.
- 'description' - string, configuration parameter description or input hint.
- 'rules' - array, value validation rules.
- 'cast' - string, native type for the value to be cast to.
- 'options' - array, additional descriptive options for this item.
Tip: since runtime configuration may consist of many items and their declaration may cost a lot of code, it can be moved into a separated file and specified by this file name.
Here are some examples of item specifications:
<?php return [ 'appName' => [ 'path' => 'name', 'label' => 'Application Name', 'rules' => [ ['required'], ['length', 'min' => 1], ], ], 'nullDisplay' => [ 'path' => 'components.format.dateFormat', 'label' => 'Date representation format', 'rules' => [ ['required'], ['length', 'min' => 1], ], ], 'adminEmail' => [ 'label' => 'Admin email address', 'rules' => [ ['required'], ['email'], ], ], 'adminTheme' => [ 'label' => 'Admin interface theme', 'path' => ['modules', 'admin', 'theme'], 'rules' => [ ['required'], ['in', 'range' => ['classic', 'bootstrap']], ], 'options' => [ 'type' => 'dropDown', 'items' => [ 'classic' => 'Classic', 'bootstrap' => 'Twitter Bootstrap', ], ], ], ];
Tip: there is no need to prepare data for particualr item inside the storage. If it is missing the value will be picked from current related application configuration. Thus, you can add and remove config items freely without extra action, like DB migration, involved.
Configuration storage
Declared configuration items may be saved into persistent storage and then retrieved from it.
The actual item storage is determined via \yii1tech\config\Manager::$storage
.
Following storages are available:
- \yii1tech\config\StoragePhp - stores configuration inside PHP files
- \yii1tech\config\StorageDb - stores configuration inside relational database
- \yii1tech\config\StorageActiveRecord - finds configuration using ActiveRecord
- \yii1tech\config\StorageArray - uses internal array for the config storage, could be useful in unit tests
Please refer to the particular storage class for more details.
Creating configuration web interface
The most common use case for this extension is creating a web interface, which allows control of application
configuration in runtime.
\yii1tech\config\Manager
serves not only for applying of the configuration - it also helps to create an
interface for configuration editing.
The web controller for configuration management may look like following:
<?php namespace app\controllers; use CController; use CHtml; use Yii; class ConfigController extends CController { /** * Performs batch updated of application configuration records. */ public function actionIndex() { /* @var $configManager \yii1tech\config\Manager */ $configManager = Yii::app()->get('configManager'); $configManager->restore(); $models = $configManager->getItems(); if (!empty($_POST)) { $valid = true; foreach ($models as $model) { $modelName = CHtml::modelName($model); if (isset($_POST[$modelName][$model->id])) { $model->setAttributes($_POST[$modelName][$model->id]); } $valid = $valid && $model->validate(); } if ($valid) { $configManager->save(); Yii::app()->getComponent('user')->setFlash('success', 'Configuration saved.'); $controller->refresh(); return; } } return $this->render('index', [ 'models' => $models, ]); } /** * Restores default values for the application configuration. */ public function actionDefault() { /* @var $configManager \yii1tech\config\Manager */ $configManager = Yii::$app->get('configManager'); $configManager->reset(); Yii::app()->getComponent('user')->setFlash('success', 'Default configuration restored.'); $this->redirect(['index']); return; } }
The main view file can be following:
<?php /** @var $this CController */ /** @var $form CActiveForm */ ?> <?php $form = $this->beginWidget(CActiveForm::class); ?> <?php foreach ($models as $model):?> <?php echo $form->labelEx($model, 'value'); ?> <div class="row"> <?php echo $form->textField($model, '[' . $model->id . ']value'); ?> </div> <?php echo $form->error($model, 'value'); ?> <?php endforeach;?> <div class="form-group"> <?= CHtml::link('Restore defaults', ['default'], ['class' => 'btn btn-danger', 'data-confirm' => 'Are you sure you want to restore default values?']); ?> <?= CHtml::submitButton('Save', ['class' => 'btn btn-primary']) ?> </div> <?php $this->endWidget(); ?>