mobility 0.5.1 → 0.6.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- checksums.yaml +4 -4
- checksums.yaml.gz.sig +2 -2
- data.tar.gz.sig +0 -0
- data/CHANGELOG.md +41 -1
- data/Gemfile.lock +3 -58
- data/README.md +22 -21
- data/lib/mobility.rb +3 -2
- data/lib/mobility/accumulator.rb +1 -2
- data/lib/mobility/active_model/backend_resetter.rb +1 -1
- data/lib/mobility/active_record.rb +12 -9
- data/lib/mobility/active_record/backend_resetter.rb +6 -7
- data/lib/mobility/active_record/uniqueness_validator.rb +12 -2
- data/lib/mobility/adapter.rb +1 -0
- data/lib/mobility/attributes.rb +3 -13
- data/lib/mobility/backends/active_record/column.rb +1 -0
- data/lib/mobility/backends/active_record/column/query_methods.rb +25 -20
- data/lib/mobility/backends/active_record/container/json_query_methods.rb +22 -16
- data/lib/mobility/backends/active_record/container/jsonb_query_methods.rb +19 -19
- data/lib/mobility/backends/active_record/hstore.rb +14 -12
- data/lib/mobility/backends/active_record/hstore/query_methods.rb +14 -5
- data/lib/mobility/backends/active_record/json.rb +21 -19
- data/lib/mobility/backends/active_record/json/query_methods.rb +16 -11
- data/lib/mobility/backends/active_record/jsonb.rb +21 -19
- data/lib/mobility/backends/active_record/jsonb/query_methods.rb +14 -5
- data/lib/mobility/backends/active_record/key_value.rb +9 -9
- data/lib/mobility/backends/active_record/key_value/query_methods.rb +53 -46
- data/lib/mobility/backends/active_record/pg_hash.rb +29 -25
- data/lib/mobility/backends/active_record/pg_query_methods.rb +76 -40
- data/lib/mobility/backends/active_record/query_methods.rb +17 -10
- data/lib/mobility/backends/active_record/serialized.rb +4 -2
- data/lib/mobility/backends/active_record/serialized/query_methods.rb +18 -15
- data/lib/mobility/backends/active_record/table.rb +21 -12
- data/lib/mobility/backends/active_record/table/query_methods.rb +82 -83
- data/lib/mobility/backends/hash_valued.rb +19 -0
- data/lib/mobility/backends/hstore.rb +3 -1
- data/lib/mobility/backends/json.rb +3 -1
- data/lib/mobility/backends/jsonb.rb +3 -1
- data/lib/mobility/backends/key_value.rb +32 -15
- data/lib/mobility/backends/sequel/column/query_methods.rb +16 -12
- data/lib/mobility/backends/sequel/container/json_query_methods.rb +25 -18
- data/lib/mobility/backends/sequel/container/jsonb_query_methods.rb +25 -18
- data/lib/mobility/backends/sequel/hstore.rb +14 -12
- data/lib/mobility/backends/sequel/hstore/query_methods.rb +18 -11
- data/lib/mobility/backends/sequel/json.rb +21 -19
- data/lib/mobility/backends/sequel/json/query_methods.rb +18 -11
- data/lib/mobility/backends/sequel/jsonb.rb +21 -19
- data/lib/mobility/backends/sequel/jsonb/query_methods.rb +18 -11
- data/lib/mobility/backends/sequel/key_value.rb +10 -11
- data/lib/mobility/backends/sequel/key_value/query_methods.rb +39 -34
- data/lib/mobility/backends/sequel/pg_hash.rb +37 -25
- data/lib/mobility/backends/sequel/pg_query_methods.rb +45 -20
- data/lib/mobility/backends/sequel/query_methods.rb +5 -0
- data/lib/mobility/backends/sequel/serialized.rb +18 -13
- data/lib/mobility/backends/sequel/serialized/query_methods.rb +10 -7
- data/lib/mobility/backends/sequel/table.rb +1 -1
- data/lib/mobility/backends/sequel/table/query_methods.rb +40 -35
- data/lib/mobility/plugins/cache/translation_cacher.rb +15 -15
- data/lib/mobility/plugins/default.rb +0 -7
- data/lib/mobility/plugins/fallbacks.rb +4 -0
- data/lib/mobility/sequel.rb +11 -5
- data/lib/mobility/sequel/backend_resetter.rb +6 -7
- data/lib/mobility/sequel/column_changes.rb +4 -4
- data/lib/mobility/version.rb +1 -1
- data/lib/rails/generators/mobility/backend_generators/base.rb +4 -0
- data/lib/rails/generators/mobility/backend_generators/table_backend.rb +0 -12
- data/lib/rails/generators/mobility/templates/column_translations.rb +2 -2
- data/lib/rails/generators/mobility/templates/create_string_translations.rb +5 -5
- data/lib/rails/generators/mobility/templates/create_text_translations.rb +5 -5
- data/lib/rails/generators/mobility/templates/initializer.rb +8 -0
- data/lib/rails/generators/mobility/templates/table_migration.rb +2 -3
- data/lib/rails/generators/mobility/templates/table_translations.rb +3 -4
- data/lib/rails/generators/mobility/translations_generator.rb +6 -5
- metadata +2 -3
- metadata.gz.sig +0 -0
- data/lib/mobility/backend/stringify_locale.rb +0 -18
@@ -12,6 +12,7 @@ Implements the {Mobility::Backends::KeyValue} backend for ActiveRecord models.
|
|
12
12
|
|
13
13
|
@example
|
14
14
|
class Post < ActiveRecord::Base
|
15
|
+
extend Mobility
|
15
16
|
translates :title, backend: :key_value, association_name: :translations, type: :string
|
16
17
|
end
|
17
18
|
|
@@ -31,17 +32,16 @@ Implements the {Mobility::Backends::KeyValue} backend for ActiveRecord models.
|
|
31
32
|
require 'mobility/backends/active_record/key_value/query_methods'
|
32
33
|
|
33
34
|
# @!group Backend Configuration
|
34
|
-
# @option
|
35
|
-
# @
|
36
|
-
# @option options [String,Class] class_name ({Mobility::ActiveRecord::TextTranslation}) Translation class
|
37
|
-
# @raise [ArgumentError] if type is not either :text or :string
|
35
|
+
# @option (see Mobility::Backends::KeyValue::ClassMethods#configure)
|
36
|
+
# @raise (see Mobility::Backends::KeyValue::ClassMethods#configure)
|
38
37
|
def self.configure(options)
|
39
38
|
super
|
40
|
-
type = options[:type]
|
41
|
-
|
42
|
-
|
43
|
-
|
44
|
-
|
39
|
+
if type = options[:type]
|
40
|
+
options[:association_name] ||= :"#{options[:type]}_translations"
|
41
|
+
options[:class_name] ||= Mobility::ActiveRecord.const_get("#{type.capitalize}Translation")
|
42
|
+
end
|
43
|
+
rescue NameError
|
44
|
+
raise ArgumentError, "You must define a Mobility::ActiveRecord::#{type.capitalize}Translation class."
|
45
45
|
end
|
46
46
|
# @!endgroup
|
47
47
|
|
@@ -3,67 +3,74 @@ require "mobility/backends/active_record/query_methods"
|
|
3
3
|
|
4
4
|
module Mobility
|
5
5
|
module Backends
|
6
|
-
|
7
|
-
|
8
|
-
|
9
|
-
|
6
|
+
module ActiveRecord
|
7
|
+
class KeyValue::QueryMethods < QueryMethods
|
8
|
+
def initialize(attributes, association_name: nil, class_name: nil, **)
|
9
|
+
super
|
10
|
+
@association_name = association_name
|
10
11
|
|
11
|
-
|
12
|
-
|
13
|
-
|
12
|
+
define_join_method(association_name, class_name)
|
13
|
+
define_query_methods(association_name)
|
14
|
+
end
|
14
15
|
|
15
|
-
|
16
|
-
|
17
|
-
|
18
|
-
|
16
|
+
def extended(relation)
|
17
|
+
super
|
18
|
+
association_name = @association_name
|
19
|
+
q = self
|
19
20
|
|
20
|
-
|
21
|
-
|
22
|
-
|
23
|
-
|
24
|
-
|
25
|
-
|
26
|
-
|
27
|
-
|
21
|
+
mod = Module.new do
|
22
|
+
define_method :not do |opts, *rest|
|
23
|
+
if i18n_keys = q.extract_attributes(opts)
|
24
|
+
opts = opts.with_indifferent_access
|
25
|
+
i18n_keys.each do |attr|
|
26
|
+
opts["#{attr}_#{association_name}"] = { value: q.collapse(opts.delete(attr)) }
|
27
|
+
end
|
28
|
+
super(opts, *rest).send(:"join_#{association_name}", *i18n_keys)
|
29
|
+
else
|
30
|
+
super(opts, *rest)
|
31
|
+
end
|
28
32
|
end
|
29
33
|
end
|
34
|
+
relation.mobility_where_chain.include(mod)
|
30
35
|
end
|
31
|
-
relation.mobility_where_chain.include(mod)
|
32
|
-
end
|
33
36
|
|
34
|
-
|
37
|
+
private
|
35
38
|
|
36
|
-
|
37
|
-
|
38
|
-
|
39
|
-
|
40
|
-
|
41
|
-
|
42
|
-
|
43
|
-
|
44
|
-
|
45
|
-
|
46
|
-
|
39
|
+
def define_join_method(association_name, translation_class)
|
40
|
+
define_method :"join_#{association_name}" do |*attributes, **options|
|
41
|
+
attributes.inject(self) do |relation, attribute|
|
42
|
+
t = translation_class.arel_table.alias("#{attribute}_#{association_name}")
|
43
|
+
m = arel_table
|
44
|
+
join_type = options[:outer_join] ? Arel::Nodes::OuterJoin : Arel::Nodes::InnerJoin
|
45
|
+
relation.joins(m.join(t, join_type).
|
46
|
+
on(t[:key].eq(attribute).
|
47
|
+
and(t[:locale].eq(Mobility.locale).
|
48
|
+
and(t[:translatable_type].eq(base_class.name).
|
49
|
+
and(t[:translatable_id].eq(m[:id]))))).join_sources)
|
50
|
+
end
|
47
51
|
end
|
48
52
|
end
|
49
|
-
end
|
50
53
|
|
51
|
-
|
52
|
-
|
54
|
+
def define_query_methods(association_name)
|
55
|
+
q = self
|
53
56
|
|
54
|
-
|
55
|
-
|
56
|
-
|
57
|
-
|
58
|
-
|
59
|
-
|
60
|
-
|
61
|
-
|
62
|
-
|
63
|
-
|
57
|
+
define_method :where! do |opts, *rest|
|
58
|
+
if i18n_keys = q.extract_attributes(opts)
|
59
|
+
opts = opts.with_indifferent_access
|
60
|
+
i18n_nulls = i18n_keys.reject { |key| opts[key] && [*opts[key]].all? }
|
61
|
+
i18n_keys.each do |attr|
|
62
|
+
opts["#{attr}_#{association_name}"] = { value: q.collapse(opts.delete(attr)) }
|
63
|
+
end
|
64
|
+
super(opts, *rest).
|
65
|
+
send("join_#{association_name}", *(i18n_keys - i18n_nulls)).
|
66
|
+
send("join_#{association_name}", *i18n_nulls, outer_join: true)
|
67
|
+
else
|
68
|
+
super(opts, *rest)
|
69
|
+
end
|
64
70
|
end
|
65
71
|
end
|
66
72
|
end
|
73
|
+
KeyValue.private_constant :QueryMethods
|
67
74
|
end
|
68
75
|
end
|
69
76
|
end
|
@@ -10,39 +10,43 @@ Internal class used by ActiveRecord backends backed by a Postgres data type
|
|
10
10
|
(hstore, jsonb).
|
11
11
|
|
12
12
|
=end
|
13
|
-
|
14
|
-
|
15
|
-
|
16
|
-
|
17
|
-
|
18
|
-
|
19
|
-
|
20
|
-
|
13
|
+
module ActiveRecord
|
14
|
+
class PgHash
|
15
|
+
include ActiveRecord
|
16
|
+
include HashValued
|
17
|
+
|
18
|
+
# @!macro backend_iterator
|
19
|
+
def each_locale
|
20
|
+
super { |l| yield l.to_sym }
|
21
|
+
end
|
21
22
|
|
22
|
-
|
23
|
-
|
24
|
-
|
23
|
+
def translations
|
24
|
+
model.read_attribute(column_name)
|
25
|
+
end
|
25
26
|
|
26
|
-
|
27
|
-
|
28
|
-
|
27
|
+
setup do |attributes, options = {}|
|
28
|
+
affix = "#{options[:column_prefix]}%s#{options[:column_suffix]}"
|
29
|
+
attributes.each { |attribute| store (affix % attribute), coder: Coder }
|
30
|
+
end
|
29
31
|
|
30
|
-
|
31
|
-
|
32
|
-
|
33
|
-
|
34
|
-
|
35
|
-
|
32
|
+
class Coder
|
33
|
+
def self.dump(obj)
|
34
|
+
if obj.is_a? Hash
|
35
|
+
obj.inject({}) do |translations, (locale, value)|
|
36
|
+
translations[locale] = value if value.present?
|
37
|
+
translations
|
38
|
+
end
|
39
|
+
else
|
40
|
+
raise ArgumentError, "Attribute is supposed to be a Hash, but was a #{obj.class}. -- #{obj.inspect}"
|
36
41
|
end
|
37
|
-
else
|
38
|
-
raise ArgumentError, "Attribute is supposed to be a Hash, but was a #{obj.class}. -- #{obj.inspect}"
|
39
42
|
end
|
40
|
-
end
|
41
43
|
|
42
|
-
|
43
|
-
|
44
|
+
def self.load(obj)
|
45
|
+
obj
|
46
|
+
end
|
44
47
|
end
|
45
48
|
end
|
49
|
+
private_constant :PgHash
|
46
50
|
end
|
47
51
|
end
|
48
52
|
end
|
@@ -1,11 +1,23 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
1
3
|
module Mobility
|
2
4
|
module Backends
|
3
5
|
module ActiveRecord
|
4
6
|
=begin
|
5
7
|
|
6
|
-
|
7
|
-
|
8
|
-
|
8
|
+
Internal module builder defining query methods for Postgres backends. Including
|
9
|
+
class must define the following methods:
|
10
|
+
|
11
|
+
- a method +matches+ which takes an attribute, and a locale to match, and
|
12
|
+
returns an Arel node which is used to check that the attribute has the
|
13
|
+
specified value in the specified locale
|
14
|
+
- a method +exists+ which takes an attribute and a locale and
|
15
|
+
returns an Arel node checking that a value exists for the attribute in the
|
16
|
+
specified locale
|
17
|
+
- a method +quote+ which quotes the value to be matched
|
18
|
+
- an optional method +absent+ which takes an attribute and a locale and returns
|
19
|
+
an Arel node checking that the value for the attribute does not exist in the
|
20
|
+
specified locale. Defaults to +exists(key, locale).not+.
|
9
21
|
|
10
22
|
This module avoids a lot of duplication between hstore/json/jsonb/container
|
11
23
|
backend querying code.
|
@@ -18,18 +30,19 @@ backend querying code.
|
|
18
30
|
|
19
31
|
=end
|
20
32
|
module PgQueryMethods
|
21
|
-
attr_reader :arel_table
|
33
|
+
attr_reader :arel_table, :column_affix
|
22
34
|
|
23
35
|
def initialize(attributes, options)
|
24
36
|
super
|
25
|
-
@arel_table
|
37
|
+
@arel_table = options[:model_class].arel_table
|
38
|
+
@column_affix = "#{options[:column_prefix]}%s#{options[:column_suffix]}"
|
26
39
|
|
27
40
|
q = self
|
28
41
|
|
29
42
|
define_method :where! do |opts, *rest|
|
30
43
|
if i18n_keys = q.extract_attributes(opts)
|
31
44
|
opts = opts.with_indifferent_access
|
32
|
-
query = q.
|
45
|
+
query = q.create_query!(opts, i18n_keys)
|
33
46
|
|
34
47
|
opts.empty? ? super(query) : super(opts, *rest).where(query)
|
35
48
|
else
|
@@ -46,7 +59,7 @@ backend querying code.
|
|
46
59
|
define_method :not do |opts, *rest|
|
47
60
|
if i18n_keys = q.extract_attributes(opts)
|
48
61
|
opts = opts.with_indifferent_access
|
49
|
-
query = q.
|
62
|
+
query = q.create_query!(opts, i18n_keys, inverse: true)
|
50
63
|
|
51
64
|
super(opts, *rest).where(query)
|
52
65
|
else
|
@@ -57,62 +70,85 @@ backend querying code.
|
|
57
70
|
relation.mobility_where_chain.include(mod)
|
58
71
|
end
|
59
72
|
|
60
|
-
# Create +where+ query for
|
61
|
-
# @note This is a destructive operation, it will modify +opts+.
|
73
|
+
# Create +where+ query for specified key and value
|
62
74
|
#
|
75
|
+
# @note This is a destructive operation, it will modify +opts+.
|
63
76
|
# @param [Hash] opts Hash of attribute/value pairs
|
64
77
|
# @param [Array] keys Translated attribute names
|
78
|
+
# @option [Boolean] inverse (false) If true, create a +not+ query
|
79
|
+
# instead of a +where+ query
|
65
80
|
# @return [Arel::Node] Arel node to pass to +where+
|
66
|
-
def
|
67
|
-
locale = Mobility.locale
|
81
|
+
def create_query!(opts, keys, inverse: false)
|
68
82
|
keys.map { |key|
|
69
|
-
values = opts.delete(key)
|
70
|
-
|
71
|
-
next has_locale(key, locale).not if values.nil?
|
72
|
-
|
73
|
-
Array.wrap(values).map { |value|
|
74
|
-
value.nil? ?
|
75
|
-
has_locale(key, locale).not :
|
76
|
-
matches(key, value, locale)
|
77
|
-
}.inject(&:or)
|
83
|
+
values = Array.wrap(opts.delete(key)).uniq
|
84
|
+
send(inverse ? :not_query : :where_query, key, values, Mobility.locale)
|
78
85
|
}.inject(&:and)
|
79
86
|
end
|
80
87
|
|
81
|
-
|
82
|
-
|
83
|
-
#
|
84
|
-
# @param [Hash] opts Hash of attribute/value pairs
|
85
|
-
# @param [Array] keys Translated attribute names
|
86
|
-
# @return [Arel::Node] Arel node to pass to +where+
|
87
|
-
def create_not_query!(opts, keys)
|
88
|
-
locale = Mobility.locale
|
89
|
-
keys.map { |key|
|
90
|
-
values = opts.delete(key)
|
91
|
-
|
92
|
-
Array.wrap(values).map { |value|
|
93
|
-
matches(key, value, locale).not
|
94
|
-
}.inject(has_locale(key, locale), &:and)
|
95
|
-
}.inject(&:and)
|
88
|
+
def matches(_key, _locale)
|
89
|
+
raise NotImplementedError
|
96
90
|
end
|
97
91
|
|
98
|
-
|
92
|
+
def exists(_key, _locale)
|
93
|
+
raise NotImplementedError
|
94
|
+
end
|
99
95
|
|
100
|
-
def
|
96
|
+
def quote(_value)
|
101
97
|
raise NotImplementedError
|
102
98
|
end
|
103
99
|
|
104
|
-
def
|
105
|
-
|
100
|
+
def absent(key, locale)
|
101
|
+
exists(key, locale).not
|
106
102
|
end
|
107
103
|
|
104
|
+
private
|
105
|
+
|
108
106
|
def build_infix(*args)
|
109
107
|
arel_table.grouping(Arel::Nodes::InfixOperation.new(*args))
|
110
108
|
end
|
111
109
|
|
112
|
-
def
|
110
|
+
def build_quoted(value)
|
113
111
|
Arel::Nodes.build_quoted(value.to_s)
|
114
112
|
end
|
113
|
+
|
114
|
+
def column_name(attribute)
|
115
|
+
column_affix % attribute
|
116
|
+
end
|
117
|
+
|
118
|
+
# Create +where+ query for specified key and values
|
119
|
+
#
|
120
|
+
# @param [String] key Translated attribute name
|
121
|
+
# @param [Array] values Values to match
|
122
|
+
# @param [Symbol] locale Locale to query for
|
123
|
+
# @return [Arel::Node] Arel node to pass to +where+
|
124
|
+
def where_query(key, values, locale)
|
125
|
+
nils, vals = values.partition(&:nil?)
|
126
|
+
|
127
|
+
return absent(key, locale) if vals.empty?
|
128
|
+
|
129
|
+
node = matches(key, locale)
|
130
|
+
vals = vals.map(&method(:quote))
|
131
|
+
|
132
|
+
query = vals.size == 1 ? node.eq(vals.first) : node.in(vals)
|
133
|
+
query = query.or(absent(key, locale)) unless nils.empty?
|
134
|
+
query
|
135
|
+
end
|
136
|
+
|
137
|
+
# Create +not+ query for specified key and values
|
138
|
+
#
|
139
|
+
# @param [String] key Translated attribute name
|
140
|
+
# @param [Array] values Values to match
|
141
|
+
# @param [Symbol] locale Locale to query for
|
142
|
+
# @return [Arel::Node] Arel node to pass to +where+
|
143
|
+
def not_query(key, values, locale)
|
144
|
+
vals = values.map(&method(:quote))
|
145
|
+
node = matches(key, locale)
|
146
|
+
|
147
|
+
query = vals.size == 1 ? node.eq(vals.first) : node.in(vals)
|
148
|
+
query.not.and(exists(key, locale))
|
149
|
+
end
|
115
150
|
end
|
151
|
+
private_constant :PgQueryMethods
|
116
152
|
end
|
117
153
|
end
|
118
154
|
end
|
@@ -21,23 +21,30 @@ models. For details see backend-specific subclasses.
|
|
21
21
|
|
22
22
|
# @param [ActiveRecord::Relation] relation Relation being extended
|
23
23
|
# @note Only want to define this once, even if multiple QueryMethods
|
24
|
-
# modules are included, so
|
24
|
+
# modules are included, so include it here into the singleton class.
|
25
25
|
def extended(relation)
|
26
|
-
|
27
|
-
relation.define_singleton_method(:mobility_where_chain) do
|
28
|
-
@mobility_where_chain ||= Class.new(::ActiveRecord::QueryMethods::WhereChain)
|
29
|
-
end
|
30
|
-
|
31
|
-
relation.define_singleton_method :where do |opts = :chain, *rest|
|
32
|
-
opts == :chain ? mobility_where_chain.new(spawn) : super(opts, *rest)
|
33
|
-
end
|
34
|
-
end
|
26
|
+
relation.singleton_class.include WhereChainable
|
35
27
|
end
|
36
28
|
|
37
29
|
def extract_attributes(opts)
|
38
30
|
opts.is_a?(Hash) && (opts.keys.map(&:to_s) & @attributes).presence
|
39
31
|
end
|
32
|
+
|
33
|
+
def collapse(value)
|
34
|
+
value.is_a?(Array) ? value.uniq : value
|
35
|
+
end
|
36
|
+
end
|
37
|
+
|
38
|
+
module WhereChainable
|
39
|
+
def where(opts = :chain, *rest)
|
40
|
+
opts == :chain ? mobility_where_chain.new(spawn) : super
|
41
|
+
end
|
42
|
+
|
43
|
+
def mobility_where_chain
|
44
|
+
@mobility_where_chain ||= Class.new(::ActiveRecord::QueryMethods::WhereChain)
|
45
|
+
end
|
40
46
|
end
|
47
|
+
private_constant :QueryMethods, :WhereChainable
|
41
48
|
end
|
42
49
|
end
|
43
50
|
end
|
@@ -11,6 +11,7 @@ Implements {Mobility::Backends::Serialized} backend for ActiveRecord models.
|
|
11
11
|
|
12
12
|
@example Define attribute with serialized backend
|
13
13
|
class Post < ActiveRecord::Base
|
14
|
+
extend Mobility
|
14
15
|
translates :title, backend: :serialized, format: :yaml
|
15
16
|
end
|
16
17
|
|
@@ -42,7 +43,8 @@ Implements {Mobility::Backends::Serialized} backend for ActiveRecord models.
|
|
42
43
|
|
43
44
|
setup do |attributes, options|
|
44
45
|
coder = { yaml: YAMLCoder, json: JSONCoder }[options[:format]]
|
45
|
-
|
46
|
+
column_affix = "#{options[:column_prefix]}%s#{options[:column_suffix]}"
|
47
|
+
attributes.each { |attribute| serialize (column_affix % attribute), coder }
|
46
48
|
end
|
47
49
|
|
48
50
|
setup_query_methods(QueryMethods)
|
@@ -51,7 +53,7 @@ Implements {Mobility::Backends::Serialized} backend for ActiveRecord models.
|
|
51
53
|
# Returns column value as a hash
|
52
54
|
# @return [Hash]
|
53
55
|
def translations
|
54
|
-
model.read_attribute(
|
56
|
+
model.read_attribute(column_name)
|
55
57
|
end
|
56
58
|
|
57
59
|
%w[yaml json].each do |format|
|