我正在慢慢学习如何应用 CakePHP 的翻译行为,并且我认为我已经掌握了基础知识,但我正在使用现有数据处理现有项目。 Cake 能为我插入新记录真是太好了,但我需要手动(我假设)为一些现有数据插入一些翻译。我的第一个问题:
如果 en_us 是我的默认语言并且是我的核心表中使用的语言,我是否必须在 i18n 表中拥有 en_us 的记录?例如,如果categories.name = 'Entertainment',我真的需要在i18n中创建一个“重复”记录来指示指定“Entertainment”的英文翻译吗?经验证据似乎表明是的,但这似乎需要很多额外的工作,所以我希望有人可以告诉我我错过了一些东西。
第二,有没有一种“简单”的方法将翻译记录存入数据库?随着项目过程中添加语言,返回并为遗留数据创建 i18n 记录将非常痛苦。
谢谢。
最佳答案
我知道这已经很旧了,但由于它没有得到解答,而且我在解决这个问题时遇到了一些麻烦,这里是我的两分钱:
范围,Cakephp 1.3。
首先,您的应用程序中的每个字段 -> 记录 -> 模型都需要一个 i18n 记录,当然只有具有翻译行为的模型并且仅适用于指定的字段,所以是的,您最终会得到重复的内容在实际模型字段和 i18n 表中。
此外,您需要为 find 方法指定的任何语言提供现有翻译才能返回任何内容。这让我很困惑,因为我还将翻译行为添加到了一个已经开发的项目中,其中包含大量数据。基本上我所做的是创建一个同步方法,以便为具有翻译行为的每个模型的每个字段创建每个翻译。如果将来我添加一种新语言,我就必须再次运行它。
这是代码:
$locales = array( 'spa', 'eng', 'por' );
$models = array( 'Event', 'News', 'Promotion', 'Shop', 'ShopCategory' );
foreach ( $models as $model )
{
$this->loadModel( $model );
$records = $this->{$model}->find( 'all', array(
'fields' => array( "*" ),
'contain' => FALSE
) );
$fields = $this->{$model}->actsAs['Translate'];
foreach ( $records as $record )
{
foreach ( $fields as $field )
{
foreach ( $locales as $locale )
{
$content = mysql_real_escape_string( $record[$model][$field] );
$this->{$model}->query( "INSERT INTO `i18n` (`locale`, `model`, `foreign_key`, `field`, `content`) VALUES('{$locale}', '{$model}', '{$record[$model]['id']}', '{$field}', '{$content}');" );
}
}
}
}
提示:使用 locale、model、foreign_key 和 field 键在 i18n 表中创建唯一索引。
所以,现在我已经用所有语言复制了原始数据,我需要能够使用给定语言创建新记录。问题是,如果我用英语创建新记录,我应该能够用西类牙语更新它,但由于西类牙语没有 i18n 记录,我在 CMS 中看不到该记录,也无法编辑它。 我解决这个问题的方法是在创建新记录时为每种语言创建 i18n 记录,但在编辑记录时仅使用当前语言进行编辑。
我对翻译行为使用了此修改: http://bin.cakephp.org/view/1939852942
但是进行此修改的大多数示例都表示您必须在表单中创建表单输入: echo $this->Form->input('name.eng'); echo $this->Form->input('name.spa'); echo $this->Form->input('description.eng'); echo $this->Form->input('description.spa');
我觉得这很烦人,所以我基本上在 app_controller 中创建了一个辅助函数来将可翻译字段转换为这个数据结构:
function _expandLocalizations( $data )
{
foreach ( $data as $modelName => $modelData )
{
if ( !isset( $modelData[$this->{$modelName}->primaryKey] ) )
{
foreach ( $this->{$modelName}->actsAs['Translate'] as $field )
{
$translations = array();
foreach ( $this->languages as $language )
{
$translations[$language] = $this->data[$modelName][$field];
}
$data[$modelName][$field] = $translations;
}
}
}
return $data;
}
在每个添加方法中:
if ( !empty( $this->data ) )
{
$this->News->set( $this->data );
if ( $this->News->validates() )
{
$this->News->create();
$data = $this->_expandLocalizations( $this->data );
$saved = $this->News->save( $data );
if ( $saved )
{
这样我就可以使用传统的表单,并且如果添加新语言我不需要更改 View 。 我需要修改传统的烘焙添加方法,因为我需要提交的数据进行验证,但需要修改后的数据进行保存。
最后,我按照以下步骤更改站点/管理中的语言:http://nuts-and-bolts-of-cakephp.com/2008/11/28/cakephp-url-based-language-switching-for-i18n-and-l10n-internationalization-and-localization/
基本上就是这样。 1. 您为数据库中已有的每个数据创建翻译,每个数据都复制到每种语言。 2. 在创建时为新记录创建每个翻译,当然所有翻译都具有相同的值。 3. 编辑所选翻译中的每条记录。
关于cakephp - 事后应用 CakePHP 的翻译行为,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/744802/