Commit 1dd9406b authored by webchick's avatar webchick

Issue #1842362 by vijaycs85, Sutharsan, Berdir, ocsilalala, skipyT: Replace...

Issue #1842362 by vijaycs85, Sutharsan, Berdir, ocsilalala, skipyT: Replace locale_project table and improve caching.
parent 06adfe58
......@@ -1607,16 +1607,15 @@ function _install_prepare_import($langcode) {
// we check if at least the major version number is available.
if ($info['major']) {
$core = $info['major'] . '.x';
db_insert('locale_project')
->fields(array(
'name' => 'drupal',
'project_type' => 'module',
'core' => $core,
'version' => $version,
'server_pattern' => $install_state['server_pattern'],
'status' => 1,
))
->execute();
$data = array(
'name' => 'drupal',
'project_type' => 'module',
'core' => $core,
'version' => $version,
'server_pattern' => $install_state['server_pattern'],
'status' => 1,
);
\Drupal::service('locale.project')->set($data['name'], $data);
module_load_include('compare.inc', 'locale');
locale_translation_check_projects_local(array('drupal'), array($install_state['parameters']['langcode']));
}
......
......@@ -19,9 +19,7 @@
* Clear the project data table.
*/
function locale_translation_flush_projects() {
// Followup issue: http://drupal.org/node/1842362
// Replace {locale_project} table by \Drupal::state() variable(s).
db_truncate('locale_project')->execute();
\Drupal::service('locale.project')->deleteAll();
}
/**
......@@ -55,11 +53,7 @@ function locale_translation_build_projects() {
$projects = locale_translation_project_list();
// Mark all previous projects as disabled and store new project data.
db_update('locale_project')
->fields(array(
'status' => 0,
))
->execute();
\Drupal::service('locale.project')->disableAll();
$default_server = locale_translation_default_translation_server();
......@@ -91,6 +85,7 @@ function locale_translation_build_projects() {
// For every project store information.
$data += array(
'name' => $name,
'version' => isset($data['info']['version']) ? $data['info']['version'] : '',
'core' => isset($data['info']['core']) ? $data['info']['core'] : \Drupal::CORE_COMPATIBILITY,
// A project can provide the path and filename pattern to download the
......@@ -102,17 +97,7 @@ function locale_translation_build_projects() {
$projects[$name] = $project;
// Create or update the project record.
db_merge('locale_project')
->key('name', $project->name)
->fields(array(
'name' => $project->name,
'project_type' => $project->project_type,
'core' => $project->core,
'version' => $project->version,
'server_pattern' => $project->server_pattern,
'status' => $project->status,
))
->execute();
\Drupal::service('locale.project')->set($project->name, $data);
// Invalidate the cache of translatable projects.
locale_translation_clear_cache_projects();
......
......@@ -228,55 +228,6 @@ function locale_schema() {
),
'primary key' => array('project', 'langcode'),
);
$schema['locale_project'] = array(
'description' => 'Translation status information for projects and server data.',
'fields' => array(
'name' => array(
'description' => 'A unique short name to identify the project.',
'type' => 'varchar',
'length' => 255,
'not null' => TRUE,
),
'project_type' => array(
'description' => 'Project type: core, module, or theme.',
'type' => 'varchar',
'length' => 15,
'not null' => TRUE,
),
'core' => array(
// http://drupal.org/node/542202#core has an example.
'description' => 'Core compatibility string for this project, for example: 8.x',
'type' => 'varchar',
'length' => 4,
'not null' => TRUE,
'default' => '',
),
'version' => array(
// http://drupal.org/node/467026 has examples.
'description' => 'The version release of the project, for example: 8.x-2.1 or 8.x-1.0-dev',
'type' => 'varchar',
'length' => 128,
'not null' => TRUE,
'default' => '',
),
'server_pattern' => array(
'description' => 'Pattern of path and name of the gettext file at the translation server.',
'type' => 'varchar',
'length' => 255,
'not null' => TRUE,
'default' => '',
),
'status' => array(
// locale.compare.inc gives possible values for status.
'description' => 'The status of the project. Possible values are: 1 = enabled, 0 = disabled.',
'type' => 'int',
'not null' => TRUE,
'default' => 1,
),
),
'primary key' => array('name'),
);
return $schema;
}
......
......@@ -530,9 +530,7 @@ function locale_system_remove($components) {
// Remove translatable projects.
// Followup issue http://drupal.org/node/1842362 to replace the
// {locale_project} table. Then change this to a function call.
db_delete('locale_project')
->condition('name', $list)
->execute();
\Drupal::service('locale.project')->deleteMultiple($list);
// Clear the translation status.
locale_translation_status_delete_projects($list);
......
......@@ -7,6 +7,9 @@ services:
arguments: ['@database']
tags:
- { name: backend_overridable }
locale.project:
class: Drupal\locale\LocaleProjectStorage
arguments: ['@keyvalue']
string_translator.locale.lookup:
class: Drupal\locale\LocaleTranslation
arguments: ['@locale.storage', '@cache.default', '@lock', '@config.factory', '@language_manager']
......
......@@ -57,8 +57,7 @@ function locale_translation_get_projects($project_names = array()) {
if (empty($projects)) {
// Get project data from the database.
$row_count = db_query_range('SELECT 1 FROM {locale_project}', 0, 1)->fetchField();
$row_count = \Drupal::service('locale.project')->countProjects();
// http://drupal.org/node/1777106 is a follow-up issue to make the check for
// possible out-of-date project information more robust.
if ($row_count == 0 && \Drupal::moduleHandler()->moduleExists('update')) {
......@@ -67,11 +66,10 @@ function locale_translation_get_projects($project_names = array()) {
// data if none are found.
locale_translation_build_projects();
}
$result = db_query('SELECT name, project_type, core, version, server_pattern, status FROM {locale_project}');
foreach ($result as $project) {
$projects[$project->name] = $project;
}
$projects = \Drupal::service('locale.project')->getAll();
array_walk($projects, function(&$project) {
$project = (object) $project;
});
}
// Return the requested project names or all projects.
......@@ -329,13 +327,15 @@ function locale_cron_fill_queue() {
// Determine which project+language should be updated.
$last = REQUEST_TIME - $config->get('translation.update_interval_days') * 3600 * 24;
$query = db_select('locale_file', 'f');
$query->join('locale_project', 'p', 'p.name = f.project');
$query->condition('f.last_checked', $last, '<');
$query->fields('f', array('project', 'langcode'));
// Only currently installed / enabled components should be checked for.
$query->condition('p.status', 1);
$files = $query->execute()->fetchAll();
$projects = \Drupal::service('locale.project')->getAll();
$projects = array_filter($projects, function($project) {
return $project['status'] == 1;
});
$files = db_select('locale_file', 'f')
->condition('f.project', array_keys($projects))
->condition('f.last_checked', $last, '<')
->fields('f', array('project', 'langcode'))
->execute()->fetchAll();
foreach ($files as $file) {
$updates[$file->project][] = $file->langcode;
......
<?php
/**
* @file
* Contains Drupal\locale\LocaleProjectStorage.
*/
namespace Drupal\locale;
use Drupal\Core\KeyValueStore\KeyValueFactoryInterface;
/**
* Provides the locale project storage system using a key value store.
*/
class LocaleProjectStorage implements LocaleProjectStorageInterface {
/**
* The key value store to use.
*
* @var \Drupal\Core\KeyValueStore\KeyValueStoreInterface
*/
protected $keyValueStore;
/**
* Static state cache.
*
* @var array
*/
protected $cache = array();
/**
* Cache status flag.
*
* @var bool
*/
protected static $all = FALSE;
/**
* Constructs a State object.
*
* @param \Drupal\Core\KeyValueStore\KeyValueFactoryInterface $key_value_factory
* The key value store to use.
*/
function __construct(KeyValueFactoryInterface $key_value_factory) {
$this->keyValueStore = $key_value_factory->get('locale.project');
}
/**
* {@inheritdoc}
*/
public function get($key, $default = NULL) {
$values = $this->getMultiple(array($key));
return isset($values[$key]) ? $values[$key] : $default;
}
/**
* {@inheritdoc}
*/
public function getMultiple(array $keys) {
$values = array();
$load = array();
foreach ($keys as $key) {
// Check if we have a value in the cache.
if (isset($this->cache[$key])) {
$values[$key] = $this->cache[$key];
}
// Load the value if we don't have an explicit NULL value.
elseif (!array_key_exists($key, $this->cache)) {
$load[] = $key;
}
}
if ($load) {
$loaded_values = $this->keyValueStore->getMultiple($load);
foreach ($load as $key) {
// If we find a value, even one that is NULL, add it to the cache and
// return it.
if (isset($loaded_values[$key])) {
$values[$key] = $loaded_values[$key];
$this->cache[$key] = $loaded_values[$key];
}
else {
$this->cache[$key] = NULL;
}
}
}
return $values;
}
/**
* {@inheritdoc}
*/
public function set($key, $value) {
$this->setMultiple(array($key => $value));
}
/**
* {@inheritdoc}
*/
public function setMultiple(array $data) {
foreach ($data as $key => $value) {
$this->cache[$key] = $value;
}
$this->keyValueStore->setMultiple($data);
}
/**
* {@inheritdoc}
*/
public function delete($key) {
$this->deleteMultiple(array($key));
}
/**
* {@inheritdoc}
*/
public function deleteMultiple(array $keys) {
foreach ($keys as $key) {
$this->cache[$key] = NULL;
}
$this->keyValueStore->deleteMultiple($keys);
}
/**
* {@inheritdoc}
*/
public function resetCache() {
$this->cache = array();
static::$all = FALSE;
}
/**
* {@inheritdoc}
*/
public function deleteAll() {
$this->keyValueStore->deleteAll();
$this->resetCache();
}
/**
* {@inheritdoc}
*/
public function disableAll() {
$projects = $this->keyValueStore->getAll();
foreach (array_keys($projects) as $key) {
$projects[$key]['status'] = 0;
if (isset($cache[$key])) {
$cache[$key] = $projects[$key];
}
}
$this->keyValueStore->setMultiple($projects);
}
/**
* {@inheritdoc}
*/
public function countProjects() {
return count($this->getAll());
}
/**
* {@inheritdoc}
*/
public function getAll() {
if (!static::$all) {
$this->cache = $this->keyValueStore->getAll();
static::$all = TRUE;
}
return $this->cache;
}
}
<?php
/**
* @file
* Contains Drupal\locale\LocalProjectStorageInterface.
*/
namespace Drupal\locale;
/**
* Defines the locale project storage interface.
*/
interface LocaleProjectStorageInterface {
/**
* Returns the stored value for a given key.
*
* @param string $key
* The key of the data to retrieve.
* @param mixed $default
* The default value to use if the key is not found.
*
* @return mixed
* The stored value, or the default value if no value exists.
*/
public function get($key, $default = NULL);
/**
* Returns a list of project records.
*
* @param array $keys
* A list of keys to retrieve.
*
* @return array
* An associative array of items successfully returned, indexed by key.
*/
public function getMultiple(array $keys);
/**
* Creates or updates the project record.
*
* @param string $key
* The key of the data to store.
* @param mixed $value
* The data to store.
*/
public function set($key, $value);
/**
* Creates or updates multiple project records.
*
* @param array $data
* An associative array of key/value pairs.
*/
public function setMultiple(array $data);
/**
* Deletes project records for a given key.
*
* @param string $key
* The key of the data to delete.
*/
public function delete($key);
/**
* Deletes multiple project records.
*
* @param array $keys
* A list of item names to delete.
*/
public function deleteMultiple(array $keys);
/**
* Returns all the project records.
*
* @return array
* An associative array of items successfully returned, indexed by key.
*/
public function getAll();
/**
* Deletes all projects records.
*
* @return array
* An associative array of items successfully returned, indexed by key.
*/
public function deleteAll();
/**
* Mark all projects as disabled.
*/
public function disableAll();
/**
* Resets the project storage cache.
*/
public function resetCache();
/**
* Returns the count of project records.
*
* @return int
* The number of saved items.
*/
public function countProjects();
}
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment