ruby on rails - relacional - I18n: ¿Cómo verificar si faltan un par de clave/valor de traducción?
nosql clave valor oracle (4)
Acabo de tener la misma pregunta y quiero calcular una cadena automática en caso de que falte la traducción. Si uso la opción por :default
, tengo que calcular la cadena automática cada vez, incluso cuando no falta la traducción. Así que busqué otra solución.
Puede agregar la opción :raise => true
o usar I18n.translate!
en lugar de I18n.translate
. Si no se puede encontrar una traducción, se genera una excepción.
begin
I18n.translate!(''this.key.should.be.translated'', :raise => true)
rescue I18n::MissingTranslationData
do_some_resource_eating_text_generation_here
end
Estoy usando Ruby on Rails 3.1.0 y la gema I18n . Yo (estoy implementando un complemento y) Me gustaría verificar en tiempo de ejecución si al I18n le faltan una clave de traducción / pares de valores y, si es así, usar una cadena personalizada. Es decir, tengo:
validates :link_url,
:format => {
:with => REGEX,
:message => I18n.t(
''custom_invalid_format'',
:scope => ''activerecord.errors.messages''
)
}
Si en el archivo .yml
no hay el siguiente código
activerecord:
errors:
messages:
custom_invalid_format: This is the test error message 1
Me gustaría usar el This is the test error message 2
. ¿Es posible? Si es así, ¿cómo puedo hacer eso?
BTW : Por razones de rendimiento, ¿es recomendable verificar en tiempo de ejecución si los pares clave / valor de traducción están presentes?
No sé cómo hacerlo en tiempo de ejecución, pero puedes usar rake para averiguarlo. Tendrás que crear tu propia tarea de rake para eso. Aquí hay uno:
namespace :i18n do
desc "Find and list translation keys that do not exist in all locales"
task :missing_keys => :environment do
def collect_keys(scope, translations)
full_keys = []
translations.to_a.each do |key, translations|
new_scope = scope.dup << key
if translations.is_a?(Hash)
full_keys += collect_keys(new_scope, translations)
else
full_keys << new_scope.join(''.'')
end
end
return full_keys
end
# Make sure we''ve loaded the translations
I18n.backend.send(:init_translations)
puts "#{I18n.available_locales.size} #{I18n.available_locales.size == 1 ? ''locale'' : ''locales''} available: #{I18n.available_locales.to_sentence}"
# Get all keys from all locales
all_keys = I18n.backend.send(:translations).collect do |check_locale, translations|
collect_keys([], translations).sort
end.flatten.uniq
puts "#{all_keys.size} #{all_keys.size == 1 ? ''unique key'' : ''unique keys''} found."
missing_keys = {}
all_keys.each do |key|
I18n.available_locales.each do |locale|
I18n.locale = locale
begin
result = I18n.translate(key, :raise => true)
rescue I18n::MissingInterpolationArgument
# noop
rescue I18n::MissingTranslationData
if missing_keys[key]
missing_keys[key] << locale
else
missing_keys[key] = [locale]
end
end
end
end
puts "#{missing_keys.size} #{missing_keys.size == 1 ? ''key is missing'' : ''keys are missing''} from one or more locales:"
missing_keys.keys.sort.each do |key|
puts "''#{key}'': Missing from #{missing_keys[key].join('', '')}"
end
end
end
ponga lo dado en un archivo .rake en su directorio lib / tasks y ejecute:
rake i18n:missing_keys
La fuente de información está here y el código en github here .
Podría pasar un parámetro predeterminado a I18n.t:
I18n.t :missing, :default => ''Not here''
# => ''Not here''
Puedes leer más sobre esto here .
Si desea pasar una variable al mensaje como This is the test error message {variable}
Esto es posible usando variables en el archivo de idioma como abajo.
# app/views/home/index.html.erb
<%=t ''greet_username'', :user => "Bill", :message => "Goodbye" %>
# config/locales/en.yml
en:
greet_username: "%{message}, %{user}!"
Más descripción se puede encontrar aquí .