Skip to content

Commit

Permalink
Merge pull request #4 from GunioRobot/clean
Browse files Browse the repository at this point in the history
Hi! We cleaned up your code for you!
  • Loading branch information
Tony Issakov committed Feb 17, 2012
2 parents bc192bd + e97eb75 commit 7f70825
Show file tree
Hide file tree
Showing 9 changed files with 187 additions and 187 deletions.
2 changes: 1 addition & 1 deletion .bundle/config
@@ -1,2 +1,2 @@
---
---
BUNDLE_DISABLE_SHARED_GEMS: "1"
38 changes: 19 additions & 19 deletions README.md
Expand Up @@ -12,7 +12,7 @@ now get the joy of scoped access restrictions across any ORM built on ActiveMode
To use, just add to any application using ActiveModel. In Rails 3, this is a simple job of adding:

gem 'scoped_attr_accessible'

To our Gemfile and running `bundle install`.

If you encounter issues, please make sure you add it right after activerecord or rails - Otherwise, you might
Expand All @@ -26,21 +26,21 @@ When in use, you can simply pass the `:scope` option in your declaration to decl
For example,

class User < ActiveRecord::Base

# All attributes are accessible for the admin scope.
attr_accessible :all, :scope => :admin

# The default scope can only access a and b.
attr_accessible :a, :b

# Make both :c and :d accessible for owners and the default scope
attr_accessible :c, :d, :scope => [:owner, :default]

# Also, it works the same with attr_protected!
attr_protected :n, :scope => :default

end

If both `attr_accessible` and `attr_protected` are used on a given scope, attributes
declared in `attr_protected` take precedence. Also, If `attr_accessible` isn't called for a scope
at all, it will allow all variables except those marked as protected.
Expand Down Expand Up @@ -69,15 +69,15 @@ user intervention this scope is simply `:default`.
To set the scope, you can do so on a class an instance level with instance-level taking precedence.

To set it on a class level, simply do:

User.current_sanitizer_scope = :admin
# Or, dynamically:
User.current_sanitizer_scope = @user.role.name.to_sym

This will be set Thread local. Also note you can get the current class-level scope:

p User.current_sanitizer_scope # => nil by default

Or, temporarily switch it out, resetting it afterwards:

p User.current_sanitizer_scope
Expand All @@ -92,7 +92,7 @@ You can also declare this on the instance level, e.g:
user.current_sanitizer_scope = :admin
# Or, more complex:
user.current_sanitizer_scope = "something-else"

### Complex Scoping

Although the scope on a given accessible / protected declaration must be a symbol,
Expand All @@ -109,23 +109,23 @@ match. e.g:

# Reeopen the class
class User < ActiveRecord::Base

sanitizer_scope_recognizer :admin do |record, scope_value|
scope_value.is_a?(User) && scope_value.admin?
end

sanitizer_scope_recognizer :owner do |record, scope_value|
scope_value.is_a?(User) && scope_value == record
end

end

In this example, we could simply do:

user = User.find(params[:id])
user.current_sanitizer_scope = current_user
user.update_attributes params[:user]

And it would automatically set the scope to :owner / :admin when sanitizing the attributes.

The second and more flexible option is scope convertors - they're given the same information (e.g.
Expand All @@ -137,18 +137,18 @@ As an example, we could implement the following:

# Reeopen the class
class User < ActiveRecord::Base

sanitizer_scope_converter do |record, scope_value|
return user.role.name.to_sym if scope_value.is_a?(User)
return scope_value.user if scope_value.is_a?(UserSession)
end

end

When combined, these all form a very flexible way to dynamically scope attribute accessible.

## Note on Patches/Pull Requests

* Fork the project.
* Make your feature addition or bug fix.
* Add tests for it. This is important so I don't break it in a future version unintentionally.
Expand Down
14 changes: 7 additions & 7 deletions lib/scoped_attr_accessible.rb
Expand Up @@ -3,39 +3,39 @@
module ScopedAttrAccessible
autoload :Sanitizer, 'scoped_attr_accessible/sanitizer'
autoload :ActiveModelMixin, 'scoped_attr_accessible/active_model_mixin'

# Mixes the am mixin into ActiveModel's mass assignment helpers.
def self.mixin!
require 'active_model/mass_assignment_security'
ActiveModel::MassAssignmentSecurity.module_eval do
extend ScopedAttrAccessible::ActiveModelMixin::IncludedHook
end
end

GLOBAL_SCOPE_KEY = :_scoped_attr_accessible_sanitizer_scope

def self.current_sanitizer_scope
Thread.current[GLOBAL_SCOPE_KEY]
end

def self.current_sanitizer_scope=(value)
Thread.current[GLOBAL_SCOPE_KEY] = value
end

