# Locale Fallbacks## Extends the I18n module to hold a fallbacks instance which is set to an# instance of I18n::Locale::Fallbacks by default but can be swapped with a# different implementation.## Locale fallbacks will compute a number of fallback locales for a given locale.# For example:## <pre><code># I18n.fallbacks[:"es-MX"] # => [:"es-MX", :es, :en] </code></pre>## Locale fallbacks always fall back to## * all parent locales of a given locale (e.g. :es for :"es-MX") first,# * the current default locales and all of their parents second## The default locales are set to [] by default but can be set to something else.## One can additionally add any number of additional fallback locales manually.# These will be added before the default locales to the fallback chain. For# example:## # using a custom locale as default fallback locale## I18n.fallbacks = I18n::Locale::Fallbacks.new(:"en-GB", :"de-AT" => :de, :"de-CH" => :de)# I18n.fallbacks[:"de-AT"] # => [:"de-AT", :de, :"en-GB", :en]# I18n.fallbacks[:"de-CH"] # => [:"de-CH", :de, :"en-GB", :en]## # mapping fallbacks to an existing instance## # people speaking Catalan also speak Spanish as spoken in Spain# fallbacks = I18n.fallbacks# fallbacks.map(:ca => :"es-ES")# fallbacks[:ca] # => [:ca, :"es-ES", :es, :"en-US", :en]## # people speaking Arabian as spoken in Palestine also speak Hebrew as spoken in Israel# fallbacks.map(:"ar-PS" => :"he-IL")# fallbacks[:"ar-PS"] # => [:"ar-PS", :ar, :"he-IL", :he, :"en-US", :en]# fallbacks[:"ar-EG"] # => [:"ar-EG", :ar, :"en-US", :en]## # people speaking Sami as spoken in Finland also speak Swedish and Finnish as spoken in Finland# fallbacks.map(:sms => [:"se-FI", :"fi-FI"])# fallbacks[:sms] # => [:sms, :"se-FI", :se, :"fi-FI", :fi, :"en-US", :en]moduleI18nmoduleLocaleclassFallbacks<Hashdefinitialize(*mappings)@map={}map(mappings.pop)ifmappings.last.is_a?(Hash)self.defaults=mappings.empty??[]:mappingsenddefdefaults=(defaults)@defaults=defaults.flat_map{|default|compute(default,false)}endattr_reader:defaultsdef[](locale)raiseInvalidLocale.new(locale)iflocale.nil?raiseDisabled.new('fallback#[]')iflocale==falselocale=locale.to_symsuper||store(locale,compute(locale))enddefmap(*args,&block)ifargs.count==1&&!block_given?mappings=args.firstmappings.eachdo|from,to|from,to=from.to_sym,Array(to)to.eachdo|_to|@map[from]||=[]@map[from]<<_to.to_symendendelse@map.map(*args,&block)endenddefempty?@map.empty?&&@defaults.empty?enddefinspect"#<#{self.class.name} @map=#{@map.inspect} @defaults=#{@defaults.inspect}>"endprotecteddefcompute(tags,include_defaults=true,exclude=[])result=[]Array(tags).eachdo|tag|tags=I18n::Locale::Tag.tag(tag).self_and_parents.map!{|t|t.to_sym}-excluderesult+=tagstags.each{|_tag|result+=compute(@map[_tag],false,exclude+result)if@map[_tag]}endresult.push(*defaults)ifinclude_defaultsresult.uniq!result.compact!resultendendendend