Multi-idioma
El multi-idioma utiliza el componente symfony/translation.
Instalación
composer require symfony/translation
Crear Paquete de Idioma
Por defecto, webman coloca los paquetes de idioma en el directorio resource/translations
(si no existe, créalo tú mismo). Si necesitas cambiar el directorio, configúralo en config/translation.php
.
Cada idioma tiene su propia subcarpeta y las definiciones de idioma suelen ir por defecto en messages.php
. Por ejemplo:
resource/
└── translations
├── en
│ └── messages.php
└── zh_CN
└── messages.php
Todos los archivos de idioma devuelven un array, por ejemplo:
// resource/translations/en/messages.php
return [
'hello' => 'Hello webman',
];
Configuración
config/translation.php
return [
// Idioma por defecto
'locale' => 'zh_CN',
// Idioma de reemplazo. Si no se puede encontrar una traducción en el idioma actual, se intentará usar la traducción del idioma de reemplazo.
'fallback_locale' => ['zh_CN', 'en'],
// Directorio donde se almacenan los archivos de idioma
'path' => base_path() . '/resource/translations',
];
Traducción
La traducción se realiza mediante el método trans()
.
Crea el archivo de idioma resource/translations/zh_CN/messages.php
de la siguiente manera:
return [
'hello' => '¡Hola mundo!',
];
Crea el archivo app/controller/UserController.php
:
<?php
namespace app\controller;
use support\Request;
class UserController
{
public function get(Request $request)
{
$hello = trans('hello'); // ¡Hola mundo!
return response($hello);
}
}
Al visitar http://127.0.0.1:8787/user/get
regresará "¡Hola mundo!"
Cambiar Idioma Predeterminado
Para cambiar el idioma, usa el método locale()
.
Agrega el archivo de idioma resource/translations/en/messages.php
de la siguiente manera:
return [
'hello' => '¡Hola mundo!',
];
<?php
namespace app\controller;
use support\Request;
class UserController
{
public function get(Request $request)
{
// Cambiar idioma
locale('en');
$hello = trans('hello'); // ¡Hola mundo!
return response($hello);
}
}
Al visitar http://127.0.0.1:8787/user/get
regresará "¡Hola mundo!"
También puedes usar el cuarto parámetro de la función trans()
para cambiar temporalmente el idioma. Por ejemplo, los dos ejemplos a continuación son equivalentes:
<?php
namespace app\controller;
use support\Request;
class UserController
{
public function get(Request $request)
{
// Cuarto parámetro para cambiar el idioma
$hello = trans('hello', [], null, 'en'); // ¡Hola mundo!
return response($hello);
}
}
Establecer un Idioma Específico para Cada Solicitud
La traducción es un singleton, lo que significa que todas las solicitudes comparten la misma instancia. Si una solicitud usa locale()
para establecer el idioma por defecto, afectará a todas las solicitudes posteriores en el mismo proceso. Por lo tanto, se debe establecer un idioma específico para cada solicitud. Por ejemplo, utilizando el middleware siguiente:
Crea el archivo app/middleware/Lang.php
(si el directorio no existe, créalo tú mismo) de la siguiente manera:
<?php
namespace app\middleware;
use Webman\MiddlewareInterface;
use Webman\Http\Response;
use Webman\Http\Request;
class Lang implements MiddlewareInterface
{
public function process(Request $request, callable $handler) : Response
{
locale(session('lang', 'zh_CN'));
return $handler($request);
}
}
Agrega el middleware global en config/middleware.php
de la siguiente manera:
return [
// Middleware global
'' => [
// ... Se omiten otros middlewares
app\middleware\Lang::class,
]
];
Uso de Marcadores de Posición
A veces, un mensaje contiene variables que deben ser traducidas, por ejemplo:
trans('hello ' . $name);
En estos casos, se utilizan marcadores de posición.
Modifica resource/translations/zh_CN/messages.php
de la siguiente manera:
return [
'hello' => '¡Hola %name%!',
];
Al traducir, se pasa el valor correspondiente del marcador de posición como segundo parámetro:
trans('hello', ['%name%' => 'webman']); // ¡Hola webman!
Tratamiento de Pluralidad
Algunos idiomas requieren diferentes formas de frases dependiendo de la cantidad de elementos, por ejemplo Hay %count% manzanas
, donde la frase es correcta cuando %count%
es 1, pero incorrecta cuando es mayor.
En estos casos, se utilizan un pipe (|
) para listar las formas de pluralidad.
Agrega la clave apple_count
al archivo de idioma resource/translations/en/messages.php
de la siguiente manera:
return [
// ...
'apple_count' => 'Hay una manzana|Hay %count% manzanas',
];
trans('apple_count', ['%count%' => 10]); // Hay 10 manzanas
Incluso se pueden especificar rangos numéricos para crear reglas de pluralidad más complejas:
return [
// ...
'apple_count' => '{0} No hay manzanas|{1} Hay una manzana|]1,19] Hay %count% manzanas|[20,Inf[ Hay muchas manzanas'
];
trans('apple_count', ['%count%' => 20]); // Hay muchas manzanas
Especificar Archivos de Idioma
El archivo de idioma se llama por defecto messages.php
, pero en realidad puedes crear archivos de idioma con otros nombres.
Crea el archivo de idioma resource/translations/zh_CN/admin.php
de la siguiente manera:
return [
'hello_admin' => '¡Hola administrador!',
];
Especifica el archivo de idioma a través del tercer parámetro de trans()
(omitir la extensión .php
).
trans('hello', [], 'admin', 'zh_CN'); // ¡Hola administrador!
Más Información
Consulta el manual de symfony/translation para más detalles.