File: active_support/vendor/i18n-0.4.1/i18n/backend/flatten.rb

Overview
Module Structure
Code

Overview

Module Structure

  module: <Toplevel Module>
  module: I18n#1
  module: Backend#2
  module: Flatten#11
has properties
constant: SEPARATOR_ESCAPE_CHAR #12
constant: FLATTEN_SEPARATOR #13
module method: normalize_flat_keys (1/2) / 4 #18
module method: escape_default_separator (1/2) / 1 #33
method: normalize_flat_keys (2/E) / 4 #39
method: links #45
method: flatten_keys / 4 #54
method: flatten_translations / 4 #69
method: store_link / 3 #84
method: resolve_link / 2 #88
method: find_link / 2 #101
method: escape_default_separator (2/E) / 1 #107

Code

   1  module I18n
   2    module Backend
   3      # This module contains several helpers to assist flattening translations.
   4      # You may want to flatten translations for:
   5      #
   6      #   1) speed up lookups, as in the Memoize backend;
   7      #   2) In case you want to store translations in a data store, as in ActiveRecord backend;
   8      #
   9      # You can check both backends above for some examples.
  10      # This module also keeps all links in a hash so they can be properly resolved when flattened.
  11      module Flatten
  12        SEPARATOR_ESCAPE_CHAR = "\001"
  13        FLATTEN_SEPARATOR = "."
  14 
  15        # normalize_keys the flatten way. This method is significantly faster
  16        # and creates way less objects than the one at I18n.normalize_keys.
  17        # It also handles escaping the translation keys.
  18        def self.normalize_flat_keys(locale, key, scope, separator)
  19          keys = [scope, key].flatten.compact
  20          separator ||= I18n.default_separator
  21 
  22          if separator != FLATTEN_SEPARATOR
  23            keys.map! do |k|
  24              k.to_s.tr("#{FLATTEN_SEPARATOR}#{separator}",
  25                "#{SEPARATOR_ESCAPE_CHAR}#{FLATTEN_SEPARATOR}")
  26            end
  27          end
  28 
  29          keys.join(".")
  30        end
  31 
  32        # Receives a string and escape the default separator.
  33        def self.escape_default_separator(key) #:nodoc:
  34          key.to_s.tr(FLATTEN_SEPARATOR, SEPARATOR_ESCAPE_CHAR)
  35        end
  36 
  37        # Shortcut to I18n::Backend::Flatten.normalize_flat_keys
  38        # and then resolve_links.
  39        def normalize_flat_keys(locale, key, scope, separator)
  40          key = I18n::Backend::Flatten.normalize_flat_keys(locale, key, scope, separator)
  41          resolve_link(locale, key)
  42        end
  43 
  44        # Store flattened links.
  45        def links
  46          @links ||= Hash.new { |h,k| h[k] = {} }
  47        end
  48 
  49        # Flatten keys for nested Hashes by chaining up keys:
  50        #
  51        #   >> { "a" => { "b" => { "c" => "d", "e" => "f" }, "g" => "h" }, "i" => "j"}.wind
  52        #   => { "a.b.c" => "d", "a.b.e" => "f", "a.g" => "h", "i" => "j" }
  53        #
  54        def flatten_keys(hash, escape, prev_key=nil, &block)
  55          hash.each_pair do |key, value|
  56            key = escape_default_separator(key) if escape
  57            curr_key = [prev_key, key].compact.join(FLATTEN_SEPARATOR).to_sym
  58            yield curr_key, value
  59            flatten_keys(value, escape, curr_key, &block) if value.is_a?(Hash)
  60          end
  61        end
  62 
  63        # Receives a hash of translations (where the key is a locale and
  64        # the value is another hash) and return a hash with all
  65        # translations flattened.
  66        #
  67        # Nested hashes are included in the flattened hash just if subtree
  68        # is true and Symbols are automatically stored as links.
  69        def flatten_translations(locale, data, escape, subtree)
  70          hash = {}
  71          flatten_keys(data, escape) do |key, value|
  72            if value.is_a?(Hash)
  73              hash[key] = value if subtree
  74            else
  75              store_link(locale, key, value) if value.is_a?(Symbol)
  76              hash[key] = value
  77            end
  78          end
  79          hash
  80        end
  81 
  82        protected
  83 
  84          def store_link(locale, key, link)
  85            links[locale.to_sym][key.to_s] = link.to_s
  86          end
  87 
  88          def resolve_link(locale, key)
  89            key, locale = key.to_s, locale.to_sym
  90            links = self.links[locale]
  91 
  92            if links.key?(key)
  93              links[key]
  94            elsif link = find_link(locale, key)
  95              store_link(locale, key, key.gsub(*link))
  96            else
  97              key
  98            end
  99          end
 100 
 101          def find_link(locale, key) #:nodoc:
 102            links[locale].each do |from, to|
 103              return [from, to] if key[0, from.length] == from
 104            end && nil
 105          end
 106 
 107          def escape_default_separator(key) #:nodoc:
 108            I18n::Backend::Flatten.escape_default_separator(key)
 109          end
 110 
 111      end
 112    end
 113  en