Skip to content

Instantly share code, notes, and snippets.

@yaroslav
Created August 30, 2008 14:53
Show Gist options
  • Save yaroslav/8116 to your computer and use it in GitHub Desktop.
Save yaroslav/8116 to your computer and use it in GitHub Desktop.
Ruby i18n: SimpleBackend support for CLDR-style "standalone" and "format" monthnames and daynames
LOCALIZE_ABBR_MONTH_NAMES_MATCH = /(%d|%e)?(\s*)(%b)/
LOCALIZE_MONTH_NAMES_MATCH = /(%d|%e)?(\s*)(%B)/
LOCALIZE_STANDALONE_ABBR_DAY_NAMES_MATCH = /^%a/
LOCALIZE_STANDALONE_DAY_NAMES_MATCH = /^%A/
# Acts the same as +strftime+, but returns a localized version of the
# formatted date string. Takes a key from the date/time formats
# translations as a format argument (<em>e.g.</em>, <tt>:short</tt> in <tt>:'date.formats'</tt>).
def localize(locale, object, format = :default)
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'
# TODO only translate these if format is a String?
formats = translate(locale, :"#{type}.formats")
format = formats[format.to_sym] if formats && formats[format.to_sym]
# TODO raise exception unless format found?
format = format.to_s.dup
# TODO only translate these if the format string is actually present
# TODO check which format strings are present, then bulk translate then, then replace them
if lookup(locale, :"date.standalone_abbr_day_names")
format.gsub!(LOCALIZE_STANDALONE_ABBR_DAY_NAMES_MATCH, translate(locale, :"date.standalone_abbr_day_names")[object.wday])
end
format.gsub!(/%a/, translate(locale, :"date.abbr_day_names")[object.wday])
if lookup(locale, :"date.standalone_day_names")
format.gsub!(LOCALIZE_STANDALONE_DAY_NAMES_MATCH, translate(locale, :"date.standalone_day_names")[object.wday])
end
format.gsub!(/%A/, translate(locale, :"date.day_names")[object.wday])
if lookup(locale, :"date.standalone_abbr_month_names")
format.gsub!(LOCALIZE_ABBR_MONTH_NAMES_MATCH) do
$1 ? $1 + $2 + translate(locale, :"date.abbr_month_names")[object.mon] : $2 + translate(locale, :"date.standalone_abbr_month_names")[object.mon]
end
else
format.gsub!(/%b/, translate(locale, :"date.abbr_month_names")[object.mon])
end
if lookup(locale, :"date.standalone_month_names")
format.gsub!(LOCALIZE_MONTH_NAMES_MATCH) do
$1 ? $1 + $2 + translate(locale, :"date.month_names")[object.mon] : $2 + translate(locale, :"date.standalone_month_names")[object.mon]
end
else
format.gsub!(/%B/, translate(locale, :"date.month_names")[object.mon])
end
format.gsub!(/%p/, translate(locale, :"time.#{object.hour < 12 ? :am : :pm}")) if object.respond_to? :hour
object.strftime(format)
end
@backend.store_translations :'ru-RU', {
:date => {
:formats => {
:default => "%d.%m.%Y",
:short => "%e %B",
:long => "%e %B %Y",
},
# format > abbreviated
:abbr_day_names => %w(Вс Пн Вт Ср Чт Пт Сб),
# format > wide
:day_names => %w(воскресенье понедельник вторник среда четверг пятница суббота),
# stand-alone > wide
:standalone_day_names => %w(Воскресенье Понедельник Вторник Среда Четверг Пятница Суббота),
# format > abbreviated
:abbr_month_names => %w(янв. февр. марта апр. мая июня июля авг. сент. окт. нояб. дек.).unshift(nil),
# format > wide
:month_names => %w(января февраля марта апреля мая июня июля августа сентября октября ноября декабря).unshift(nil),
# stand-alone > abbreviated
:standalone_abbr_month_names => %w(янв. февр. март апр. май июнь июль авг. сент. окт. нояб. дек.).unshift(nil),
# stand-alone > wide
:standalone_month_names => %w(Январь Февраль Март Апрель Май Июнь Июль Август Сентябрь Октябрь Ноябрь Декабрь).unshift(nil),
:order => [:day, :month, :year]
},
:time => {
:formats => {
:default => "%a, %d %b %Y %H:%M:%S %z",
:short => "%e %b %H:%M",
:long => "%d %B %Y %H:%M",
},
:am => 'утра',
:pm => 'вечера'
}
}
class I18nSimpleBackendLocalizeDateTest < Test::Unit::TestCase
include I18nSimpleBackendTestSetup
def setup
@backend = I18n::Backend::Simple.new
add_datetime_translations
@date = Date.new 2008, 1, 1
@date_march = Date.new 2008, 3, 1
end
def test_translate_uses_standalone_month_names
assert_equal 'Январь', @backend.localize('ru-RU', @date, '%B')
assert_equal '01 января', @backend.localize('ru-RU', @date, '%d %B')
assert_equal ' 1 января', @backend.localize('ru-RU', @date, '%e %B')
assert_equal 'Январь 2008', @backend.localize('ru-RU', @date, '%B %Y')
end
def test_translate_uses_standalone_abbr_month_names
assert_equal 'март', @backend.localize('ru-RU', @date_march, '%b')
assert_equal '01 марта', @backend.localize('ru-RU', @date_march, '%d %b')
assert_equal ' 1 марта', @backend.localize('ru-RU', @date_march, '%e %b')
assert_equal 'март 2008', @backend.localize('ru-RU', @date_march, '%b %Y')
end
def test_translate_uses_standalone_day_names
assert_equal 'Вторник', @backend.localize('ru-RU', @date, '%A')
assert_match /вторник/, @backend.localize('ru-RU', @date, '%d %b, %A')
assert_match /Вторник/, @backend.localize('ru-RU', @date, '%A, %d %b %Y')
end
end
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment