Материал переведен отсюда
На прошлой неделе, перед DrupalCamp Colorado, Greg "heyrocker" Dunlap, David Strauss, Larry "Crell" Garfield, and Karoly "chx" Negyesi, встретились, чтобы определить основные моменты кода Drupal 8, сделанные на скорую руку Группой Управления Конфигурацией(Configuration Management Initiative).
Какие проблемы мы пытаемся решить?
Мы пока не решаем проблему контекстной конфигурации; только нужного для него API для чтения/записи этой конфигурации и перемещения его для нужных сайтов.
Код прототипа доступен по следующей ссылке http://drupal.org/sandbox/heyrocker/1145636 . Основные изменения находятся в файлах includes/config.inc и modules/config/config.test
Ниже приведены результаты разработанного как прототип кода.
Общее строение

Уровень 1: Хранилище файлов с цифровой подписью.
На самом низком уровне, все данные конфигурации хранятся на диске, используя подписанные JSON файлы, находящиеся в sites/$sitename/config. Так же смотрите "Вопросы безопасности", изложенные ниже.
Пример того, как может выглядеть такой файл prefix.example.json.php
<?php die(); 723fd490de3fb7203c3a408abee8c0bf3c2d302392[snip]
{
"string_value": "string",
"integer_value": 1,
"array_or_object_value": [
"value1",
"value2"],
"boolean_value": false,
}Первая строка предотвращает непосредственный просмотр файлов, а также обеспечивает цифровую подпись для проверки целостности файлов.
Предполагается, что в файле подобном module.$modulename.json.php будет хранится информация о всей конфигурации модуля. Ядро может включать в себя такие файлы как core.site_information.json.php, а модуль типа Flag может хранить свои глобальные настройки как в файле module.flag.json.php так и в flag.$flagname.json.php
Преимущество хранения информации в таком формате заключается в том, что не надо будет загружать всю таблицу переменных в каждом запросе, а загружать лишь те, которые нам нужны для обработки конкретного запроса.
Уровень 2: Активная обертка конфигуратора
Этот слой перемещает конфигурационные данные из файловой системы во что-то откуда можно их легко прочитать и получить доступ. Для подавляющего большинства "друпаловских" сайтов это хранилище баз данных, но для высоко производительных сайтов может понадобится что-то наподобие MongoDB или Redis.
В конфигурации по умолчанию, эти данные будут передаваться в главную таблицу называемой "config"
CREATE TABLE config (
name varchar(255) NOT NULL DEFAULT '' COMMENT 'The identifier for the configuration entry, such as module.example (the name of the file, minus .json.php).',
data longtext NOT NULL COMMENT 'The raw JSON data for this configuration entry.',
PRIMARY KEY (name),
);На первый взгляд "переменные" выглядят как таблица в Drupal 7, но есть одно серьёзное отличие: она хранит конфигурационные данные (скажем, всю информацию о сайте: название, миссия...), а переменная хранит в себе только одно значение (например, название сайта). Кроме этого мы не загружаем всю таблицу переменных из памяти.
Всю конфигурацию сайта можно прочесть через эту обертку. Данные обновляются по двум условиям:
Уровень 3: API конфигурации
На этом уровне находятся функции, через которые, по сути, разработчик и будет работать: конкретно, замена функций variable_get()/varriable_set().
<?php
// Load a set of configuration out of the active store.
// 'prefix.name' refers to the filename of the .json.php file, without the extension.
$config = config('prefix.name');
// Access a single value out of the store.
echo $config->value;
// Change a value and save it back to both the active store and the filesystem.
$config->value = 'new value';
$config->save();
?>Я разработчик модулей. Как предлагаемые изменения повлияют на меня?
variable_get()/varriable_set()
В версиях Drupal 7 и ниже, все переменные являются глобальными, поэтому доступ и сохранение переменных делается так:
<?php
// Load the site name out of configuration.
$site_name = variable_get('site_name', 'Drupal');
// Change the site name to something else.
variable_set('site_name', 'This is the dev site.');
?>В Drupal 8 конфигурация будет загружаться только при необходимости. Приведенный выше код изменится и будет выглядеть так:
<?php
// Load the site name out of configuration.
$site_name = config('core.site_information')->name;
// Change the site name to something else.
$config = config('core.site_information');
$config->name = 'My Awesome Site';
$config->save();
?>Для загрузки таких как объектов как entities или views, вы можете загрузить все "вложенные" конфигурационные файлы (в том числе, для списка вьюс, списка всех типов материалов...) следующим вызовом: config_get_names_with_prefix('entity.node.'); Это вернет что-то вроде array('entity.node.page', 'entity.node.article'); Таким образом, чтобы получить все настройки для типа материала page запустите config('entity.node.page');Это означает, что config('entity.node')не будет ничего возвращать.
Объявление собственных настроек
Раньше конфигурация объявлялась разными путями, system_settings_form() автоматически сохраняла все элементы как переменные в таблице переменных. Модули такие как Flag и Views использовали hook_X_default() как шаблон.
В новой системе объявление собственной "переменной" происходит в файле module.$modulename.json.php, который поставляется вместе с модулем. Вы определяете эти переменные по умолчанию только в одном месте, а не каждый раз когда вам их надо получить.
Например, файл может выглядеть так:
module.book.json.php
<?php die();
{
"book_child_type": "book",
"book_block_mode": "all pages",
"book_allowed_types": [
"book"
]
}Во время установки модуля файл конфигурации скопируется в sites/$sitename/config и все настройки будут храниться здесь.
Определение дефолтных вьюшек, переменных и т.п. определяется таким же образом, именно через файлы с расширением .json.php.
Но мои конфигурационные данные намного сложнее, чем эти!
Так как мы используем JSON как формат хранения, то конфигурационные объекты могут быть произвольной сложности. Однако есть здесь одно затруднение. JSON не делает различий между объектом и ключом, поэтому мы поддерживаем только массивы "ключ/значение" как в PHP. После некоторого обсуждения мы решили, что отображение всех таких данных в ассоциативном массиве обеспечивает надежную структуру для дискретного набора свойств, а данные вроде $object->1 являются недействительными.
<?php
$config = config('module.mymodule');
$config->alternate_name; // A simple property
$config->instances[0]['name']; // An array
// You can't do this...
$config->foo->bar->baz = 1;
// But you can do this instead...
$config->foo['bar']['baz'] = 1;
?>Если ваши конфигурационные данные особенно сложны, то, скорее всего вы предусмотрите использование своего конфигурационного класса.
Я супер-пупер разработчик и мне надо что-то мощнее, чем это. Как я могу изменить это?
Объект $config будет реализацией базового класса, который реализует логику ->save(). Для продвинутого использования его можно будет переопределять
<?php
class MyAdvancedConfig extends DrupalConfig {
function someHelperMethod() {
$this->pants = 'fancy';
echo "Ma'am, you have my compliments on your fancy pants.";
}
}
$config = config('core.site', 'MyAdvancedConfig');
$config->someHelperMethod();
$config->save();
?>Перемещение конфигурации с разработческой площадки на боевой сайт
Общий процесс работы выглядит следующим образом:
sites/$sitename/config при помощи команды $vcs diff (или в выбранном вами инструменте), убедитесь что они верны.$vcs add/commit/push, $vcs update/pull). Ничего не будет изменено пока сайт не будет готов к запуску, т.к. все данные будут считываться из базы данных.admin/configuration/system/config и запустите команду drush config-update (Примечание: эта команда запускается на данный момент). Будут определены различия между тем, что было и что стало. Если все правильно подтвердите перезапись. Командная строка будет спрашивать по необходимости подтверждение на применение изменений.Обработка локальных изменений
Обычно удобно для API keys или $db_url иметь настройки специфичные для каждого сайта, которые не находятся под версионным контролем. В Drupal 7 и ниже это решается при помощи settings.php (или settings.local.php)
<?php
$conf['site_name'] = 'This is the dev site';
?>В новой системе будет специальный файл, в котором будут храниться все локальные изменения (этот файл не будет проверяться системой контроля версии): /sites/default/config/local.json.php. В этом файле будут храниться все переопределенные параметры в виде ключ/значение.
<?php die(); 723fd490de3fb7203c3a408abee8c0bf3c2d302392[snip]
{
"core.site_information": {"site_name": "This is the dev site"}
}Правила безопасности
Много переговоров были проведены с командой безопасности Drupal о безопасности использования веб интерфейса при записи файлов на диск. Так как эти файлы хранят в себе важные данные такие, как пароли баз данных и многое другое, то важно чтобы этими файлами никто посторонний не смог воспользоваться или осуществить какие-то манипуляции. В ходе переговоров было установлено следующее:
<?php die(); c3a408abee8c0bf3c2d302392<?php die(); 723fd490de3fb7203c3a408abee8c0bf3c2d302392[snip]
// All JSON data follows here.
Последние комментарии