/** * Creates PO file for specified Language * * @param string $lang_code 2-letters language code (Example: "en", "ru") * @param string $output Output destination * screen - Output countent direct to browser page * download - Force file downloading * server - upload file to the config.dir.lang_packs directory */ public static function export($lang_code, $output = 'download') { $mve_lang_variables = array(); // Translation packs should not include "Not translated" language data $allow_overlap = $lang_code == 'en' ? true : false; $default_lang = Registry::get('settings.Appearance.backend_default_language'); $langs = self::get(array('lang_code' => $lang_code)); $lang = $langs[$lang_code]; $pack_path = fn_get_cache_path(false) . 'lang_pack/'; $core_pack_path = $pack_path . 'core.po'; $mve_pack_path = $pack_path . 'editions/mve.po'; fn_rm($pack_path); fn_mkdir($pack_path); if (fn_allowed_for('MULTIVENDOR') && is_file(Registry::get('config.dir.lang_packs') . $default_lang . '/editions/mve.po')) { $mve_lang_variables = Po::getValues(Registry::get('config.dir.lang_packs') . $default_lang . '/editions/mve.po'); Po::createHeader($mve_pack_path, $lang); } Po::createHeader($core_pack_path, $lang); // Export Language values list($values) = LanguageValues::getVariables(array(), 0, $lang_code); foreach ($values as $_id => $value) { $values[$_id]['msgctxt'] = 'Languages' . \I18n_Pofile::DELIMITER . $value['name']; } $values = fn_array_value_to_key($values, 'msgctxt'); $addons_lang_vars = array(); list($addons) = fn_get_addons(array('type' => 'installed'), 0, $lang_code); foreach ($addons as $addon_id => $addon) { $addons_lang_vars = array_merge($addons_lang_vars, self::exportAddonsPo($addon_id, $pack_path . 'addons/' . $addon_id . '.po', $lang_code, $values)); } $original_values = self::getOriginalValues('Languages'); $values = array_diff_key($values, $addons_lang_vars); foreach ($values as $_id => $value) { $values[$_id]['original_value'] = isset($original_values['Languages::' . $value['name']]) ? $original_values['Languages::' . $value['name']]['msgid'] : ''; } $values = Po::convert($values, array(), $allow_overlap); list($values, $excluded) = self::excludeEditionVariables('Languages', $values, $mve_lang_variables); Po::putValues('Languages', $values, $core_pack_path); if (!empty($excluded)) { Po::putValues('Languages', $excluded, $mve_pack_path); } // Export Settings Sections $sections = Settings::instance()->getCoreSections($lang_code); $original_values = self::getOriginalValues('SettingsSections'); foreach ($sections as $_id => $value) { $sections[$_id]['original_value'] = isset($original_values['SettingsSections::' . $value['section_id']]) ? $original_values['SettingsSections::' . $value['section_id']]['msgid'] : ''; } $_sections = Po::convert($sections, array('id' => 'section_id', 'value' => 'description'), $allow_overlap); list($_sections, $excluded) = self::excludeEditionVariables('SettingsSections', $_sections, $mve_lang_variables); Po::putValues('SettingsSections', $_sections, $core_pack_path); if (!empty($excluded)) { Po::putValues('SettingsSections', $excluded, $mve_pack_path); } unset($_sections); $original_options = self::getOriginalValues('SettingsOptions'); $original_variants = self::getOriginalValues('SettingsVariants'); $original_tooltips = self::getOriginalValues('SettingsTooltips'); foreach ($sections as $section) { $options = Settings::instance()->getList($section['object_id'], 0, false, null, $lang_code); $_options = array(); $_tooltips = array(); foreach ($options['main'] as $option) { $_options[] = array('name' => $option['name'], 'value' => $option['description'], 'original_value' => isset($original_options['SettingsOptions' . \I18n_Pofile::DELIMITER . $option['name']]) ? $original_options['SettingsOptions' . \I18n_Pofile::DELIMITER . $option['name']]['msgid'] : ''); if (!empty($option['variants'])) { $_variants = array(); foreach ($option['variants'] as $variant_id => $variant) { $_variants[] = array('name' => $variant_id, 'value' => $variant, 'original_value' => isset($original_variants['SettingsVariants' . \I18n_Pofile::DELIMITER . $option['name'] . \I18n_Pofile::DELIMITER . $variant_id]) ? $original_variants['SettingsVariants' . \I18n_Pofile::DELIMITER . $option['name'] . \I18n_Pofile::DELIMITER . $variant_id]['msgid'] : ''); } $_variants = Po::convert($_variants, array(), $allow_overlap); list($_variants, $excluded) = self::excludeEditionVariables('SettingsVariants', $_variants, $mve_lang_variables); Po::putValues('SettingsVariants' . \I18n_Pofile::DELIMITER . $option['name'], $_variants, $core_pack_path); if (!empty($excluded)) { Po::putValues('SettingsVariants', $excluded, $mve_pack_path); } unset($_variants); } if (!empty($option['tooltip'])) { $_tooltips[] = array('name' => $option['name'], 'value' => $option['tooltip'], 'original_value' => isset($original_tooltips['SettingsTooltips' . \I18n_Pofile::DELIMITER . $option['name']]) ? $original_tooltips['SettingsTooltips' . \I18n_Pofile::DELIMITER . $option['name']]['msgid'] : ''); } } $_options = Po::convert($_options, array(), $allow_overlap); list($_options, $excluded) = self::excludeEditionVariables('SettingsOptions', $_options, $mve_lang_variables); Po::putValues('SettingsOptions', $_options, $core_pack_path); if (!empty($excluded)) { Po::putValues('SettingsOptions', $excluded, $mve_pack_path); } $_tooltips = Po::convert($_tooltips, array(), $allow_overlap); list($_tooltips, $excluded) = self::excludeEditionVariables('SettingsTooltips', $_tooltips, $mve_lang_variables); Po::putValues('SettingsTooltips', $_tooltips, $core_pack_path); if (!empty($excluded)) { Po::putValues('SettingsTooltips', $excluded, $mve_pack_path); } } // Export Profile fields $profile_fields = fn_get_profile_fields('ALL', array(), $lang_code); $original_values = self::getOriginalValues('ProfileFields'); $values = array(); foreach ($profile_fields as $zone => $fields) { foreach ($fields as $field_id => $field) { $values[] = array('name' => $field['field_name'], 'value' => $field['description'], 'original_value' => isset($original_values['ProfileFields::' . $field['field_name']]) ? $original_values['ProfileFields::' . $field['field_name']]['msgid'] : ''); } } $values = Po::convert($values, array(), $allow_overlap); list($values, $excluded) = self::excludeEditionVariables('ProfileFields', $values, $mve_lang_variables); Po::putValues('ProfileFields', $values, $core_pack_path); if (!empty($excluded)) { Po::putValues('ProfileFields', $excluded, $mve_pack_path); } fn_compress_files($lang_code . '.zip', './', $pack_path); $filename = $pack_path . $lang_code . '.zip'; switch ($output) { case 'server': fn_copy($filename, Registry::get('config.dir.lang_packs') . $lang_code . '.zip'); break; case 'download': fn_get_file($filename, $lang_code . '.zip'); break; } return true; }
private function getPoValues($lang_code, $section) { $addon_id = (string) $this->_xml->id; $result = array(); $pack = $this->getPoPath($lang_code); $default_pack = $this->getPoPath($this->getDefaultLanguage()); if ($default_pack != $pack && file_exists($default_pack)) { $result = $this->parsePoContent(Po::getValues($default_pack, $section)); } if (file_exists($pack)) { $result = fn_array_merge($result, $this->parsePoContent(Po::getValues($pack, $section))); } return $result; }
/** * Installs new language from PO pack * * @param string $pack_path Path to PO file * @param array $params * reinstall: Skip adding new language * validate_lang_code:Check meta information (lang_code) with updated language data (lang_code) and forbid to update if does not match * force_lang_code: Skip meta lang code and use this one in all laguage variables * @return int Language ID */ public static function installLanguagePack($pack_path, $params = array()) { $default_params = array('reinstall' => false, 'validate_lang_code' => '', 'force_lang_code' => ''); $params = array_merge($default_params, $params); if (!file_exists($pack_path)) { fn_set_notification('E', __('error'), __('unable_to_read_resource', array('[file]' => fn_get_rel_dir($pack_path)))); return false; } $lang_meta = self::getLangPacksMeta(dirname($pack_path) . '/', basename($pack_path), $params['reinstall']); if (!self::isValidMeta($lang_meta)) { // Failed to read meta data of new language fn_set_notification('E', __('error'), __('check_po_file')); return false; } if (!empty($params['validate_lang_code']) && $lang_meta['lang_code'] != $params['validate_lang_code']) { fn_set_notification('E', __('error'), __('po_meta_error_validating_lang_code')); return false; } $lc = false; if (!Registry::get('runtime.company_id')) { if (!$params['reinstall']) { $language_data = array('lang_code' => $lang_meta['lang_code'], 'name' => $lang_meta['name'], 'country_code' => $lang_meta['country_code']); $lc = self::update($language_data, 0); } else { $lc = true; } if ($lc !== false) { fn_save_languages_integrity(); $query = array(); $original_values_query = array(); $iteration = 0; $max_vars_in_query = 500; if (!empty($params['force_lang_code'])) { $lang_meta['lang_code'] = $params['force_lang_code']; } $lang_data = Po::getValues($pack_path, 'Languages'); if (!is_array($lang_data)) { fn_set_notification('E', __('error'), $lang_data); return array(); } foreach ($lang_data as $var_name => $var_data) { if (!empty($var_name)) { $id = $var_data['id']; $value = implode('', $var_data['msgstr']); $original_value = $var_data['msgid']; $value = empty($value) ? $original_value : $value; $query[] = db_quote('(?s, ?s, ?s)', $lang_meta['lang_code'], trim($id), trim($value)); $original_values_query[] = db_quote('(?s, ?s)', $var_name, trim($original_value)); } if ($iteration > $max_vars_in_query) { self::executeLangQueries('language_values', array('lang_code', 'name', 'value'), $query); self::executeLangQueries('original_values', array('msgctxt', 'msgid'), $original_values_query); $query = array(); $iteration = 0; } $iteration++; } self::executeLangQueries('language_values', array('lang_code', 'name', 'value'), $query); self::executeLangQueries('original_values', array('msgctxt', 'msgid'), $original_values_query); $settings_sections = Po::getValues($pack_path, 'SettingsSections'); $query = array(); $original_values_query = array(); $iteration = 0; foreach ($settings_sections as $var_name => $var_data) { if (!empty($var_name)) { $value = implode('', $var_data['msgstr']); $original_value = $var_data['msgid']; $value = empty($value) ? $original_value : $value; if (!empty($var_data['parent'])) { $parent_id = db_get_field('SELECT section_id FROM ?:settings_sections WHERE name = ?s AND type = ?s', $var_data['parent'], Settings::ADDON_SECTION); $section_id = db_get_field('SELECT section_id FROM ?:settings_sections WHERE name = ?s AND parent_id = ?i', $var_data['id'], $parent_id); } else { $section_id = db_get_field('SELECT section_id FROM ?:settings_sections WHERE name = ?s', $var_data['id']); } if (empty($section_id)) { continue; } $query[] = db_quote('(?i, ?s, ?s, ?s)', $section_id, 'S', $lang_meta['lang_code'], trim($value), trim($original_value)); $original_values_query[] = db_quote('(?s, ?s)', trim($var_name), trim($original_value)); } if ($iteration > $max_vars_in_query) { self::executeLangQueries('settings_descriptions', array('object_id', 'object_type', 'lang_code', 'value'), $query); self::executeLangQueries('original_values', array('msgctxt', 'msgid'), $original_values_query); $query = array(); $iteration = 0; } $iteration++; } self::executeLangQueries('settings_descriptions', array('object_id', 'object_type', 'lang_code', 'value'), $query); self::executeLangQueries('original_values', array('msgctxt', 'msgid'), $original_values_query); $original_values_query = array(); $setting_options = Po::getValues($pack_path, 'SettingsOptions'); foreach ($setting_options as $var_name => $var_data) { if (!empty($var_name)) { $value = implode('', $var_data['msgstr']); $original_value = $var_data['msgid']; $value = empty($value) ? $original_value : $value; $object = Settings::instance()->getId($var_data['id'], $var_data['parent']); if (empty($object)) { continue; } $query = array('object_id' => $object, 'object_type' => 'O', 'lang_code' => $lang_meta['lang_code'], 'value' => trim($value)); $update = array('value' => trim($value)); $original_values_query[] = db_quote('(?s, ?s)', trim($var_name), trim($original_value)); db_query('INSERT INTO ?:settings_descriptions ?e ON DUPLICATE KEY UPDATE ?u', $query, $update); self::executeLangQueries('original_values', array('msgctxt', 'msgid'), $original_values_query); } } $original_values_query = array(); $settings_tooltips = Po::getValues($pack_path, 'SettingsTooltips'); foreach ($settings_tooltips as $var_name => $var_data) { if (!empty($var_name)) { $value = implode('', $var_data['msgstr']); $original_value = $var_data['msgid']; $value = empty($value) ? $original_value : $value; $object = Settings::instance()->getId($var_data['id'], $var_data['parent']); if (empty($object)) { continue; } $query = array('object_id' => $object, 'object_type' => 'O', 'lang_code' => $lang_meta['lang_code'], 'tooltip' => trim($value)); $update = array('tooltip' => trim($value)); $original_values_query[] = db_quote('(?s, ?s)', trim($var_name), trim($original_value)); db_query('INSERT INTO ?:settings_descriptions ?e ON DUPLICATE KEY UPDATE ?u', $query, $update); self::executeLangQueries('original_values', array('msgctxt', 'msgid'), $original_values_query); } } $setting_variants = Po::getValues($pack_path, 'SettingsVariants'); $query = array(); $original_values_query = array(); $iteration = 0; foreach ($setting_variants as $var_name => $var_data) { if (!empty($var_name)) { $value = implode('', $var_data['msgstr']); $original_value = $var_data['msgid']; $value = empty($value) ? $original_value : $value; $object = Settings::instance()->getVariant($var_data['section'], $var_data['parent'], $var_data['id']); if (empty($object)) { continue; } $query[] = db_quote('(?i, ?s, ?s, ?s)', $object['variant_id'], 'V', $lang_meta['lang_code'], trim($value)); $original_values_query[] = db_quote('(?s, ?s)', trim($var_name), trim($original_value)); } if ($iteration > $max_vars_in_query) { self::executeLangQueries('settings_descriptions', array('variant_id', 'object_type', 'lang_code', 'value'), $query); self::executeLangQueries('original_values', array('msgctxt', 'msgid'), $original_values_query); $query = array(); $iteration = 0; } $iteration++; } self::executeLangQueries('settings_descriptions', array('object_id', 'object_type', 'lang_code', 'value'), $query); self::executeLangQueries('original_values', array('msgctxt', 'msgid'), $original_values_query); $addons = Po::getValues($pack_path, 'Addons'); $query = array(); $original_values_query = array(); if (!empty($addons)) { foreach ($addons as $var_name => $var_data) { if (!empty($var_name)) { $value = implode('', $var_data['msgstr']); $original_value = $var_data['msgid']; $value = empty($value) ? $original_value : $value; if ($var_data['parent'] == 'name') { db_query('UPDATE ?:addon_descriptions SET name = ?s WHERE addon = ?s AND lang_code = ?s', trim($value), $var_data['id'], $lang_meta['lang_code']); } else { db_query('UPDATE ?:addon_descriptions SET description = ?s WHERE addon = ?s AND lang_code = ?s', trim($value), $var_data['id'], $lang_meta['lang_code']); } $original_values_query[] = db_quote('(?s, ?s)', trim($var_name), trim($original_value)); } } self::executeLangQueries('original_values', array('msgctxt', 'msgid'), $original_values_query); } $profile_fields = Po::getValues($pack_path, 'ProfileFields'); $query = array(); $original_values_query = array(); foreach ($profile_fields as $var_name => $var_data) { if (!empty($var_name)) { $value = implode('', $var_data['msgstr']); $original_value = $var_data['msgid']; $value = empty($value) ? $original_value : $value; $field_ids = db_get_fields('SELECT field_id FROM ?:profile_fields WHERE field_name = ?s', $var_data['id']); if (empty($field_ids)) { continue; } foreach ($field_ids as $field_id) { $query[] = db_quote('(?i, ?s, ?s, ?s)', $field_id, trim($value), 'F', $lang_meta['lang_code']); } $original_values_query[] = db_quote('(?s, ?s)', trim($var_name), trim($original_value)); } } self::executeLangQueries('profile_field_descriptions', array('object_id', 'description', 'object_type', 'lang_code'), $query); self::executeLangQueries('original_values', array('msgctxt', 'msgid'), $original_values_query); if (!$params['reinstall']) { fn_set_notification('N', __('notice'), __('text_changes_saved')); } $_suffix = ''; } } return $lc; }