Imporove localization strings import and saving

This commit is contained in:
Dmitriy Simushev 2014-07-14 10:23:49 +00:00
parent 67383cf052
commit 5636b1ab3d
2 changed files with 53 additions and 33 deletions

View File

@ -117,6 +117,14 @@ translation:
context: "varchar(256) NOT NULL DEFAULT ''" context: "varchar(256) NOT NULL DEFAULT ''"
source: "text COLLATE utf8_bin" source: "text COLLATE utf8_bin"
translation: "text" translation: "text"
# An artificial unique key for the record. It is needed to avoid
# duplication of translation strings. The field contains SHA-1 hash of
# combination of locale, context and source fields. Native MySQL unique
# keys cannot be applied to them because "source" field has text data
# type.
hash: "char(40) NOT NULL"
unique_keys:
hash: [hash]
# Contains locales info # Contains locales info
locale: locale:

View File

@ -711,7 +711,10 @@ function get_locale_info($locale)
} }
/** /**
* Load localized messages id some service locale info. * Loads localized messages for the specified locale.
*
* In common case messages will be loaded from the database but if the
* installation is runnig they will be loaded from files.
* *
* Messages are statically cached. * Messages are statically cached.
* *
@ -734,24 +737,39 @@ function load_messages($locale)
$messages[$locale] = $locale_data['messages']; $messages[$locale] = $locale_data['messages'];
} else { } else {
// Load localizations from the database // Load localizations from the database
$db = Database::getInstance(); $messages[$locale] = load_db_messages($locale);
$db_messages = $db->query(
'SELECT * FROM {translation} WHERE locale = ?',
array($locale),
array(
'return_rows' => Database::RETURN_ALL_ROWS
)
);
foreach ($db_messages as $message) {
$messages[$locale][$message['source']] = $message['translation'];
}
} }
} }
return $messages[$locale]; return $messages[$locale];
} }
/**
* Loads localized messages from the database for the specified locale.
*
* @param string $locale Name of a locale whose messages should be loaded.
* @return array Localized messages array
*/
function load_db_messages($locale)
{
// Load localizations from the database
$db = Database::getInstance();
$db_messages = $db->query(
'SELECT * FROM {translation} WHERE locale = ?',
array($locale),
array(
'return_rows' => Database::RETURN_ALL_ROWS
)
);
$messages = array();
foreach ($db_messages as $message) {
$messages[$message['source']] = $message['translation'];
}
return $messages;
}
/** /**
* Imports localized messages from the specified file to the specified locale. * Imports localized messages from the specified file to the specified locale.
* *
@ -761,7 +779,7 @@ function load_messages($locale)
*/ */
function import_messages($locale, $file, $override = false) function import_messages($locale, $file, $override = false)
{ {
$available_messages = load_messages($locale); $available_messages = load_db_messages($locale);
$locale_data = read_locale_file($file); $locale_data = read_locale_file($file);
foreach ($locale_data['messages'] as $source => $translation) { foreach ($locale_data['messages'] as $source => $translation) {
@ -865,27 +883,18 @@ function get_localized_string($string, $locale)
*/ */
function save_message($locale, $key, $value) function save_message($locale, $key, $value)
{ {
$db = Database::getInstance(); static $available_messages = null;
// Check if the string is already in the database. if (is_null($available_messages)) {
list($count) = $db->query( $available_messages = load_db_messages($locale);
'SELECT COUNT(*) FROM {translation} WHERE locale = :locale AND source = :key', }
array(
':locale' => $locale,
':key' => $key,
),
array(
'return_rows' => Database::RETURN_ONE_ROW,
'fetch_type' => Database::FETCH_NUM,
)
);
$exists = ($count != 0);
// Prepare the value to save in the database. // Prepare the value to save in the database.
$translation = str_replace("\r", "", trim($value)); $translation = str_replace("\r", "", trim($value));
if ($exists) { $db = Database::getInstance();
// There is no such string in the database. Create it. if (array_key_exists($key, $available_messages)) {
// The string is already in the database. Update it.
$db->query( $db->query(
('UPDATE {translation} SET translation = :translation ' ('UPDATE {translation} SET translation = :translation '
. 'WHERE locale = :locale AND source = :key'), . 'WHERE locale = :locale AND source = :key'),
@ -896,16 +905,19 @@ function save_message($locale, $key, $value)
) )
); );
} else { } else {
// The string is already in the database. Update it. // There is no such string in the database. Create it.
$db->query( $db->query(
('INSERT INTO {translation} (locale, source, translation) ' ('INSERT INTO {translation} (locale, source, translation, hash) '
. 'VALUES (:locale, :key, :translation)'), . 'VALUES (:locale, :key, :translation, :hash)'),
array( array(
':locale' => $locale, ':locale' => $locale,
':key' => $key, ':key' => $key,
':translation' => $translation, ':translation' => $translation,
':hash' => sha1($locale . '##'. $key),
) )
); );
// The message is now in the database. Next time it should be updated.
$available_messages[$key] = $value;
} }
} }