diff --git a/core/lib/Drupal/Core/Config/InstallStorage.php b/core/lib/Drupal/Core/Config/InstallStorage.php index 5a7044b..6b611ef 100644 --- a/core/lib/Drupal/Core/Config/InstallStorage.php +++ b/core/lib/Drupal/Core/Config/InstallStorage.php @@ -15,6 +15,13 @@ class InstallStorage extends FileStorage { /** + * Folder map indexed by configuration name. + * + * @var array + */ + protected $folders; + + /** * Overrides Drupal\Core\Config\FileStorage::__construct(). */ public function __construct() { @@ -38,17 +45,9 @@ public function __construct() { * afterwards check for a corresponding module or theme. */ public function getFilePath($name) { - // Extract the owner. - $owner = strtok($name, '.'); - // Determine the path to the owner. - $path = FALSE; - foreach (array('profile', 'module', 'theme') as $type) { - if ($path = drupal_get_path($type, $owner)) { - $file = $path . '/config/' . $name . '.' . static::getFileExtension(); - if (file_exists($file)) { - return $file; - } - } + $folders = $this->getAllFolders(); + if (isset($folders[$name])) { + return $folders[$name] . '/' . $name . '.' . $this->getFileExtension(); } // If any code in the early installer requests a configuration object that // does not exist anywhere as default config, then that must be mistake. @@ -86,12 +85,79 @@ public function rename($name, $new_name) { /** * Implements Drupal\Core\Config\StorageInterface::listAll(). - * - * @throws Drupal\Core\Config\StorageException */ public function listAll($prefix = '') { - throw new StorageException('List operation is not allowed during install.'); - } + $names = array_keys($this->getAllFolders()); + if (!$prefix) { + return $names; + } + else { + $return = array(); + foreach ($names as $index => $name) { + if (strpos($name, $prefix) === 0 ) { + $return[$index] = $names[$index]; + } + } + return $return; + } + } + + /** + * Returns a map of all config object names and their folders. + * + * @return array + * An array mapping config object names with directories. + */ + protected function getAllFolders() { + if (!isset($this->folders)) { + $this->folders = $this->getComponentNames('profile', array(drupal_get_profile())); + $this->folders += $this->getComponentNames('module', array_keys(drupal_system_listing('/^' . DRUPAL_PHP_FUNCTION_PATTERN . '\.module$/', 'modules', 'name', 0))); + $this->folders += $this->getComponentNames('theme', array_keys(drupal_system_listing('/^' . DRUPAL_PHP_FUNCTION_PATTERN . '\.info$/', 'themes'))); + } + return $this->folders; + } + + /** + * Get all configuration names and folders for a list of modules or themes. + * + * @param string $type + * Type of components: 'module' | 'theme' | 'profile' + * @param array $list + * Array of theme or module names. + * + * @return array + * Folders indexed by configuration name. + */ + protected function getComponentNames($type, $list) { + $extension = '.' . $this->getFileExtension(); + $folders = array(); + foreach ($list as $name) { + $directory = $this->getComponentFolder($type, $name); + if (file_exists($directory)) { + $files = glob($directory . '/*' . $extension); + foreach ($files as $filename) { + $name = basename($filename, $extension); + $folders[$name] = $directory; + } + } + } + return $folders; + } + + /** + * Get folder inside each component that contains the files. + * + * @param string $type + * Component type: 'module' | 'theme' | 'profile' + * @param string $name + * Component name. + * + * @return string + * The configuration folder name for this component. + */ + protected function getComponentFolder($type, $name) { + return drupal_get_path($type, $name) . '/config'; + } /** * Overrides Drupal\Core\Config\FileStorage::deleteAll(). diff --git a/core/lib/Drupal/Core/Config/Schema/SchemaDiscovery.php b/core/lib/Drupal/Core/Config/Schema/SchemaDiscovery.php index 9a08992..41b88ca 100644 --- a/core/lib/Drupal/Core/Config/Schema/SchemaDiscovery.php +++ b/core/lib/Drupal/Core/Config/Schema/SchemaDiscovery.php @@ -38,12 +38,7 @@ class SchemaDiscovery implements DiscoveryInterface { */ public function __construct($storage) { $this->storage = $storage; - // Load definitions for all enabled modules. - foreach (module_list() as $module) { - $this->loadSchema($module); - } - // @todo Load definitions for all enabled themes. - + $this->loadAllSchema(); } /** @@ -84,11 +79,12 @@ public function getDefinitions() { /** * Load schema for module / theme. */ - protected function loadSchema($component) { - if ($schema = $this->storage->read($component . '.schema')) { - foreach ($schema as $type => $definition) { - $this->definitions[$type] = $definition; - + protected function loadAllSchema() { + foreach ($this->storage->listAll() as $name) { + if ($schema = $this->storage->read($name)) { + foreach ($schema as $type => $definition) { + $this->definitions[$type] = $definition; + } } } } diff --git a/core/lib/Drupal/Core/Config/Schema/SchemaStorage.php b/core/lib/Drupal/Core/Config/Schema/SchemaStorage.php new file mode 100644 index 0000000..171f30a --- /dev/null +++ b/core/lib/Drupal/Core/Config/Schema/SchemaStorage.php @@ -0,0 +1,59 @@ +getAllFolders()); + } + + /** + * Overrides \Drupal\Core\Config\InstallStorage::getComponentFolder(). + */ + protected function getComponentFolder($type, $name) { + return drupal_get_path($type, $name) . '/config/schema'; + } + + /** + * Overrides \Drupal\Core\Config\InstallStorage::write(). + * + * @throws \Drupal\Core\Config\StorageException + */ + public function write($name, array $data) { + throw new StorageException('Write operation is not allowed for config schema storage.'); + } + + /** + * Overrides \Drupal\Core\Config\InstallStorage::delete(). + * + * @throws \Drupal\Core\Config\StorageException + */ + public function delete($name) { + throw new StorageException('Delete operation is not allowed for config schema storage.'); + } + + /** + * Overrides \Drupal\Core\Config\InstallStorage::rename(). + * + * @throws \Drupal\Core\Config\StorageException + */ + public function rename($name, $new_name) { + throw new StorageException('Rename operation is not allowed for config schema storage.'); + } + +} diff --git a/core/lib/Drupal/Core/Config/TypedConfigManager.php b/core/lib/Drupal/Core/Config/TypedConfigManager.php index 2028d20..4a8a289 100644 --- a/core/lib/Drupal/Core/Config/TypedConfigManager.php +++ b/core/lib/Drupal/Core/Config/TypedConfigManager.php @@ -18,19 +18,21 @@ class TypedConfigManager extends TypedDataManager { /** * A storage controller instance for reading configuration data. * - * @var Drupal\Core\Config\StorageInterface + * @var \Drupal\Core\Config\StorageInterface */ - protected $storage; + protected $configStorage; /** * Creates a new typed configuration manager. * - * @param Drupal\Core\Config\StorageInterface $storage + * @param \Drupal\Core\Config\StorageInterface $configStorage + * The storage controller object to use for reading schema data + * @param \Drupal\Core\Config\StorageInterface $schemaStorage * The storage controller object to use for reading schema data */ - public function __construct($storage) { - $this->storage = $storage; - $this->discovery = new SchemaDiscovery($storage); + public function __construct(StorageInterface $configStorage, StorageInterface $schemaStorage) { + $this->configStorage = $configStorage; + $this->discovery = new SchemaDiscovery($schemaStorage); $this->factory = new TypedConfigElementFactory($this->discovery); } @@ -40,17 +42,17 @@ public function __construct($storage) { * @param string $name * Configuration object name. * - * @return Drupal\Core\Config\Schema\Element + * @return \Drupal\Core\Config\Schema\Element * Typed configuration element. */ public function get($name) { - $data = $this->storage->read($name); + $data = $this->configStorage->read($name); $definition = $this->getDefinition($name); return $this->create($definition, $data); } /** - * Overrides Drupal\Core\TypedData\TypedDataManager::create() + * Overrides \Drupal\Core\TypedData\TypedDataManager::create() * * Fills in default type and does variable replacement. */ diff --git a/core/lib/Drupal/Core/CoreBundle.php b/core/lib/Drupal/Core/CoreBundle.php index 2ebe38f..33ea86f 100644 --- a/core/lib/Drupal/Core/CoreBundle.php +++ b/core/lib/Drupal/Core/CoreBundle.php @@ -67,9 +67,14 @@ public function build(ContainerBuilder $container) { ->addArgument(new Reference('database')) ->addArgument('config_snapshot'); + // Register schema configuration storage. + $container + ->register('config.storage.schema', 'Drupal\Core\Config\Schema\SchemaStorage'); + // Register the typed configuration data manager. $container->register('config.typed', 'Drupal\Core\Config\TypedConfigManager') - ->addArgument(new Reference('config.storage')); + ->addArgument(new Reference('config.storage')) + ->addArgument(new Reference('config.storage.schema')); // Register the service for the default database connection. $container->register('database', 'Drupal\Core\Database\Connection') diff --git a/core/modules/contact/config/contact.schema.yml b/core/modules/contact/config/schema/contact.schema.yml similarity index 100% rename from core/modules/contact/config/contact.schema.yml rename to core/modules/contact/config/schema/contact.schema.yml diff --git a/core/modules/image/config/image.schema.yml b/core/modules/image/config/schema/image.schema.yml similarity index 100% rename from core/modules/image/config/image.schema.yml rename to core/modules/image/config/schema/image.schema.yml diff --git a/core/modules/system/config/system.schema.yml b/core/modules/system/config/schema/system.data_types.schema.yml similarity index 61% rename from core/modules/system/config/system.schema.yml rename to core/modules/system/config/schema/system.data_types.schema.yml index 3514260..ac9bc78 100644 --- a/core/modules/system/config/system.schema.yml +++ b/core/modules/system/config/schema/system.data_types.schema.yml @@ -61,44 +61,3 @@ mail: "body": type: text label: "Body" - -# Schema for configuration files of system module: - -system.site: - type: mapping - label: 'Site information' - mapping: - "name": - label: "Site name" - type: label - "mail": - label: "Site mail" - type: email - "slogan": - label: "Site slogan" - type: text - "page": - type: mapping - mapping: - "403": - type: path - "404": - type: path - "front": - type: path - label: "Front page path" - "admin_compact_mode": - type: boolean - "weight_select_max": - type: integer - -system.maintenance: - type: mapping - label: 'Maintenance mode' - mapping: - "enabled": - type: boolean - label: "Put site into maintenance mode" - "message": - type: text - label: "Message to display when in maintenance mode" diff --git a/core/modules/system/config/schema/system.schema.yml b/core/modules/system/config/schema/system.schema.yml new file mode 100644 index 0000000..ad6755d --- /dev/null +++ b/core/modules/system/config/schema/system.schema.yml @@ -0,0 +1,39 @@ +# Schema for configuration files of system module: +system.site: + type: mapping + label: 'Site information' + mapping: + "name": + label: "Site name" + type: label + "mail": + label: "Site mail" + type: email + "slogan": + label: "Site slogan" + type: text + "page": + type: mapping + mapping: + "403": + type: path + "404": + type: path + "front": + type: path + label: "Front page path" + "admin_compact_mode": + type: boolean + "weight_select_max": + type: integer + +system.maintenance: + type: mapping + label: 'Maintenance mode' + mapping: + "enabled": + type: boolean + label: "Put site into maintenance mode" + "message": + type: text + label: "Message to display when in maintenance mode" diff --git a/core/modules/user/config/user.schema.yml b/core/modules/user/config/schema/user.schema.yml similarity index 100% rename from core/modules/user/config/user.schema.yml rename to core/modules/user/config/schema/user.schema.yml diff --git a/core/modules/views/config/views.schema.yml b/core/modules/views/config/schema/views.schema.yml similarity index 100% rename from core/modules/views/config/views.schema.yml rename to core/modules/views/config/schema/views.schema.yml