mobility 0.1.20 → 0.2.0
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +4 -4
- checksums.yaml.gz.sig +0 -0
- data.tar.gz.sig +2 -0
- data/CHANGELOG.md +17 -0
- data/CONTRIBUTING.md +55 -0
- data/Gemfile +2 -0
- data/Gemfile.lock +2 -56
- data/README.md +64 -15
- data/Rakefile +17 -17
- data/lib/mobility.rb +43 -40
- data/lib/mobility/active_model.rb +0 -1
- data/lib/mobility/active_model/backend_resetter.rb +1 -1
- data/lib/mobility/active_record.rb +8 -15
- data/lib/mobility/active_record/backend_resetter.rb +2 -0
- data/lib/mobility/active_record/model_translation.rb +1 -1
- data/lib/mobility/active_record/string_translation.rb +2 -0
- data/lib/mobility/active_record/text_translation.rb +2 -0
- data/lib/mobility/attributes.rb +74 -71
- data/lib/mobility/backend.rb +64 -25
- data/lib/mobility/backend/orm_delegator.rb +17 -7
- data/lib/mobility/backend/stringify_locale.rb +18 -0
- data/lib/mobility/backend_resetter.rb +8 -5
- data/lib/mobility/backends.rb +4 -0
- data/lib/mobility/backends/active_record.rb +20 -0
- data/lib/mobility/{backend → backends}/active_record/column.rb +25 -13
- data/lib/mobility/{backend → backends}/active_record/column/query_methods.rb +5 -3
- data/lib/mobility/backends/active_record/hstore.rb +29 -0
- data/lib/mobility/{backend → backends}/active_record/hstore/query_methods.rb +2 -2
- data/lib/mobility/{backend → backends}/active_record/jsonb.rb +6 -6
- data/lib/mobility/{backend → backends}/active_record/jsonb/query_methods.rb +4 -2
- data/lib/mobility/{backend → backends}/active_record/key_value.rb +10 -44
- data/lib/mobility/{backend → backends}/active_record/key_value/query_methods.rb +4 -2
- data/lib/mobility/{backend/active_record/hash_valued.rb → backends/active_record/pg_hash.rb} +13 -21
- data/lib/mobility/{backend → backends}/active_record/query_methods.rb +2 -2
- data/lib/mobility/{backend → backends}/active_record/serialized.rb +12 -28
- data/lib/mobility/{backend → backends}/active_record/serialized/query_methods.rb +5 -8
- data/lib/mobility/{backend → backends}/active_record/table.rb +11 -60
- data/lib/mobility/{backend → backends}/active_record/table/query_methods.rb +5 -3
- data/lib/mobility/{backend → backends}/column.rb +8 -4
- data/lib/mobility/backends/hash_valued.rb +29 -0
- data/lib/mobility/{backend → backends}/hstore.rb +4 -4
- data/lib/mobility/{backend → backends}/jsonb.rb +4 -4
- data/lib/mobility/backends/key_value.rb +111 -0
- data/lib/mobility/{backend → backends}/null.rb +4 -4
- data/lib/mobility/backends/sequel.rb +20 -0
- data/lib/mobility/backends/sequel/column.rb +52 -0
- data/lib/mobility/{backend → backends}/sequel/column/query_methods.rb +5 -3
- data/lib/mobility/backends/sequel/hstore.rb +29 -0
- data/lib/mobility/{backend → backends}/sequel/hstore/query_methods.rb +4 -3
- data/lib/mobility/{backend → backends}/sequel/jsonb.rb +6 -6
- data/lib/mobility/{backend → backends}/sequel/jsonb/query_methods.rb +4 -3
- data/lib/mobility/{backend → backends}/sequel/key_value.rb +28 -39
- data/lib/mobility/{backend → backends}/sequel/key_value/query_methods.rb +4 -5
- data/lib/mobility/backends/sequel/pg_hash.rb +46 -0
- data/lib/mobility/{backend → backends}/sequel/postgres_query_methods.rb +1 -2
- data/lib/mobility/{backend → backends}/sequel/query_methods.rb +6 -4
- data/lib/mobility/{backend → backends}/sequel/serialized.rb +17 -38
- data/lib/mobility/backends/sequel/serialized/query_methods.rb +17 -0
- data/lib/mobility/{backend → backends}/sequel/table.rb +29 -60
- data/lib/mobility/{backend → backends}/sequel/table/query_methods.rb +5 -3
- data/lib/mobility/{backend → backends}/serialized.rb +27 -5
- data/lib/mobility/{backend → backends}/table.rb +69 -29
- data/lib/mobility/configuration.rb +40 -0
- data/lib/mobility/{orm.rb → loaded.rb} +0 -0
- data/lib/mobility/plugins.rb +35 -0
- data/lib/mobility/plugins/active_model.rb +6 -0
- data/lib/mobility/plugins/active_model/dirty.rb +81 -0
- data/lib/mobility/plugins/active_record.rb +6 -0
- data/lib/mobility/plugins/active_record/dirty.rb +59 -0
- data/lib/mobility/plugins/cache.rb +54 -0
- data/lib/mobility/plugins/cache/translation_cacher.rb +40 -0
- data/lib/mobility/plugins/default.rb +73 -0
- data/lib/mobility/plugins/dirty.rb +61 -0
- data/lib/mobility/{backend → plugins}/fallbacks.rb +36 -31
- data/lib/mobility/plugins/fallthrough_accessors.rb +66 -0
- data/lib/mobility/plugins/locale_accessors.rb +84 -0
- data/lib/mobility/{backend → plugins}/presence.rb +15 -6
- data/lib/mobility/plugins/sequel.rb +6 -0
- data/lib/mobility/plugins/sequel/dirty.rb +59 -0
- data/lib/mobility/sequel.rb +5 -14
- data/lib/mobility/sequel/backend_resetter.rb +4 -6
- data/lib/mobility/sequel/column_changes.rb +4 -4
- data/lib/mobility/sequel/model_translation.rb +1 -1
- data/lib/mobility/sequel/string_translation.rb +2 -0
- data/lib/mobility/sequel/text_translation.rb +2 -0
- data/lib/mobility/translates.rb +1 -5
- data/lib/mobility/util.rb +126 -0
- data/lib/mobility/version.rb +1 -1
- data/lib/mobility/wrapper.rb +1 -1
- data/lib/rails/generators/mobility/translations_generator.rb +7 -3
- metadata +85 -55
- metadata.gz.sig +0 -0
- data/lib/mobility/backend/active_model.rb +0 -7
- data/lib/mobility/backend/active_model/dirty.rb +0 -95
- data/lib/mobility/backend/active_record.rb +0 -29
- data/lib/mobility/backend/active_record/dirty.rb +0 -54
- data/lib/mobility/backend/active_record/hstore.rb +0 -29
- data/lib/mobility/backend/cache.rb +0 -117
- data/lib/mobility/backend/dirty.rb +0 -38
- data/lib/mobility/backend/key_value.rb +0 -85
- data/lib/mobility/backend/sequel.rb +0 -29
- data/lib/mobility/backend/sequel/column.rb +0 -39
- data/lib/mobility/backend/sequel/dirty.rb +0 -57
- data/lib/mobility/backend/sequel/hash_valued.rb +0 -51
- data/lib/mobility/backend/sequel/hstore.rb +0 -29
- data/lib/mobility/backend/sequel/serialized/query_methods.rb +0 -20
- data/lib/mobility/core_ext/object.rb +0 -30
- data/lib/mobility/core_ext/string.rb +0 -16
- data/lib/mobility/fallthrough_accessors.rb +0 -57
- data/lib/mobility/locale_accessors.rb +0 -55
metadata.gz.sig
ADDED
Binary file
|
@@ -1,95 +0,0 @@
|
|
1
|
-
module Mobility
|
2
|
-
module Backend
|
3
|
-
=begin
|
4
|
-
|
5
|
-
Dirty tracking for models which include the +ActiveModel::Dirty+ module.
|
6
|
-
|
7
|
-
Assuming we have an attribute +title+, this module will add support for the
|
8
|
-
following methods:
|
9
|
-
- +title_changed?+
|
10
|
-
- +title_change+
|
11
|
-
- +title_was+
|
12
|
-
- +title_will_change!+
|
13
|
-
- +title_previously_changed?+
|
14
|
-
- +title_previous_change+
|
15
|
-
- +restore_title!+
|
16
|
-
|
17
|
-
In addition, the private method +restore_attribute!+ will also restore the
|
18
|
-
value of the translated attribute if passed to it.
|
19
|
-
|
20
|
-
@see http://api.rubyonrails.org/classes/ActiveModel/Dirty.html Rails documentation for Active Model Dirty module
|
21
|
-
|
22
|
-
=end
|
23
|
-
module ActiveModel::Dirty
|
24
|
-
# @!group Backend Accessors
|
25
|
-
# @!macro backend_writer
|
26
|
-
# @param [Hash] options
|
27
|
-
def write(locale, value, **options)
|
28
|
-
locale_accessor = Mobility.normalize_locale_accessor(attribute, locale)
|
29
|
-
if model.changed_attributes.has_key?(locale_accessor) && model.changed_attributes[locale_accessor] == value
|
30
|
-
model.attributes_changed_by_setter.except!(locale_accessor)
|
31
|
-
elsif read(locale, options.merge(fallback: false)) != value
|
32
|
-
model.send(:attribute_will_change!, locale_accessor)
|
33
|
-
end
|
34
|
-
super
|
35
|
-
end
|
36
|
-
# @!endgroup
|
37
|
-
|
38
|
-
# @param [Class] backend_class Class of backend
|
39
|
-
def self.included(backend_class)
|
40
|
-
backend_class.extend(ClassMethods)
|
41
|
-
end
|
42
|
-
|
43
|
-
# Adds hook after {Backend::Setup#setup_model} to add dirty-tracking
|
44
|
-
# methods for translated attributes onto model class.
|
45
|
-
module ClassMethods
|
46
|
-
# (see Mobility::Backend::Setup#setup_model)
|
47
|
-
def setup_model(model_class, attributes, **options)
|
48
|
-
super
|
49
|
-
model_class.class_eval do
|
50
|
-
Mobility::Backend::ActiveModel::Dirty.method_suffixes.each do |suffix|
|
51
|
-
attributes.each do |attribute|
|
52
|
-
class_eval <<-EOM, __FILE__, __LINE__ + 1
|
53
|
-
def #{attribute}#{suffix}
|
54
|
-
attribute#{suffix}(Mobility.normalize_locale_accessor("#{attribute}"))
|
55
|
-
end
|
56
|
-
EOM
|
57
|
-
end
|
58
|
-
end
|
59
|
-
end
|
60
|
-
|
61
|
-
restore_methods = Module.new do
|
62
|
-
attributes.each do |attribute|
|
63
|
-
define_method "restore_#{attribute}!" do
|
64
|
-
locale_accessor = Mobility.normalize_locale_accessor(attribute)
|
65
|
-
if attribute_changed?(locale_accessor)
|
66
|
-
__send__("#{attribute}=", changed_attributes[locale_accessor])
|
67
|
-
end
|
68
|
-
end
|
69
|
-
end
|
70
|
-
|
71
|
-
define_method :restore_attribute! do |attr|
|
72
|
-
if attributes.include?(attr.to_s)
|
73
|
-
send("restore_#{attr}!")
|
74
|
-
else
|
75
|
-
super(attr)
|
76
|
-
end
|
77
|
-
end
|
78
|
-
private :restore_attribute!
|
79
|
-
end
|
80
|
-
model_class.include restore_methods
|
81
|
-
end
|
82
|
-
end
|
83
|
-
|
84
|
-
# Get method suffixes. Creating an object just to get the list of
|
85
|
-
# suffixes is not very efficient, but the most reliable way given that
|
86
|
-
# they change from Rails version to version.
|
87
|
-
def self.method_suffixes
|
88
|
-
@method_suffixes ||=
|
89
|
-
Class.new do
|
90
|
-
include ::ActiveModel::Dirty
|
91
|
-
end.attribute_method_matchers.map(&:suffix).select { |m| m =~ /\A_/ }
|
92
|
-
end
|
93
|
-
end
|
94
|
-
end
|
95
|
-
end
|
@@ -1,29 +0,0 @@
|
|
1
|
-
module Mobility
|
2
|
-
module Backend
|
3
|
-
module ActiveRecord
|
4
|
-
autoload :Column, 'mobility/backend/active_record/column'
|
5
|
-
autoload :Dirty, 'mobility/backend/active_record/dirty'
|
6
|
-
autoload :Hstore, 'mobility/backend/active_record/hstore'
|
7
|
-
autoload :Jsonb, 'mobility/backend/active_record/jsonb'
|
8
|
-
autoload :KeyValue, 'mobility/backend/active_record/key_value'
|
9
|
-
autoload :Serialized, 'mobility/backend/active_record/serialized'
|
10
|
-
autoload :QueryMethods, 'mobility/backend/active_record/query_methods'
|
11
|
-
autoload :Table, 'mobility/backend/active_record/table'
|
12
|
-
|
13
|
-
def setup_query_methods(query_methods)
|
14
|
-
setup do |attributes, options|
|
15
|
-
extend(Module.new do
|
16
|
-
define_method ::Mobility.query_method do
|
17
|
-
super().extending(query_methods.new(attributes, options))
|
18
|
-
end
|
19
|
-
end)
|
20
|
-
end
|
21
|
-
end
|
22
|
-
|
23
|
-
def self.included(backend_class)
|
24
|
-
backend_class.include(Backend)
|
25
|
-
backend_class.extend(self)
|
26
|
-
end
|
27
|
-
end
|
28
|
-
end
|
29
|
-
end
|
@@ -1,54 +0,0 @@
|
|
1
|
-
module Mobility
|
2
|
-
module Backend
|
3
|
-
=begin
|
4
|
-
|
5
|
-
Dirty tracking for AR models. See {Mobility::Backend::ActiveModel::Dirty} for
|
6
|
-
details on usage.
|
7
|
-
|
8
|
-
=end
|
9
|
-
module ActiveRecord::Dirty
|
10
|
-
include ActiveModel::Dirty
|
11
|
-
|
12
|
-
# @param [Class] backend_class Class of backend
|
13
|
-
def self.included(backend_class)
|
14
|
-
backend_class.extend(ActiveModel::Dirty::ClassMethods)
|
15
|
-
backend_class.extend(ClassMethods)
|
16
|
-
end
|
17
|
-
|
18
|
-
# Adds hook after {Backend::Setup#setup_model} to patch AR so that it
|
19
|
-
# handles changes to translated attributes just like normal attributes.
|
20
|
-
module ClassMethods
|
21
|
-
# (see Mobility::Backend::Setup#setup_model)
|
22
|
-
def setup_model(model_class, attributes, **options)
|
23
|
-
super
|
24
|
-
|
25
|
-
method_name_regex = /\A(#{attributes.join('|'.freeze)})_([a-z]{2}(_[a-z]{2})?)(=?|\??)\z/.freeze
|
26
|
-
has_attribute = Module.new do
|
27
|
-
define_method :has_attribute? do |attr_name|
|
28
|
-
super(attr_name) || !!method_name_regex.match(attr_name)
|
29
|
-
end
|
30
|
-
end
|
31
|
-
model_class.extend has_attribute
|
32
|
-
|
33
|
-
changes_applied_method = ::ActiveRecord::VERSION::STRING < '5.1' ? :changes_applied : :changes_internally_applied
|
34
|
-
mod = Module.new do
|
35
|
-
define_method changes_applied_method do
|
36
|
-
@previously_changed = changes
|
37
|
-
super()
|
38
|
-
end
|
39
|
-
|
40
|
-
def clear_changes_information
|
41
|
-
@previously_changed = ActiveSupport::HashWithIndifferentAccess.new
|
42
|
-
super
|
43
|
-
end
|
44
|
-
|
45
|
-
def previous_changes
|
46
|
-
(@previously_changed ||= ActiveSupport::HashWithIndifferentAccess.new).merge(super)
|
47
|
-
end
|
48
|
-
end
|
49
|
-
model_class.include mod
|
50
|
-
end
|
51
|
-
end
|
52
|
-
end
|
53
|
-
end
|
54
|
-
end
|
@@ -1,29 +0,0 @@
|
|
1
|
-
require 'mobility/backend/active_record/hash_valued'
|
2
|
-
|
3
|
-
module Mobility
|
4
|
-
module Backend
|
5
|
-
=begin
|
6
|
-
|
7
|
-
Implements the {Mobility::Backend::Hstore} backend for ActiveRecord models.
|
8
|
-
|
9
|
-
@see Mobility::Backend::ActiveRecord::HashValued
|
10
|
-
|
11
|
-
=end
|
12
|
-
class ActiveRecord::Hstore < ActiveRecord::HashValued
|
13
|
-
require 'mobility/backend/active_record/hstore/query_methods'
|
14
|
-
|
15
|
-
# @!group Backend Accessors
|
16
|
-
# @!macro backend_reader
|
17
|
-
# @!method read(locale, **options)
|
18
|
-
|
19
|
-
# @!group Backend Accessors
|
20
|
-
# @!macro backend_writer
|
21
|
-
def write(locale, value, **_)
|
22
|
-
translations[locale] = value && value.to_s
|
23
|
-
end
|
24
|
-
# @!endgroup
|
25
|
-
|
26
|
-
setup_query_methods(QueryMethods)
|
27
|
-
end
|
28
|
-
end
|
29
|
-
end
|
@@ -1,117 +0,0 @@
|
|
1
|
-
module Mobility
|
2
|
-
module Backend
|
3
|
-
=begin
|
4
|
-
|
5
|
-
Caches values fetched from the backend so subsequent fetches can be performed
|
6
|
-
more quickly.
|
7
|
-
|
8
|
-
By default, the cache stores cached values in a simple hash, returned from the
|
9
|
-
{new_cache} method added to the including backend instance class. To use a
|
10
|
-
different cache class, simply define a +new_cache+ method in the backend and
|
11
|
-
return a new instance of the cache class (many backends do this, see
|
12
|
-
{Mobility::Backend::KeyValue} for one example.)
|
13
|
-
|
14
|
-
The cache is reset by the {clear_cache} method, which by default simply assigns
|
15
|
-
the result of {new_cache} to the +@cache+ instance variable. This behaviour can
|
16
|
-
also be customized by defining a +new_cache+ method on the backend class (see
|
17
|
-
{Mobility::Backend::ActiveRecord::Table#new_cache} for an example of a backend that does this).
|
18
|
-
|
19
|
-
The cache is reset when one of a set of events happens (saving, reloading,
|
20
|
-
etc.). See {BackendResetter} for details.
|
21
|
-
|
22
|
-
Values are added to the cache in two ways:
|
23
|
-
|
24
|
-
1. first read from backend
|
25
|
-
2. any write to backend
|
26
|
-
|
27
|
-
The latter can be customized by defining the {write_to_cache?} method, which by
|
28
|
-
default returns +false+. If set to +true+, then writes will only update the
|
29
|
-
cache and not hit the backend. This is a sensible setting in case the cache is
|
30
|
-
actually an object which directly stores the translation (see one of the
|
31
|
-
ORM-specific implementations of {Mobility::Backend::KeyValue} for examples of
|
32
|
-
this).
|
33
|
-
|
34
|
-
=end
|
35
|
-
module Cache
|
36
|
-
# @group Backend Accessors
|
37
|
-
# @!macro backend_reader
|
38
|
-
# @param [Hash] options
|
39
|
-
# @param [Boolean] cache
|
40
|
-
# *false* to disable cache.
|
41
|
-
def read(locale, **options)
|
42
|
-
return super if options.delete(:cache) == false
|
43
|
-
if write_to_cache? || cache.has_key?(locale)
|
44
|
-
cache[locale]
|
45
|
-
else
|
46
|
-
cache[locale] = super
|
47
|
-
end
|
48
|
-
end
|
49
|
-
|
50
|
-
# @!macro backend_writer
|
51
|
-
# @param [Hash] options
|
52
|
-
# @param [Boolean] cache
|
53
|
-
# *false* to disable cache.
|
54
|
-
def write(locale, value, **options)
|
55
|
-
return super if options.delete(:cache) == false
|
56
|
-
cache[locale] = write_to_cache? ? value : super
|
57
|
-
end
|
58
|
-
# @!endgroup
|
59
|
-
|
60
|
-
# Adds hook to {Backend::Setup#setup_model} to include instance of
|
61
|
-
# model-specific {BackendResetter} subclass when setting up
|
62
|
-
# model class, to trigger cache resetting at specific events (saving,
|
63
|
-
# reloading, etc.)
|
64
|
-
module Setup
|
65
|
-
# @param model_class Model class
|
66
|
-
# @param [Array<String>] attributes Backend attributes
|
67
|
-
def setup_model(model_class, attributes, **_)
|
68
|
-
super
|
69
|
-
model_class.include BackendResetter.for(model_class).new(attributes) { clear_cache }
|
70
|
-
end
|
71
|
-
end
|
72
|
-
|
73
|
-
# @!group Cache Methods
|
74
|
-
# @!parse
|
75
|
-
# def new_cache
|
76
|
-
# {}
|
77
|
-
# end
|
78
|
-
#
|
79
|
-
# @!parse
|
80
|
-
# def write_to_cache?
|
81
|
-
# false
|
82
|
-
# end
|
83
|
-
#
|
84
|
-
# @!parse
|
85
|
-
# def clear_cache
|
86
|
-
# @cache = new_cache
|
87
|
-
# end
|
88
|
-
# @!endgroup
|
89
|
-
|
90
|
-
# Includes cache methods to backend (unless they are already defined) and
|
91
|
-
# extends backend class with {Mobility::Cache::Setup} for backend resetting.
|
92
|
-
def self.included(backend_class)
|
93
|
-
backend_class.class_eval do
|
94
|
-
extend Setup
|
95
|
-
|
96
|
-
def new_cache
|
97
|
-
{}
|
98
|
-
end unless method_defined?(:new_cache)
|
99
|
-
|
100
|
-
def write_to_cache?
|
101
|
-
false
|
102
|
-
end unless method_defined?(:write_to_cache?)
|
103
|
-
|
104
|
-
def clear_cache
|
105
|
-
@cache = new_cache
|
106
|
-
end unless method_defined?(:clear_cache)
|
107
|
-
end
|
108
|
-
end
|
109
|
-
|
110
|
-
private
|
111
|
-
|
112
|
-
def cache
|
113
|
-
@cache ||= new_cache
|
114
|
-
end
|
115
|
-
end
|
116
|
-
end
|
117
|
-
end
|
@@ -1,38 +0,0 @@
|
|
1
|
-
module Mobility
|
2
|
-
module Backend
|
3
|
-
=begin
|
4
|
-
|
5
|
-
Dirty tracking for Mobility attributes. See class-specific implementations for
|
6
|
-
details.
|
7
|
-
|
8
|
-
@see Mobility::Backend::ActiveModel::Dirty
|
9
|
-
@see Mobility::Backend::Sequel::Dirty
|
10
|
-
|
11
|
-
@note Dirty tracking can have unexpected results when combined with fallbacks.
|
12
|
-
A change in the fallback locale value will not mark an attribute falling
|
13
|
-
through to that locale as changed, even though it may look like it has
|
14
|
-
changed. However, when the value for the current locale is changed from nil
|
15
|
-
or blank to a new value, the change will be recorded as a change from that
|
16
|
-
fallback value, rather than from the nil or blank value. The specs are the
|
17
|
-
most reliable source of information on the interaction between dirty tracking
|
18
|
-
and fallbacks.
|
19
|
-
|
20
|
-
=end
|
21
|
-
module Dirty
|
22
|
-
# @param model_class Class of model this backend is defined on.
|
23
|
-
# @return [Backend]
|
24
|
-
# @raise [ArgumentError] if model class does not support dirty tracking
|
25
|
-
def self.for(model_class)
|
26
|
-
model_class ||= Object
|
27
|
-
if Loaded::ActiveRecord && model_class.ancestors.include?(::ActiveModel::Dirty)
|
28
|
-
(model_class < ::ActiveRecord::Base) ?
|
29
|
-
Backend::ActiveRecord::Dirty : Backend::ActiveModel::Dirty
|
30
|
-
elsif Loaded::Sequel && model_class < ::Sequel::Model
|
31
|
-
Backend::Sequel::Dirty
|
32
|
-
else
|
33
|
-
raise ArgumentError, "#{model_class.to_s} does not support Dirty module."
|
34
|
-
end
|
35
|
-
end
|
36
|
-
end
|
37
|
-
end
|
38
|
-
end
|
@@ -1,85 +0,0 @@
|
|
1
|
-
module Mobility
|
2
|
-
module Backend
|
3
|
-
=begin
|
4
|
-
|
5
|
-
Stores attribute translation as attribute/value pair on a shared translations
|
6
|
-
table, using a polymorphic relationship between a translation class and models
|
7
|
-
using the backend. By default, two tables are assumed to be present supporting
|
8
|
-
string and text translations: a +mobility_text_translations+ table for text-valued translations and a
|
9
|
-
+mobility_string_translations+ table for string-valued translations (the only
|
10
|
-
difference being the column type of the +value+ column on the table).
|
11
|
-
|
12
|
-
==Backend Options
|
13
|
-
|
14
|
-
===+association_name+
|
15
|
-
|
16
|
-
Name of association on model. Defaults to +mobility_text_translations+ (if
|
17
|
-
+type+ is +:text+) or +mobility_string_translations+ (if +type+ is +:string+).
|
18
|
-
If specified, ensure name does not overlap with other methods on model or with
|
19
|
-
the association name used by other backends on model (otherwise one will
|
20
|
-
overwrite the other).
|
21
|
-
|
22
|
-
===+type+
|
23
|
-
|
24
|
-
Currently, either +:text+ or +:string+ is supported. Determines which class to
|
25
|
-
use for translations, which in turn determines which table to use to store
|
26
|
-
translations (by default +mobility_text_translations+ for text type,
|
27
|
-
+mobility_string_translations+ for string type).
|
28
|
-
|
29
|
-
===+class_name+
|
30
|
-
|
31
|
-
Class to use for translations when defining association. By default,
|
32
|
-
{Mobility::ActiveRecord::TextTranslation} or
|
33
|
-
{Mobility::ActiveRecord::StringTranslation} for ActiveRecord models (similar
|
34
|
-
for Sequel models). If string is passed in, it will be constantized to get the
|
35
|
-
class.
|
36
|
-
|
37
|
-
@see Mobility::Backend::ActiveRecord::KeyValue
|
38
|
-
@see Mobility::Backend::Sequel::KeyValue
|
39
|
-
|
40
|
-
=end
|
41
|
-
module KeyValue
|
42
|
-
include OrmDelegator
|
43
|
-
|
44
|
-
def self.included(backend)
|
45
|
-
backend.extend ClassMethods
|
46
|
-
end
|
47
|
-
|
48
|
-
module ClassMethods
|
49
|
-
# @!group Backend Configuration
|
50
|
-
# @option options [Symbol,String] type (:text) Column type to use
|
51
|
-
# @raise [ArgumentError] if type is not either :text or :string
|
52
|
-
def configure(options)
|
53
|
-
options[:type] = (options[:type] || :text).to_sym
|
54
|
-
raise ArgumentError, "type must be one of: [text, string]" unless [:text, :string].include?(options[:type])
|
55
|
-
end
|
56
|
-
end
|
57
|
-
|
58
|
-
# Simple cache to memoize translations as a hash so they can be fetched
|
59
|
-
# quickly.
|
60
|
-
class TranslationsCache
|
61
|
-
# @param backend Instance of KeyValue backend to cache
|
62
|
-
# @return [TranslationsCache]
|
63
|
-
def initialize(backend)
|
64
|
-
@cache = Hash.new { |hash, locale| hash[locale] = backend.translation_for(locale) }
|
65
|
-
end
|
66
|
-
|
67
|
-
# @param locale [Symbol] Locale to fetch
|
68
|
-
def [](locale)
|
69
|
-
@cache[locale].value
|
70
|
-
end
|
71
|
-
|
72
|
-
# @param locale [Symbol] Locale to set
|
73
|
-
# @param value [String] Value to set
|
74
|
-
def []=(locale, value)
|
75
|
-
@cache[locale].value = value
|
76
|
-
end
|
77
|
-
|
78
|
-
# @yield [locale, translation]
|
79
|
-
def each_translation &block
|
80
|
-
@cache.each_value &block
|
81
|
-
end
|
82
|
-
end
|
83
|
-
end
|
84
|
-
end
|
85
|
-
end
|