mirror of
https://github.com/rails/rails.git
synced 2022-11-09 12:12:34 -05:00
Clean up the config object in ActionPack. Create config_accessor which just delegates to the config object, reducing the number of deprecations and add specific tests.
This commit is contained in:
parent
a8330c2006
commit
4163ccec23
18 changed files with 162 additions and 226 deletions
|
@ -12,7 +12,6 @@ require 'active_support/i18n'
|
|||
module AbstractController
|
||||
extend ActiveSupport::Autoload
|
||||
|
||||
autoload :Assigns
|
||||
autoload :Base
|
||||
autoload :Callbacks
|
||||
autoload :Collector
|
||||
|
|
|
@ -1,21 +0,0 @@
|
|||
module AbstractController
|
||||
module Assigns
|
||||
# This method should return a hash with assigns.
|
||||
# You can overwrite this configuration per controller.
|
||||
# :api: public
|
||||
def view_assigns
|
||||
hash = {}
|
||||
variables = instance_variable_names
|
||||
variables -= protected_instance_variables if respond_to?(:protected_instance_variables)
|
||||
variables.each { |name| hash[name] = instance_variable_get(name) }
|
||||
hash
|
||||
end
|
||||
|
||||
# This method assigns the hash specified in _assigns_hash to the given object.
|
||||
# :api: private
|
||||
# TODO Ideally, this should be done on AV::Base.new initialization.
|
||||
def _evaluate_assigns(object)
|
||||
view_assigns.each { |k,v| object.instance_variable_set(k, v) }
|
||||
end
|
||||
end
|
||||
end
|
|
@ -1,4 +1,4 @@
|
|||
require 'active_support/ordered_options'
|
||||
require 'active_support/configurable'
|
||||
|
||||
module AbstractController
|
||||
class Error < StandardError; end
|
||||
|
@ -8,6 +8,8 @@ module AbstractController
|
|||
attr_internal :response_body
|
||||
attr_internal :action_name
|
||||
|
||||
include ActiveSupport::Configurable
|
||||
|
||||
class << self
|
||||
attr_reader :abstract
|
||||
alias_method :abstract?, :abstract
|
||||
|
@ -29,14 +31,6 @@ module AbstractController
|
|||
@descendants ||= []
|
||||
end
|
||||
|
||||
def config
|
||||
@config ||= ActiveSupport::InheritableOptions.new(superclass < Base ? superclass.config : {})
|
||||
end
|
||||
|
||||
def configure
|
||||
yield config
|
||||
end
|
||||
|
||||
# A list of all internal methods for a controller. This finds the first
|
||||
# abstract superclass of a controller, and gets a list of all public
|
||||
# instance methods on that abstract class. Public instance methods of
|
||||
|
@ -99,10 +93,6 @@ module AbstractController
|
|||
|
||||
abstract!
|
||||
|
||||
def config
|
||||
@config ||= ActiveSupport::InheritableOptions.new(self.class.config)
|
||||
end
|
||||
|
||||
# Calls the action going through the entire action dispatch stack.
|
||||
#
|
||||
# The actual method that is called is determined by calling
|
||||
|
@ -133,6 +123,7 @@ module AbstractController
|
|||
end
|
||||
|
||||
private
|
||||
|
||||
# Returns true if the name can be considered an action. This can
|
||||
# be overridden in subclasses to modify the semantics of what
|
||||
# can be considered an action.
|
||||
|
|
|
@ -8,7 +8,6 @@ module AbstractController
|
|||
|
||||
included do
|
||||
class_attribute :_helpers
|
||||
delegate :_helpers, :to => :'self.class'
|
||||
self._helpers = Module.new
|
||||
end
|
||||
|
||||
|
|
|
@ -6,7 +6,7 @@ module AbstractController
|
|||
extend ActiveSupport::Concern
|
||||
|
||||
included do
|
||||
cattr_accessor :logger
|
||||
config_accessor :logger
|
||||
extend ActiveSupport::Benchmarkable
|
||||
end
|
||||
end
|
||||
|
|
|
@ -65,8 +65,11 @@ module ActionController
|
|||
@subclasses ||= []
|
||||
end
|
||||
|
||||
# TODO Move this to the appropriate module
|
||||
config_accessor :assets_dir, :asset_path, :javascripts_dir, :stylesheets_dir
|
||||
|
||||
ActiveSupport.run_load_hooks(:action_controller, self)
|
||||
end
|
||||
end
|
||||
|
||||
require "action_controller/deprecated/base"
|
||||
require "action_controller/deprecated/base"
|
|
@ -63,12 +63,10 @@ module ActionController #:nodoc:
|
|||
included do
|
||||
extend ConfigMethods
|
||||
|
||||
delegate :perform_caching, :perform_caching=, :to => :config
|
||||
singleton_class.delegate :perform_caching, :perform_caching=, :to => :config
|
||||
self.perform_caching = true
|
||||
config_accessor :perform_caching
|
||||
self.perform_caching = true if perform_caching.nil?
|
||||
end
|
||||
|
||||
|
||||
def caching_allowed?
|
||||
request.get? && response.status == 200
|
||||
end
|
||||
|
|
|
@ -44,8 +44,8 @@ module ActionController #:nodoc:
|
|||
# For Rails, this directory has already been set to Rails.public_path (which is usually set to <tt>Rails.root + "/public"</tt>). Changing
|
||||
# this setting can be useful to avoid naming conflicts with files in <tt>public/</tt>, but doing so will likely require configuring your
|
||||
# web server to look in the new location for cached files.
|
||||
singleton_class.delegate :page_cache_directory, :page_cache_directory=, :to => :config
|
||||
self.page_cache_directory = ''
|
||||
config_accessor :page_cache_directory
|
||||
self.page_cache_directory ||= ''
|
||||
|
||||
##
|
||||
# :singleton-method:
|
||||
|
@ -53,8 +53,8 @@ module ActionController #:nodoc:
|
|||
# order to make it easy for the cached files to be picked up properly by the web server. By default, this cache extension is <tt>.html</tt>.
|
||||
# If you want something else, like <tt>.php</tt> or <tt>.shtml</tt>, just set Base.page_cache_extension. In cases where a request already has an
|
||||
# extension, such as <tt>.xml</tt> or <tt>.rss</tt>, page caching will not add an extension. This allows it to work well with RESTful apps.
|
||||
singleton_class.delegate :page_cache_extension, :page_cache_extension=, :to => :config
|
||||
self.page_cache_extension = '.html'
|
||||
config_accessor :page_cache_extension
|
||||
self.page_cache_extension ||= '.html'
|
||||
end
|
||||
|
||||
module ClassMethods
|
||||
|
|
|
@ -1,33 +1,16 @@
|
|||
module ActionController
|
||||
class Base
|
||||
class << self
|
||||
def deprecated_config_accessor(option, message = nil)
|
||||
deprecated_config_reader(option, message)
|
||||
deprecated_config_writer(option, message)
|
||||
# Deprecated methods. Wrap them in a module so they can be overwritten by plugins
|
||||
# (like the verify method.)
|
||||
module DeprecatedBehavior #:nodoc:
|
||||
def relative_url_root
|
||||
ActiveSupport::Deprecation.warn "ActionController::Base.relative_url_root is ineffective. " <<
|
||||
"Please stop using it.", caller
|
||||
end
|
||||
|
||||
def deprecated_config_reader(option, message = nil)
|
||||
message ||= "Reading #{option} directly from ActionController::Base is deprecated. " \
|
||||
"Please read it from config.#{option}"
|
||||
|
||||
self.class_eval <<-RUBY, __FILE__, __LINE__ + 1
|
||||
def #{option}
|
||||
ActiveSupport::Deprecation.warn #{message.inspect}, caller
|
||||
config.#{option}
|
||||
end
|
||||
RUBY
|
||||
end
|
||||
|
||||
def deprecated_config_writer(option, message = nil)
|
||||
message ||= "Setting #{option} directly on ActionController::Base is deprecated. " \
|
||||
"Please set it on config.action_controller.#{option}"
|
||||
|
||||
self.class_eval <<-RUBY, __FILE__, __LINE__ + 1
|
||||
def #{option}=(val)
|
||||
ActiveSupport::Deprecation.warn #{message.inspect}, caller
|
||||
config.#{option} = val
|
||||
end
|
||||
RUBY
|
||||
def relative_url_root=
|
||||
ActiveSupport::Deprecation.warn "ActionController::Base.relative_url_root= is ineffective. " <<
|
||||
"Please stop using it.", caller
|
||||
end
|
||||
|
||||
def consider_all_requests_local
|
||||
|
@ -125,9 +108,7 @@ module ActionController
|
|||
def use_accept_header=(val)
|
||||
use_accept_header
|
||||
end
|
||||
end
|
||||
|
||||
module DeprecatedBehavior
|
||||
# This method has been moved to ActionDispatch::Request.filter_parameters
|
||||
def filter_parameter_logging(*args, &block)
|
||||
ActiveSupport::Deprecation.warn("Setting filter_parameter_logging in ActionController is deprecated and has no longer effect, please set 'config.filter_parameters' in config/application.rb instead", caller)
|
||||
|
@ -146,17 +127,6 @@ module ActionController
|
|||
|
||||
extend DeprecatedBehavior
|
||||
|
||||
deprecated_config_writer :session_options
|
||||
deprecated_config_writer :session_store
|
||||
|
||||
deprecated_config_accessor :assets_dir
|
||||
deprecated_config_accessor :asset_path
|
||||
deprecated_config_accessor :helpers_path
|
||||
deprecated_config_accessor :javascripts_dir
|
||||
deprecated_config_accessor :page_cache_directory
|
||||
deprecated_config_accessor :relative_url_root, "relative_url_root is ineffective. Please stop using it"
|
||||
deprecated_config_accessor :stylesheets_dir
|
||||
|
||||
delegate :consider_all_requests_local, :consider_all_requests_local=,
|
||||
:allow_concurrency, :allow_concurrency=, :to => :"self.class"
|
||||
end
|
||||
|
|
|
@ -21,8 +21,8 @@ module ActionController
|
|||
delegate :default_charset=, :to => "ActionDispatch::Response"
|
||||
end
|
||||
|
||||
# cattr_reader :protected_instance_variables
|
||||
cattr_accessor :protected_instance_variables
|
||||
# TODO: Update protected instance variables list
|
||||
config_accessor :protected_instance_variables
|
||||
self.protected_instance_variables = %w(@assigns @performed_redirect @performed_render
|
||||
@variables_added @request_origin @url
|
||||
@parent_controller @action_name
|
||||
|
|
|
@ -52,8 +52,8 @@ module ActionController
|
|||
include AbstractController::Helpers
|
||||
|
||||
included do
|
||||
class_attribute :helpers_path
|
||||
self.helpers_path = []
|
||||
config_accessor :helpers_path
|
||||
self.helpers_path ||= []
|
||||
end
|
||||
|
||||
module ClassMethods
|
||||
|
|
|
@ -4,6 +4,45 @@ module ActionController #:nodoc:
|
|||
class InvalidAuthenticityToken < ActionControllerError #:nodoc:
|
||||
end
|
||||
|
||||
# Protecting controller actions from CSRF attacks by ensuring that all forms are coming from the current
|
||||
# web application, not a forged link from another site, is done by embedding a token based on a random
|
||||
# string stored in the session (which an attacker wouldn't know) in all forms and Ajax requests generated
|
||||
# by Rails and then verifying the authenticity of that token in the controller. Only HTML/JavaScript
|
||||
# requests are checked, so this will not protect your XML API (presumably you'll have a different
|
||||
# authentication scheme there anyway). Also, GET requests are not protected as these should be
|
||||
# idempotent anyway.
|
||||
#
|
||||
# This is turned on with the <tt>protect_from_forgery</tt> method, which will check the token and raise an
|
||||
# ActionController::InvalidAuthenticityToken if it doesn't match what was expected. You can customize the
|
||||
# error message in production by editing public/422.html. A call to this method in ApplicationController is
|
||||
# generated by default in post-Rails 2.0 applications.
|
||||
#
|
||||
# The token parameter is named <tt>authenticity_token</tt> by default. If you are generating an HTML form
|
||||
# manually (without the use of Rails' <tt>form_for</tt>, <tt>form_tag</tt> or other helpers), you have to
|
||||
# include a hidden field named like that and set its value to what is returned by
|
||||
# <tt>form_authenticity_token</tt>.
|
||||
#
|
||||
# Request forgery protection is disabled by default in test environment. If you are upgrading from Rails
|
||||
# 1.x, add this to config/environments/test.rb:
|
||||
#
|
||||
# # Disable request forgery protection in test environment
|
||||
# config.action_controller.allow_forgery_protection = false
|
||||
#
|
||||
# == Learn more about CSRF (Cross-Site Request Forgery) attacks
|
||||
#
|
||||
# Here are some resources:
|
||||
# * http://isc.sans.org/diary.html?storyid=1750
|
||||
# * http://en.wikipedia.org/wiki/Cross-site_request_forgery
|
||||
#
|
||||
# Keep in mind, this is NOT a silver-bullet, plug 'n' play, warm security blanket for your rails application.
|
||||
# There are a few guidelines you should follow:
|
||||
#
|
||||
# * Keep your GET requests safe and idempotent. More reading material:
|
||||
# * http://www.xml.com/pub/a/2002/04/24/deviant.html
|
||||
# * http://www.w3.org/Protocols/rfc2616/rfc2616-sec9.html#sec9.1.1
|
||||
# * Make sure the session cookies that Rails creates are non-persistent. Check in Firefox and look
|
||||
# for "Expires: at end of session"
|
||||
#
|
||||
module RequestForgeryProtection
|
||||
extend ActiveSupport::Concern
|
||||
|
||||
|
@ -12,54 +51,17 @@ module ActionController #:nodoc:
|
|||
included do
|
||||
# Sets the token parameter name for RequestForgery. Calling +protect_from_forgery+
|
||||
# sets it to <tt>:authenticity_token</tt> by default.
|
||||
config.request_forgery_protection_token ||= :authenticity_token
|
||||
config_accessor :request_forgery_protection_token
|
||||
self.request_forgery_protection_token ||= :authenticity_token
|
||||
|
||||
# Controls whether request forgergy protection is turned on or not. Turned off by default only in test mode.
|
||||
config.allow_forgery_protection ||= true
|
||||
config_accessor :allow_forgery_protection
|
||||
self.allow_forgery_protection = true if allow_forgery_protection.nil?
|
||||
|
||||
helper_method :form_authenticity_token
|
||||
helper_method :protect_against_forgery?
|
||||
end
|
||||
|
||||
# Protecting controller actions from CSRF attacks by ensuring that all forms are coming from the current
|
||||
# web application, not a forged link from another site, is done by embedding a token based on a random
|
||||
# string stored in the session (which an attacker wouldn't know) in all forms and Ajax requests generated
|
||||
# by Rails and then verifying the authenticity of that token in the controller. Only HTML/JavaScript
|
||||
# requests are checked, so this will not protect your XML API (presumably you'll have a different
|
||||
# authentication scheme there anyway). Also, GET requests are not protected as these should be
|
||||
# idempotent anyway.
|
||||
#
|
||||
# This is turned on with the <tt>protect_from_forgery</tt> method, which will check the token and raise an
|
||||
# ActionController::InvalidAuthenticityToken if it doesn't match what was expected. You can customize the
|
||||
# error message in production by editing public/422.html. A call to this method in ApplicationController is
|
||||
# generated by default in post-Rails 2.0 applications.
|
||||
#
|
||||
# The token parameter is named <tt>authenticity_token</tt> by default. If you are generating an HTML form
|
||||
# manually (without the use of Rails' <tt>form_for</tt>, <tt>form_tag</tt> or other helpers), you have to
|
||||
# include a hidden field named like that and set its value to what is returned by
|
||||
# <tt>form_authenticity_token</tt>.
|
||||
#
|
||||
# Request forgery protection is disabled by default in test environment. If you are upgrading from Rails
|
||||
# 1.x, add this to config/environments/test.rb:
|
||||
#
|
||||
# # Disable request forgery protection in test environment
|
||||
# config.action_controller.allow_forgery_protection = false
|
||||
#
|
||||
# == Learn more about CSRF (Cross-Site Request Forgery) attacks
|
||||
#
|
||||
# Here are some resources:
|
||||
# * http://isc.sans.org/diary.html?storyid=1750
|
||||
# * http://en.wikipedia.org/wiki/Cross-site_request_forgery
|
||||
#
|
||||
# Keep in mind, this is NOT a silver-bullet, plug 'n' play, warm security blanket for your rails application.
|
||||
# There are a few guidelines you should follow:
|
||||
#
|
||||
# * Keep your GET requests safe and idempotent. More reading material:
|
||||
# * http://www.xml.com/pub/a/2002/04/24/deviant.html
|
||||
# * http://www.w3.org/Protocols/rfc2616/rfc2616-sec9.html#sec9.1.1
|
||||
# * Make sure the session cookies that Rails creates are non-persistent. Check in Firefox and look
|
||||
# for "Expires: at end of session"
|
||||
#
|
||||
module ClassMethods
|
||||
# Turn on request forgery protection. Bear in mind that only non-GET, HTML/JavaScript requests are checked.
|
||||
#
|
||||
|
@ -79,22 +81,6 @@ module ActionController #:nodoc:
|
|||
self.request_forgery_protection_token ||= :authenticity_token
|
||||
before_filter :verify_authenticity_token, options
|
||||
end
|
||||
|
||||
def request_forgery_protection_token
|
||||
config.request_forgery_protection_token
|
||||
end
|
||||
|
||||
def request_forgery_protection_token=(val)
|
||||
config.request_forgery_protection_token = val
|
||||
end
|
||||
|
||||
def allow_forgery_protection
|
||||
config.allow_forgery_protection
|
||||
end
|
||||
|
||||
def allow_forgery_protection=(val)
|
||||
config.allow_forgery_protection = val
|
||||
end
|
||||
end
|
||||
|
||||
protected
|
||||
|
@ -104,22 +90,6 @@ module ActionController #:nodoc:
|
|||
before_filter :verify_authenticity_token, options
|
||||
end
|
||||
|
||||
def request_forgery_protection_token
|
||||
config.request_forgery_protection_token
|
||||
end
|
||||
|
||||
def request_forgery_protection_token=(val)
|
||||
config.request_forgery_protection_token = val
|
||||
end
|
||||
|
||||
def allow_forgery_protection
|
||||
config.allow_forgery_protection
|
||||
end
|
||||
|
||||
def allow_forgery_protection=(val)
|
||||
config.allow_forgery_protection = val
|
||||
end
|
||||
|
||||
# The actual before_filter that is used. Modify this to change how you handle unverified requests.
|
||||
def verify_authenticity_token
|
||||
verified_request? || raise(ActionController::InvalidAuthenticityToken)
|
||||
|
@ -146,7 +116,7 @@ module ActionController #:nodoc:
|
|||
end
|
||||
|
||||
def protect_against_forgery?
|
||||
config.allow_forgery_protection
|
||||
allow_forgery_protection
|
||||
end
|
||||
end
|
||||
end
|
||||
|
|
|
@ -13,64 +13,51 @@ module ActionController
|
|||
class Railtie < Rails::Railtie
|
||||
config.action_controller = ActiveSupport::OrderedOptions.new
|
||||
|
||||
ad = config.action_dispatch
|
||||
config.action_controller.singleton_class.send(:define_method, :session) do
|
||||
ActiveSupport::Deprecation.warn "config.action_controller.session has been " \
|
||||
"renamed to config.action_dispatch.session.", caller
|
||||
ad.session
|
||||
end
|
||||
config.action_controller.singleton_class.tap do |d|
|
||||
d.send(:define_method, :session) do
|
||||
ActiveSupport::Deprecation.warn "config.action_controller.session has been deprecated. " <<
|
||||
"Please use Rails.application.config.session_store instead.", caller
|
||||
end
|
||||
|
||||
config.action_controller.singleton_class.send(:define_method, :session=) do |val|
|
||||
ActiveSupport::Deprecation.warn "config.action_controller.session has been " \
|
||||
"renamed to config.action_dispatch.session.", caller
|
||||
ad.session = val
|
||||
end
|
||||
d.send(:define_method, :session=) do |val|
|
||||
ActiveSupport::Deprecation.warn "config.action_controller.session= has been deprecated. " <<
|
||||
"Please use config.session_store(name, options) instead.", caller
|
||||
end
|
||||
|
||||
config.action_controller.singleton_class.send(:define_method, :session_store) do
|
||||
ActiveSupport::Deprecation.warn "config.action_controller.session_store has been " \
|
||||
"renamed to config.action_dispatch.session_store.", caller
|
||||
ad.session_store
|
||||
end
|
||||
d.send(:define_method, :session_store) do
|
||||
ActiveSupport::Deprecation.warn "config.action_controller.session_store has been deprecated. " <<
|
||||
"Please use Rails.application.config.session_store instead.", caller
|
||||
end
|
||||
|
||||
config.action_controller.singleton_class.send(:define_method, :session_store=) do |val|
|
||||
ActiveSupport::Deprecation.warn "config.action_controller.session_store has been " \
|
||||
"renamed to config.action_dispatch.session_store.", caller
|
||||
ad.session_store = val
|
||||
d.send(:define_method, :session_store=) do |val|
|
||||
ActiveSupport::Deprecation.warn "config.action_controller.session_store= has been deprecated. " <<
|
||||
"Please use config.session_store(name, options) instead.", caller
|
||||
end
|
||||
end
|
||||
|
||||
log_subscriber :action_controller, ActionController::Railties::LogSubscriber.new
|
||||
|
||||
initializer "action_controller.logger" do
|
||||
ActiveSupport.on_load(:action_controller) { self.logger ||= Rails.logger }
|
||||
end
|
||||
|
||||
initializer "action_controller.page_cache_directory" do
|
||||
ActiveSupport.on_load(:action_controller) do
|
||||
self.page_cache_directory = Rails.public_path
|
||||
end
|
||||
end
|
||||
|
||||
initializer "action_controller.set_configs" do |app|
|
||||
paths = app.config.paths
|
||||
ac = app.config.action_controller
|
||||
|
||||
ac.assets_dir = paths.public.to_a.first
|
||||
ac.javascripts_dir = paths.public.javascripts.to_a.first
|
||||
ac.stylesheets_dir = paths.public.stylesheets.to_a.first
|
||||
ac.assets_dir ||= paths.public.to_a.first
|
||||
ac.javascripts_dir ||= paths.public.javascripts.to_a.first
|
||||
ac.stylesheets_dir ||= paths.public.stylesheets.to_a.first
|
||||
ac.page_cache_directory ||= paths.public.to_a.first
|
||||
ac.helpers_path ||= paths.app.helpers.to_a
|
||||
|
||||
ActiveSupport.on_load(:action_controller) do
|
||||
self.config.merge!(ac)
|
||||
end
|
||||
end
|
||||
|
||||
initializer "action_controller.initialize_framework_caches" do
|
||||
ActiveSupport.on_load(:action_controller) { self.cache_store ||= RAILS_CACHE }
|
||||
initializer "action_controller.logger" do
|
||||
ActiveSupport.on_load(:action_controller) { self.logger ||= Rails.logger }
|
||||
end
|
||||
|
||||
initializer "action_controller.set_helpers_path" do |app|
|
||||
ActiveSupport.on_load(:action_controller) do
|
||||
self.helpers_path = app.config.paths.app.helpers.to_a
|
||||
end
|
||||
initializer "action_controller.initialize_framework_caches" do
|
||||
ActiveSupport.on_load(:action_controller) { self.cache_store ||= RAILS_CACHE }
|
||||
end
|
||||
|
||||
initializer "action_controller.url_helpers" do |app|
|
||||
|
|
|
@ -31,8 +31,8 @@ module ActionView
|
|||
include ActionController::PolymorphicRoutes
|
||||
include ActionController::RecordIdentifier
|
||||
|
||||
include AbstractController::Helpers
|
||||
include ActionView::Helpers
|
||||
include ActionController::Helpers
|
||||
|
||||
class_inheritable_accessor :helper_class
|
||||
attr_accessor :controller, :output_buffer, :rendered
|
||||
|
|
|
@ -3,9 +3,6 @@ require 'abstract_unit'
|
|||
class FormTagHelperTest < ActionView::TestCase
|
||||
tests ActionView::Helpers::FormTagHelper
|
||||
|
||||
# include ActiveSupport::Configurable
|
||||
# DEFAULT_CONFIG = ActionView::DEFAULT_CONFIG
|
||||
|
||||
def setup
|
||||
super
|
||||
@controller = BasicController.new
|
||||
|
|
|
@ -1,35 +1,36 @@
|
|||
require "active_support/concern"
|
||||
require 'active_support/concern'
|
||||
require 'active_support/ordered_options'
|
||||
require 'active_support/core_ext/kernel/singleton_class'
|
||||
require 'active_support/core_ext/module/delegation'
|
||||
|
||||
module ActiveSupport
|
||||
module Configurable
|
||||
extend ActiveSupport::Concern
|
||||
|
||||
module ClassMethods
|
||||
def get_config
|
||||
module_parts = name.split("::")
|
||||
modules = [Object]
|
||||
module_parts.each {|name| modules.push modules.last.const_get(name) }
|
||||
modules.reverse_each do |mod|
|
||||
return mod.const_get(:DEFAULT_CONFIG) if const_defined?(:DEFAULT_CONFIG)
|
||||
end
|
||||
{}
|
||||
end
|
||||
|
||||
def config
|
||||
self.config = get_config unless @config
|
||||
@config
|
||||
@config ||= ActiveSupport::InheritableOptions.new(superclass.respond_to?(:config) ? superclass.config : {})
|
||||
end
|
||||
|
||||
def config=(hash)
|
||||
@config = ActiveSupport::OrderedOptions.new
|
||||
hash.each do |key, value|
|
||||
@config[key] = value
|
||||
def configure
|
||||
yield config
|
||||
end
|
||||
|
||||
def config_accessor(*names)
|
||||
names.each do |name|
|
||||
code, line = <<-RUBY, __LINE__ + 1
|
||||
def #{name}; config.#{name}; end
|
||||
def #{name}=(value); config.#{name} = value; end
|
||||
RUBY
|
||||
|
||||
singleton_class.class_eval code, __FILE__, line
|
||||
class_eval code, __FILE__, line
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
def config
|
||||
self.class.config
|
||||
@config ||= ActiveSupport::InheritableOptions.new(self.class.config)
|
||||
end
|
||||
end
|
||||
end
|
42
activesupport/test/configurable_test.rb
Normal file
42
activesupport/test/configurable_test.rb
Normal file
|
@ -0,0 +1,42 @@
|
|||
require 'abstract_unit'
|
||||
require 'active_support/configurable'
|
||||
|
||||
class ConfigurableActiveSupport < ActiveSupport::TestCase
|
||||
class Parent
|
||||
include ActiveSupport::Configurable
|
||||
config_accessor :foo
|
||||
end
|
||||
|
||||
class Child < Parent
|
||||
end
|
||||
|
||||
setup do
|
||||
Parent.config.clear
|
||||
Parent.config.foo = :bar
|
||||
|
||||
Child.config.clear
|
||||
end
|
||||
|
||||
test "adds a configuration hash" do
|
||||
assert_equal({ :foo => :bar }, Parent.config)
|
||||
end
|
||||
|
||||
test "configuration hash is inheritable" do
|
||||
assert_equal :bar, Child.config.foo
|
||||
assert_equal :bar, Parent.config.foo
|
||||
|
||||
Child.config.foo = :baz
|
||||
assert_equal :baz, Child.config.foo
|
||||
assert_equal :bar, Parent.config.foo
|
||||
end
|
||||
|
||||
test "configuration hash is available on instance" do
|
||||
instance = Parent.new
|
||||
assert_equal :bar, instance.config.foo
|
||||
assert_equal :bar, Parent.config.foo
|
||||
|
||||
instance.config.foo = :baz
|
||||
assert_equal :baz, instance.config.foo
|
||||
assert_equal :bar, Parent.config.foo
|
||||
end
|
||||
end
|
|
@ -128,13 +128,13 @@ module Rails
|
|||
end
|
||||
end
|
||||
|
||||
protected
|
||||
|
||||
def session_options
|
||||
return @session_options unless @session_store == :cookie_store
|
||||
@session_options.merge(:secret => @secret_token)
|
||||
end
|
||||
|
||||
protected
|
||||
|
||||
def default_middleware_stack
|
||||
ActionDispatch::MiddlewareStack.new.tap do |middleware|
|
||||
middleware.use('::ActionDispatch::Static', lambda { paths.public.to_a.first }, :if => lambda { serve_static_assets })
|
||||
|
|
Loading…
Reference in a new issue