def self.with_sanitizer_scope(scope)
old_sanitizer_scope = self.current_sanitizer_scope
self.current_sanitizer_scope = scope
yield if block_given?
ensure
self.current_sanitizer_scope = old_sanitizer_scope
end

if defined?(Rails::Railtie)
class Railtie < Rails::Railtie
initializer "scoped_attr_accessible.setup" do
ScopedAttrAccessible.mixin!
end
end
end

end
38 changes: 19 additions & 19 deletions lib/scoped_attr_accessible/active_model_mixin.rb
Expand Up @@ -3,23 +3,23 @@
require 'active_support/core_ext/array/extract_options'

module ScopedAttrAccessible
module ActiveModelMixin
module ActiveModelMixin
extend ActiveSupport::Concern


module IncludedHook
def included(base)
super
base.class_eval { include ActiveModelMixin }
end
end

included do
extlib_inheritable_accessor :_scoped_attr_sanitizer
end

module ClassMethods

def attr_accessible(*args)
scopes = scopes_from_args(args)
sanitizer = self.scoped_attr_sanitizer
Expand All @@ -28,7 +28,7 @@ def attr_accessible(*args)
end
self._active_authorizer = sanitizer
end

def attr_protected(*args)
scopes = scopes_from_args(args)
sanitizer = self.scoped_attr_sanitizer
Expand All @@ -37,51 +37,51 @@ def attr_protected(*args)
end
self._active_authorizer = sanitizer
end

def scoped_attr_sanitizer
self._scoped_attr_sanitizer ||= ScopedAttrAccessible::Sanitizer.new
end

def current_sanitizer_scope
Thread.current[current_sanitizer_scope_key]
end

def current_sanitizer_scope=(value)
Thread.current[current_sanitizer_scope_key] = value
end

def with_sanitizer_scope(scope_name)
old_scope = current_sanitizer_scope
self.current_sanitizer_scope = scope_name
yield if block_given?
ensure
self.current_sanitizer_scope = old_scope
end

def sanitizer_scope_recognizer(name, &recognizer)
scoped_attr_sanitizer.define_recognizer(name, &recognizer)
end

def sanitizer_scope_converter(&converter)
scoped_attr_sanitizer.define_converter(&converter)
end

protected

def current_sanitizer_scope_key
:"#{name}_sanitizer_scope"
end

def scopes_from_args(args)
options = args.extract_options!
scope = Array(options.delete(:scope)).map(&:to_sym)
scope << :default if scope.empty?
args << options unless options.empty?
scope
end

end

module InstanceMethods

def current_sanitizer_scope
Expand All @@ -104,6 +104,6 @@ def sanitize_for_mass_assignment(attributes)
end

end

end
end
24 changes: 12 additions & 12 deletions lib/scoped_attr_accessible/sanitizer.rb
Expand Up @@ -2,7 +2,7 @@

module ScopedAttrAccessible
class Sanitizer

def initialize
@accessible_attributes = Hash.new { |h,k| h[k] = Set.new }
@protected_attributes = Hash.new { |h,k| h[k] = Set.new }
Expand All @@ -11,7 +11,7 @@ def initialize
# Returns a scope symbol.
@scope_converters = []
end

# Looks up a scope name from the registered recognizers and then from the converters.
def normalize_scope(object, context)
return object if object.is_a?(Symbol)
Expand All @@ -27,40 +27,40 @@ def normalize_scope(object, context)
# 3. Fall back to default
return :default
end

def sanitize(attributes, context = Object.new)
sanitize_with_scope attributes, :default, context
end

def sanitize_with_scope(attributes, scope, context)
scope = normalize_scope scope, context
attributes.reject { |k, v| deny? k, scope }
end

def define_recognizer(scope, &blk)
@scope_recognizers[scope.to_sym] << blk
end

def define_converter(&blk)
@scope_converters << blk
end

def make_protected(attribute, scope = :default)
@protected_attributes[scope.to_sym] << attribute.to_s
end

def make_accessible(attribute, scope = :default)
@accessible_attributes[scope.to_sym] << attribute.to_s
end

def deny?(attribute, scope = :default)
!attribute_assignable_with_scope?(attribute, scope)
end

def allow?(attribute, scope = :default)
attribute_assignable_with_scope?(attribute, scope)
end

def attribute_assignable_with_scope?(attribute, scope)
attribute = attribute.to_s.gsub(/\(.+/, '')
scope = scope.to_sym
Expand All @@ -76,6 +76,6 @@ def attribute_assignable_with_scope?(attribute, scope)
return true
end
end

end
end

0 comments on commit 7f70825

Please sign in to comment.