From 2fb4b9f60b504fc9940f9e3b4e9941765a223458 Mon Sep 17 00:00:00 2001 From: Clarke Brunsdon Date: Tue, 22 Aug 2017 19:27:23 -0700 Subject: [PATCH 1/5] Move preferences to /lib Nothing in preferences needs to be in /app, as nothing relies on rails anymore --- core/app/models/spree/app_configuration.rb | 1 + core/app/models/spree/payment_method.rb | 2 + .../models/spree/preferences/preferable.rb | 133 ----------------- core/lib/spree/core.rb | 4 + .../spree/preferences/configuration.rb | 2 + core/lib/spree/preferences/preferable.rb | 140 ++++++++++++++++++ .../preferences/preferable_class_methods.rb | 0 .../spree/preferences/scoped_store.rb | 0 .../preferences/static_model_preferences.rb | 0 .../preferences/statically_configurable.rb | 0 .../models => lib}/spree/preferences/store.rb | 0 11 files changed, 149 insertions(+), 133 deletions(-) delete mode 100644 core/app/models/spree/preferences/preferable.rb rename core/{app/models => lib}/spree/preferences/configuration.rb (98%) create mode 100644 core/lib/spree/preferences/preferable.rb rename core/{app/models => lib}/spree/preferences/preferable_class_methods.rb (100%) rename core/{app/models => lib}/spree/preferences/scoped_store.rb (100%) rename core/{app/models => lib}/spree/preferences/static_model_preferences.rb (100%) rename core/{app/models => lib}/spree/preferences/statically_configurable.rb (100%) rename core/{app/models => lib}/spree/preferences/store.rb (100%) diff --git a/core/app/models/spree/app_configuration.rb b/core/app/models/spree/app_configuration.rb index 4e99959d9ae..d47dce3529e 100644 --- a/core/app/models/spree/app_configuration.rb +++ b/core/app/models/spree/app_configuration.rb @@ -17,6 +17,7 @@ # require "spree/core/search/base" require "spree/core/search/variant" +require 'spree/preferences/configuration' module Spree class AppConfiguration < Preferences::Configuration diff --git a/core/app/models/spree/payment_method.rb b/core/app/models/spree/payment_method.rb index aa03108087c..1399ffef5d3 100644 --- a/core/app/models/spree/payment_method.rb +++ b/core/app/models/spree/payment_method.rb @@ -1,3 +1,5 @@ +require 'spree/preferences/statically_configurable' + module Spree # A base class which is used for implementing payment methods. # diff --git a/core/app/models/spree/preferences/preferable.rb b/core/app/models/spree/preferences/preferable.rb deleted file mode 100644 index 672b7a13953..00000000000 --- a/core/app/models/spree/preferences/preferable.rb +++ /dev/null @@ -1,133 +0,0 @@ -# Preferable allows defining preference accessor methods. -# -# A class including Preferable must implement #preferences which should return -# an object responding to .fetch(key), []=(key, val), and .delete(key). -# -# The generated writer method performs typecasting before assignment into the -# preferences object. -# -# Examples: -# -# # Spree::Base includes Preferable and defines preferences as a serialized -# # column. -# class Settings < Spree::Base -# preference :color, :string, default: 'red' -# preference :temperature, :integer, default: 21 -# end -# -# s = Settings.new -# s.preferred_color # => 'red' -# s.preferred_temperature # => 21 -# -# s.preferred_color = 'blue' -# s.preferred_color # => 'blue' -# -# # Typecasting is performed on assignment -# s.preferred_temperature = '24' -# s.preferred_color # => 24 -# -# # Modifications have been made to the .preferences hash -# s.preferences #=> {color: 'blue', temperature: 24} -# -# # Save the changes. All handled by activerecord -# s.save! -module Spree::Preferences::Preferable - extend ActiveSupport::Concern - - included do - extend Spree::Preferences::PreferableClassMethods - end - - # Get a preference - # @param name [#to_sym] name of preference - # @return [Object] The value of preference +name+ - def get_preference(name) - has_preference! name - send self.class.preference_getter_method(name) - end - - # Set a preference - # @param name [#to_sym] name of preference - # @param value [Object] new value for preference +name+ - def set_preference(name, value) - has_preference! name - send self.class.preference_setter_method(name), value - end - - # @param name [#to_sym] name of preference - # @return [Symbol] The type of preference +name+ - def preference_type(name) - has_preference! name - send self.class.preference_type_getter_method(name) - end - - # @param name [#to_sym] name of preference - # @return [Object] The default for preference +name+ - def preference_default(name) - has_preference! name - send self.class.preference_default_getter_method(name) - end - - # Raises an exception if the +name+ preference is not defined on this class - # @param name [#to_sym] name of preference - def has_preference!(name) - raise NoMethodError.new "#{name} preference not defined" unless has_preference? name - end - - # @param name [#to_sym] name of preference - # @return [Boolean] if preference exists on this class - def has_preference?(name) - defined_preferences.include?(name.to_sym) - end - - # @return [Array] All preferences defined on this class - def defined_preferences - self.class.defined_preferences - end - - # @return [Hash{Symbol => Object}] Default for all preferences defined on this class - def default_preferences - Hash[ - defined_preferences.map do |preference| - [preference, preference_default(preference)] - end - ] - end - - private - - def convert_preference_value(value, type) - return nil if value.nil? - case type - when :string, :text - value.to_s - when :password - value.to_s - when :decimal - begin - value.to_s.to_d - rescue ArgumentError - BigDecimal.new(0) - end - when :integer - value.to_i - when :boolean - if !value || - value == 0 || - value =~ /\A(f|false|0)\Z/i || - (value.respond_to?(:empty?) && value.empty?) - false - else - true - end - when :array - raise TypeError, "Array expected got #{value.inspect}" unless value.is_a?(Array) - value - when :hash - raise TypeError, "Hash expected got #{value.inspect}" unless value.is_a?(Hash) - value - else - value - end - end -end diff --git a/core/lib/spree/core.rb b/core/lib/spree/core.rb index d9f92d12f77..049e2597042 100644 --- a/core/lib/spree/core.rb +++ b/core/lib/spree/core.rb @@ -86,3 +86,7 @@ class GatewayError < RuntimeError; end require 'spree/permission_sets' require 'spree/core/price_migrator' + +require 'spree/preferences/store' +require 'spree/preferences/static_model_preferences' +require 'spree/preferences/scoped_store' diff --git a/core/app/models/spree/preferences/configuration.rb b/core/lib/spree/preferences/configuration.rb similarity index 98% rename from core/app/models/spree/preferences/configuration.rb rename to core/lib/spree/preferences/configuration.rb index 8bfda8e8749..d9c748df1fb 100644 --- a/core/app/models/spree/preferences/configuration.rb +++ b/core/lib/spree/preferences/configuration.rb @@ -1,3 +1,5 @@ +require 'spree/preferences/preferable' + module Spree::Preferences # This takes the preferrable methods and adds some # syntatic sugar to access the preferences diff --git a/core/lib/spree/preferences/preferable.rb b/core/lib/spree/preferences/preferable.rb new file mode 100644 index 00000000000..ac814a5e97e --- /dev/null +++ b/core/lib/spree/preferences/preferable.rb @@ -0,0 +1,140 @@ +# Preferable allows defining preference accessor methods. +# +# A class including Preferable must implement #preferences which should return +# an object responding to .fetch(key), []=(key, val), and .delete(key). +# +# The generated writer method performs typecasting before assignment into the +# preferences object. +# +# Examples: +# +# # Spree::Base includes Preferable and defines preferences as a serialized +# # column. +# class Settings < Spree::Base +# preference :color, :string, default: 'red' +# preference :temperature, :integer, default: 21 +# end +# +# s = Settings.new +# s.preferred_color # => 'red' +# s.preferred_temperature # => 21 +# +# s.preferred_color = 'blue' +# s.preferred_color # => 'blue' +# +# # Typecasting is performed on assignment +# s.preferred_temperature = '24' +# s.preferred_color # => 24 +# +# # Modifications have been made to the .preferences hash +# s.preferences #=> {color: 'blue', temperature: 24} +# +# # Save the changes. All handled by activerecord +# s.save! + +require 'spree/preferences/preferable_class_methods' + +module Spree + module Preferences + module Preferable + extend ActiveSupport::Concern + + included do + extend Spree::Preferences::PreferableClassMethods + end + + # Get a preference + # @param name [#to_sym] name of preference + # @return [Object] The value of preference +name+ + def get_preference(name) + has_preference! name + send self.class.preference_getter_method(name) + end + + # Set a preference + # @param name [#to_sym] name of preference + # @param value [Object] new value for preference +name+ + def set_preference(name, value) + has_preference! name + send self.class.preference_setter_method(name), value + end + + # @param name [#to_sym] name of preference + # @return [Symbol] The type of preference +name+ + def preference_type(name) + has_preference! name + send self.class.preference_type_getter_method(name) + end + + # @param name [#to_sym] name of preference + # @return [Object] The default for preference +name+ + def preference_default(name) + has_preference! name + send self.class.preference_default_getter_method(name) + end + + # Raises an exception if the +name+ preference is not defined on this class + # @param name [#to_sym] name of preference + def has_preference!(name) + raise NoMethodError.new "#{name} preference not defined" unless has_preference? name + end + + # @param name [#to_sym] name of preference + # @return [Boolean] if preference exists on this class + def has_preference?(name) + defined_preferences.include?(name.to_sym) + end + + # @return [Array] All preferences defined on this class + def defined_preferences + self.class.defined_preferences + end + + # @return [Hash{Symbol => Object}] Default for all preferences defined on this class + def default_preferences + Hash[ + defined_preferences.map do |preference| + [preference, preference_default(preference)] + end + ] + end + + private + + def convert_preference_value(value, type) + return nil if value.nil? + case type + when :string, :text + value.to_s + when :password + value.to_s + when :decimal + begin + value.to_s.to_d + rescue ArgumentError + BigDecimal.new(0) + end + when :integer + value.to_i + when :boolean + if !value || + value == 0 || + value =~ /\A(f|false|0)\Z/i || + (value.respond_to?(:empty?) && value.empty?) + false + else + true + end + when :array + raise TypeError, "Array expected got #{value.inspect}" unless value.is_a?(Array) + value + when :hash + raise TypeError, "Hash expected got #{value.inspect}" unless value.is_a?(Hash) + value + else + value + end + end + end + end +end diff --git a/core/app/models/spree/preferences/preferable_class_methods.rb b/core/lib/spree/preferences/preferable_class_methods.rb similarity index 100% rename from core/app/models/spree/preferences/preferable_class_methods.rb rename to core/lib/spree/preferences/preferable_class_methods.rb diff --git a/core/app/models/spree/preferences/scoped_store.rb b/core/lib/spree/preferences/scoped_store.rb similarity index 100% rename from core/app/models/spree/preferences/scoped_store.rb rename to core/lib/spree/preferences/scoped_store.rb diff --git a/core/app/models/spree/preferences/static_model_preferences.rb b/core/lib/spree/preferences/static_model_preferences.rb similarity index 100% rename from core/app/models/spree/preferences/static_model_preferences.rb rename to core/lib/spree/preferences/static_model_preferences.rb diff --git a/core/app/models/spree/preferences/statically_configurable.rb b/core/lib/spree/preferences/statically_configurable.rb similarity index 100% rename from core/app/models/spree/preferences/statically_configurable.rb rename to core/lib/spree/preferences/statically_configurable.rb diff --git a/core/app/models/spree/preferences/store.rb b/core/lib/spree/preferences/store.rb similarity index 100% rename from core/app/models/spree/preferences/store.rb rename to core/lib/spree/preferences/store.rb From 256a9b6e9cedba078e81a5be316184d93a48538f Mon Sep 17 00:00:00 2001 From: Clarke Brunsdon Date: Tue, 22 Aug 2017 20:12:12 -0700 Subject: [PATCH 2/5] Set Spree::Config in spree/config This allows apps to require spree/config earlier in their startup and access the configuration before its set by the rails environment. --- core/lib/spree/config.rb | 3 +++ core/lib/spree/core/engine.rb | 1 - core/lib/spree/core/environment.rb | 4 +++- 3 files changed, 6 insertions(+), 2 deletions(-) create mode 100644 core/lib/spree/config.rb diff --git a/core/lib/spree/config.rb b/core/lib/spree/config.rb new file mode 100644 index 00000000000..cbf6c71c7cc --- /dev/null +++ b/core/lib/spree/config.rb @@ -0,0 +1,3 @@ +require 'spree/app_configuration' + +Spree::Config = Spree::AppConfiguration.new diff --git a/core/lib/spree/core/engine.rb b/core/lib/spree/core/engine.rb index 1b19cad60dc..9f5168400db 100644 --- a/core/lib/spree/core/engine.rb +++ b/core/lib/spree/core/engine.rb @@ -10,7 +10,6 @@ class Engine < ::Rails::Engine initializer "spree.environment", before: :load_config_initializers do |app| app.config.spree = Spree::Core::Environment.new - Spree::Config = app.config.spree.preferences # legacy access end initializer "spree.default_permissions", before: :load_config_initializers do |_app| diff --git a/core/lib/spree/core/environment.rb b/core/lib/spree/core/environment.rb index dbb884afc73..6a6cbab1312 100644 --- a/core/lib/spree/core/environment.rb +++ b/core/lib/spree/core/environment.rb @@ -9,8 +9,10 @@ class Environment attr_accessor :calculators, :preferences, :promotions def initialize + require 'spree/config' + @calculators = Calculators.new - @preferences = Spree::AppConfiguration.new + @preferences = Spree::Config @promotions = Spree::Promo::Environment.new end end From bc659cf29aea56bb9bf790b61514232edbd7495b Mon Sep 17 00:00:00 2001 From: Clarke Brunsdon Date: Tue, 22 Aug 2017 20:16:00 -0700 Subject: [PATCH 3/5] Move AppConfiguration to /lib Nothing in here requires rails to exist, so it can live in /lib just as easily as /app/models --- core/{app/models => lib}/spree/app_configuration.rb | 0 core/lib/spree/preferences/preferable.rb | 6 +++--- 2 files changed, 3 insertions(+), 3 deletions(-) rename core/{app/models => lib}/spree/app_configuration.rb (100%) diff --git a/core/app/models/spree/app_configuration.rb b/core/lib/spree/app_configuration.rb similarity index 100% rename from core/app/models/spree/app_configuration.rb rename to core/lib/spree/app_configuration.rb diff --git a/core/lib/spree/preferences/preferable.rb b/core/lib/spree/preferences/preferable.rb index ac814a5e97e..f71c6451c42 100644 --- a/core/lib/spree/preferences/preferable.rb +++ b/core/lib/spree/preferences/preferable.rb @@ -118,9 +118,9 @@ def convert_preference_value(value, type) value.to_i when :boolean if !value || - value == 0 || - value =~ /\A(f|false|0)\Z/i || - (value.respond_to?(:empty?) && value.empty?) + value == 0 || + value =~ /\A(f|false|0)\Z/i || + (value.respond_to?(:empty?) && value.empty?) false else true From 8aa053faeb2e7c67c51eeef1d259d899fad67da0 Mon Sep 17 00:00:00 2001 From: Clarke Brunsdon Date: Wed, 23 Aug 2017 09:09:41 -0700 Subject: [PATCH 4/5] Skip the inline require in environment With the previous commit I can now require this at the top --- core/lib/spree/core/environment.rb | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/core/lib/spree/core/environment.rb b/core/lib/spree/core/environment.rb index 6a6cbab1312..02ef37b920f 100644 --- a/core/lib/spree/core/environment.rb +++ b/core/lib/spree/core/environment.rb @@ -1,3 +1,5 @@ +require 'spree/config' + module Spree module Core class Environment @@ -9,8 +11,6 @@ class Environment attr_accessor :calculators, :preferences, :promotions def initialize - require 'spree/config' - @calculators = Calculators.new @preferences = Spree::Config @promotions = Spree::Promo::Environment.new From 72cc52a179609184abc761baef2d389cb8ce06b9 Mon Sep 17 00:00:00 2001 From: Clarke Brunsdon Date: Wed, 23 Aug 2017 09:36:32 -0700 Subject: [PATCH 5/5] Add a changelog entry for preference move to /lib --- CHANGELOG.md | 2 ++ 1 file changed, 2 insertions(+) diff --git a/CHANGELOG.md b/CHANGELOG.md index 330f3144c1f..8a616864751 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -27,6 +27,8 @@ - Remove Skeleton Grid CSS from the admin and complete its transition to Bootstrap. [\#2127](https://github.com/solidusio/solidus/pull/2127) ([graygilmore](https://github.com/graygilmore)) +- Move preferences namespace to /lib. Initializes the Spree::Config object in its own file. [\#2178](https://github.com/solidusio/solidus/pull/2178) ([cbrunsdon](https://github.com/cbrunsdon)) + ## Solidus 2.3.0 (unreleased) - Rails 5.1 [\#1895](https://github.com/solidusio/solidus/pull/1895) ([jhawthorn](https://github.com/jhawthorn))