Module: Babylonia::ClassMethods
- Defined in:
- lib/babylonia/class_methods.rb
Overview
Class methods to extend a class with in order to make it able to handle translatable attributes
Instance Method Summary collapse
-
#build_babylonian_tower_on(*fields) ⇒ Object
Main class method ob Babylonia.
-
#handled_babylonian_fields ⇒ Object
Store all handled fields in a class instance variable.
Instance Method Details
#build_babylonian_tower_on(*fields) ⇒ Object
Main class method ob Babylonia. Use to make attributes translatable
36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 |
# File 'lib/babylonia/class_methods.rb', line 36 def build_babylonian_tower_on(*fields) = fields.last.is_a?(Hash) ? fields.pop : {} add_to_handled_babylonian_fields fields [:locale] ||= lambda { |r, f| I18n.locale } [:default_locale] ||= lambda { |r, f| I18n.default_locale } [:available_locales] ||= lambda { |r, f| I18n.available_locales } [:fallback] = true if [:fallback].nil? fields.each do |field| instance_variable_set(:"@babylonian_options_for_#{field}", ) # Alias method chain the field to a translated value # @param [Symbol] locale Pass a locale to get the field translation in this specific locale # @return [String, NilClass] Either the string with the translation, the fallback, the placeholder or nil # @example Call a field in italian # your_instance.field(:it) #=> "Translation" # define_method :"#{field}_translated" do |locale=nil| field_hash = send(:"#{field}_hash") translation = field_hash[locale || evaluate_babylonian_option!(:locale, field)] translation = field_hash[evaluate_babylonian_option!(:default_locale, field)] if (translation.nil? or translation.empty?) and evaluate_babylonian_option!(:fallback, field) (translation.nil? or translation.empty?) ? evaluate_babylonian_option!(:placeholder, field) : translation end alias_method :"#{field}_raw", field alias_method field, :"#{field}_translated" # Return the translated values as a hash # @return [Hash] The hash with all the translations stored in the field # define_method :"#{field}_hash" do field_content = send(:"#{field}_raw") field_content.is_a?(String) ? YAML.load(field_content) : {} end # Return all the languages stored # @return [Array] An array containing all languages stored in the field # define_method :"#{field}_languages" do send(:"#{field}_hash").keys end define_method :has_translated_attribute? do |attr| self.class.handled_babylonian_fields.include?(attr.to_sym) end # Return if a translation in the language is stored for the field # @return [Boolean] True if a translation is stored # define_method :"#{field}_has_locale?" do |locale| send(:"#{field}_languages").include?(locale.to_sym) end # Return if a locale is theoretically available for the field # @return [Boolean] True if the language is available # define_method :"#{field}_has_available_locale?" do |locale| evaluate_babylonian_option!(:available_locales, field).include?(locale.to_sym) end # Set the field to a value. This either takes a string or a hash # If given a String, the current locale is set to this value # If given a Hash, the hash is merged into the current translation hash, and empty values are purged # @param [String, Hash] data The data to set either the current language translation or all translations to # @example Set the translation for the current locale # your_object.field = "TRANSLATION" # @example Set the translation and delete italian # your_object.field = {de: 'DEUTSCH', it: ''} # define_method :"#{field}_translated=" do |data| current_hash = send(:"#{field}_hash") if data.is_a?(String) current_hash.merge! evaluate_babylonian_option!(:locale, field) => data elsif data.is_a?(Hash) data.delete_if{|k,v| !send(:"#{field}_has_available_locale?", k) } current_hash.merge! data end send(:"#{field}_raw=", YAML.dump(current_hash.delete_if{|k,v| v.nil? || v.empty? })) end alias_method :"#{field}_raw=", :"#{field}=" alias_method :"#{field}=", :"#{field}_translated=" end # Define method missing to be able to access a language directly define_method :method_missing do |meth, *args, &block| if (m = meth.to_s.match(/\A([^_]+)_(\w+)(=)?\z/).to_a[1..3]) && has_translated_attribute?(m[0]) && send(:"#{m[0]}_has_available_locale?", m[1]) send(m[0] + m[2].to_s, m[2] ? {m[1].to_sym => args.first} : m[1].to_sym) else super(meth, *args, &block) end end define_method :evaluate_babylonian_option! do |option, field, recursion=false| = self.class.instance_variable_get :"@babylonian_options_for_#{field}" o = [option] if o.is_a?(Proc) o.call self, field elsif o.is_a?(Symbol) && (recursion || !evaluate_babylonian_option!(:available_locales, field, true).include?(o)) send o else o end end end |
#handled_babylonian_fields ⇒ Object
Store all handled fields in a class instance variable
24 25 26 |
# File 'lib/babylonia/class_methods.rb', line 24 def handled_babylonian_fields instance_variable_get(:@handled_babylonian_fields) || instance_variable_set(:@handled_babylonian_fields, []) end |