December 15th, 2008 By: Daniel
What happens when you add a new string to your default locale file and forget about the other languages? Well, by default it’ll raise a MissingTranslationData and your users will see an ugly string the likes of “es-MX, marketing_interface, index, title“. Wouldn’t it be better to at least try and default to English? My guess is that most people would prefer to see the message in another language than some cryptic error message. And while we’re wishing, don’t you think the localize method shouldn’t die a noisy death when you happen to pass it a nil?
My solution? A custom I18n backend. I simply copy/pasted the code from the default “Simple” backend, tweaked a few lines and I was good to go!
# In some file that gets sourced on startup, like maybe in your config/initializers directory
module I18n
module Backend
class Moki < Simple
def translate(locale, key, options = {})
raise InvalidLocale.new(locale) if locale.nil?
return key.map { |k| translate(locale, k, options) } if key.is_a? Array
reserved = :scope, :default
count, scope, default = options.values_at(:count, *reserved)
options.delete(:default)
values = options.reject { |name, value| reserved.include?(name) }
entry = lookup(locale, key, scope)
if entry.nil?
entry = default(locale, default, options)
entry ||= lookup(I18n.default_locale, key, scope)
raise(I18n::MissingTranslationData.new(locale, key, options)) if entry.nil?
end
entry = pluralize(locale, entry, count)
entry = interpolate(locale, entry, values)
entry
end
def localize(locale, object, format = :default)
return nil if object.nil?
raise ArgumentError, "Object must be a Date, DateTime or Time object. #{object.inspect} given." unless object.respond_to?(:strftime)
type = object.respond_to?(:sec) ? 'time' : 'date'
formats = translate(locale, "#{type}.formats")
format = formats[format.to_sym] if formats && formats[format.to_sym]
format = format.to_s.dup
format.gsub!(/%a/, translate(locale, "date.abbr_day_names")[object.wday])
format.gsub!(/%A/, translate(locale, "date.day_names")[object.wday])
format.gsub!(/%b/, translate(locale, "date.abbr_month_names")[object.mon])
format.gsub!(/%B/, translate(locale, "date.month_names")[object.mon])
format.gsub!(/%p/, translate(locale, "time.#{object.hour < 12 ? :am : :pm}")) if object.respond_to? :hour
object.strftime(format)
end
end
end
end
I18n.backend = I18n::Backend::Moki.new
No comments:
Post a Comment