polar 0.2.1

Sign up to get free protection for your applications and to get access to all the features.
data/.gitignore ADDED
@@ -0,0 +1,36 @@
1
+ ## MAC OS
2
+ .DS_Store
3
+
4
+ ## TEXTMATE
5
+ *.tmproj
6
+ tmtags
7
+
8
+ ## EMACS
9
+ *~
10
+ \#*
11
+ .\#*
12
+
13
+ ## VIM
14
+ *.swp
15
+
16
+ ## Rubinius
17
+ *.rbc
18
+
19
+ ## PROJECT::GENERAL
20
+ *.gem
21
+ coverage
22
+ rdoc
23
+ pkg
24
+ tmp
25
+ doc
26
+ log
27
+ .yardoc
28
+ measurements
29
+
30
+ ## BUNDLER
31
+ .bundle
32
+ Gemfile.local
33
+ Gemfile.lock
34
+
35
+ ## PROJECT::SPECIFIC
36
+ vendor
data/Polar.gemspec ADDED
@@ -0,0 +1,56 @@
1
+ # Generated by jeweler
2
+ # DO NOT EDIT THIS FILE DIRECTLY
3
+ # Instead, edit Jeweler::Tasks in Rakefile, and run the gemspec command
4
+ # -*- encoding: utf-8 -*-
5
+
6
+ Gem::Specification.new do |s|
7
+ s.name = %q{polar}
8
+ s.version = "0.2.1"
9
+
10
+ s.required_rubygems_version = Gem::Requirement.new(">= 0") if s.respond_to? :required_rubygems_version=
11
+ s.authors = ["Grzegorz Kazulak", "Lukasz Tackowiak"]
12
+ s.date = %q{2010-07-29}
13
+ s.description = %q{Control access like a bear}
14
+ s.email = %q{grzegorz.kazulak@gmail.com}
15
+ s.extra_rdoc_files = [
16
+ "README.md"
17
+ ]
18
+ s.files = [
19
+ ".gitignore",
20
+ "Polar.gemspec",
21
+ "README.md",
22
+ "Rakefile",
23
+ "VERSION",
24
+ "init.rb",
25
+ "lib/polar.rb",
26
+ "lib/polar/adapter.rb",
27
+ "lib/polar/adapters/active_record.rb",
28
+ "lib/polar/errors.rb",
29
+ "lib/polar/frameworks/rails.rb",
30
+ "lib/polar/groups.rb",
31
+ "lib/polar/permissions.rb",
32
+ "spec/polar_spec.rb",
33
+ "spec/spec_helper.rb"
34
+ ]
35
+ s.homepage = %q{http://github.com/grzegorzkazulak/polar}
36
+ s.rdoc_options = ["--charset=UTF-8"]
37
+ s.require_paths = ["lib"]
38
+ s.rubyforge_project = %q{polar}
39
+ s.rubygems_version = %q{1.3.7}
40
+ s.summary = %q{Access control for polar bears}
41
+ s.test_files = [
42
+ "spec/polar_spec.rb",
43
+ "spec/spec_helper.rb"
44
+ ]
45
+
46
+ if s.respond_to? :specification_version then
47
+ current_version = Gem::Specification::CURRENT_SPECIFICATION_VERSION
48
+ s.specification_version = 3
49
+
50
+ if Gem::Version.new(Gem::VERSION) >= Gem::Version.new('1.2.0') then
51
+ else
52
+ end
53
+ else
54
+ end
55
+ end
56
+
data/README.md ADDED
@@ -0,0 +1,61 @@
1
+ Polar
2
+ ===============================
3
+
4
+ Polar is a simple, fast and powerful way to manage user permissions/groups. It uses redis as a backend storage mechanism for all your permissions mechanism and simple DSL to define all the available permissions within a system.
5
+
6
+ Usage example
7
+ ----------
8
+
9
+ class User < ActiveRecord::Base
10
+
11
+ default :permissions do |p|
12
+ p.edit_profile
13
+ p.manage_addresses
14
+ end
15
+
16
+ default :groups do |g|
17
+ g.administrators
18
+ end
19
+ end
20
+
21
+ Below the code definition to accompany the settings from User model. That should resist somewhere in your initializers folder.
22
+
23
+ Example definition
24
+ ----------
25
+
26
+ Polar.define :permissions do |gz|
27
+ gz.edit_profile do |c|
28
+ c.allow :users_controller, :only => [:edit, :update]
29
+ end
30
+
31
+ gz.manage_addresses do |gz|
32
+ c.allow :addresses_controller
33
+ end
34
+ end
35
+
36
+ Example usage
37
+ ----------
38
+
39
+ @user = User.first
40
+
41
+ # Check if user has specific permission
42
+ @user.can?(:edit_profile)
43
+
44
+ # Check if user belongs to specific group
45
+ @user.member_of?(:administrators)
46
+
47
+
48
+ ## Note on Patches/Pull Requests
49
+
50
+ * Fork the project.
51
+ * Make your feature addition or bug fix.
52
+ * Add tests for it. This is important so I don't break it in a
53
+ future version unintentionally.
54
+ * Commit, do not mess with rakefile, version, or history.
55
+ (if you want to have your own version, that is fine but bump version in a commit by itself I can ignore when I pull)
56
+ * Send me a pull request. Bonus points for topic branches.
57
+
58
+
59
+ ### Credits
60
+
61
+ - Grzegorz Kazulak <grzegorz.kazulak@gmail.com>
data/Rakefile ADDED
@@ -0,0 +1,49 @@
1
+ require 'rake'
2
+ require 'spec/rake/spectask'
3
+ adapters = Dir[File.dirname(__FILE__) + '/lib/polar/adapter/*.rb'].map{|file| File.basename(file, '.rb') }
4
+
5
+ task :spec do
6
+ adapters.map{|adapter| "spec:#{adapter}"}.each do |spec|
7
+ Rake::Task[spec].invoke
8
+ end
9
+ end
10
+
11
+ namespace :spec do
12
+ adapters.each do |adapter|
13
+ Spec::Rake::SpecTask.new(adapter) do |spec|
14
+ spec.spec_files = FileList['spec/*_spec.rb']
15
+ end
16
+ end
17
+ end
18
+
19
+ Spec::Rake::SpecTask.new(:rcov) do |spec|
20
+ spec.libs << 'lib' << 'spec'
21
+ spec.pattern = 'spec/**/*_spec.rb'
22
+ spec.rcov = true
23
+ end
24
+
25
+ task :default => :spec
26
+
27
+ begin
28
+ gem 'jeweler', '~> 1.4'
29
+ require 'jeweler'
30
+
31
+ Jeweler::Tasks.new do |gem|
32
+ gem.name = 'polar'
33
+ gem.summary = 'Access control for polar bears'
34
+ gem.description = 'Control access like a bear'
35
+ gem.email = 'grzegorz.kazulak@gmail.com'
36
+ gem.homepage = 'http://github.com/grzegorzkazulak/%s' % gem.name
37
+ gem.authors = [ 'Grzegorz Kazulak', 'Lukasz Tackowiak']
38
+
39
+ gem.rubyforge_project = 'polar'
40
+ end
41
+
42
+ Jeweler::GemcutterTasks.new
43
+
44
+ FileList['tasks/**/*.rake'].each { |task| import task }
45
+ rescue LoadError
46
+ puts 'Jeweler (or a dependency) not available. Install it with: gem install jeweler'
47
+ end
48
+
49
+ task(:spec) {} # stub out the spec task for as long as we don't have any specs
data/VERSION ADDED
@@ -0,0 +1 @@
1
+ 0.2.1
data/init.rb ADDED
@@ -0,0 +1 @@
1
+ require 'polar'
data/lib/polar.rb ADDED
@@ -0,0 +1,23 @@
1
+ require 'logger'
2
+ require 'polar/adapter'
3
+ require 'polar/errors'
4
+ require 'polar/groups'
5
+ require 'polar/permissions'
6
+ require 'polar/frameworks/rails'
7
+
8
+ module Polar
9
+
10
+ class << self
11
+ attr_accessor :logger
12
+ end
13
+
14
+ def self.define(type)
15
+ case type
16
+ when :permissions
17
+ yield(Polar::Permissions.define)
18
+ when :groups
19
+ yield(Polar::Groups.define)
20
+ end
21
+ end
22
+ self.logger = Logger.new(STDOUT)
23
+ end
@@ -0,0 +1,7 @@
1
+ require File.expand_path(File.dirname(__FILE__) + '/adapters/active_record')
2
+
3
+ module Polar #nodoc
4
+ module Adapter
5
+
6
+ end
7
+ end
@@ -0,0 +1,86 @@
1
+ require 'active_record'
2
+
3
+ class UserPermission < ActiveRecord::Base;
4
+ def self.get_for_subject(subject_id)
5
+ find_all_by_user_id(subject_id)
6
+ end
7
+ end
8
+
9
+ class UserGroup < ActiveRecord::Base;
10
+ def self.get_for_subject(subject_id)
11
+ find_all_by_user_id(subject_id)
12
+ end
13
+ end
14
+
15
+ module Polar #nodoc
16
+ module ActiveRecordExtensions
17
+
18
+ def self.included(base)
19
+ base.extend(ClassMethods)
20
+ base.send(:include, InstanceMethods)
21
+ end
22
+
23
+ module InstanceMethods
24
+ def permission_object
25
+ UserPermission
26
+ end
27
+
28
+ def group_object
29
+ UserGroup
30
+ end
31
+
32
+ def permissions
33
+ return @permissions if defined?(@permissions)
34
+ auth = Polar::Permissions.new
35
+ auth.fill_subject_from_external_store(self.id, permission_object, group_object)
36
+ @permissions = auth.subject_store.sort { |a,b| a.to_s <=> b.to_s }
37
+ end
38
+
39
+ def groups
40
+ return @groups if defined?(@groups)
41
+ auth = Polar::Groups.new
42
+ auth.fill_subject_from_external_store(self.id, group_object)
43
+ @groups = auth.subject_store.sort { |a,b| a.to_s <=> b.to_s }
44
+ end
45
+
46
+ # Check whenever specific subject has right permission assigned to him
47
+ # either via defaults defined in the model or the database
48
+ def can?(permission)
49
+ raise Polar::PermissionNotDefined unless Polar::Permissions.defined_store.has_key?(permission)
50
+ permissions.include? permission
51
+ end
52
+
53
+ # Check whenever specific subject is a member of a right group
54
+ # either via defaults defined in the model or the database
55
+ def member_of?(group)
56
+ groups.include? group
57
+ end
58
+
59
+ end
60
+
61
+ module ClassMethods
62
+
63
+ def acts_as_polar
64
+ end
65
+
66
+ def owner(authorization_subject)
67
+ # Return owner
68
+ end
69
+
70
+ def default(kind)
71
+ case kind
72
+ when :permissions
73
+ # Permissions
74
+ yield(Polar::DefaultPermissions.instance)
75
+ when :groups
76
+ # Groups
77
+ yield(Polar::DefaultGroups.instance)
78
+ end
79
+ end
80
+ end
81
+ end
82
+ end
83
+
84
+ if defined? ActiveRecord::Base
85
+ ActiveRecord::Base.send(:include, Polar::ActiveRecordExtensions)
86
+ end
@@ -0,0 +1,7 @@
1
+ module Polar #nodoc
2
+ class PermissionNotDefinedButSetAsDefault < StandardError; end
3
+ class PermissionNotDefined < StandardError; end
4
+ class AuthorizationFailureNoUser < StandardError; end
5
+ class AuthorizationFailureDenyPermission < StandardError; end
6
+ class AuthorizationFailureMissedPermission < StandardError; end
7
+ end
@@ -0,0 +1,55 @@
1
+ require 'action_controller'
2
+
3
+ module Polar #nodoc
4
+ module ActionControllerExtensions
5
+
6
+ def self.included(base)
7
+ base.extend(ClassMethods)
8
+ base.send(:include, InstanceMethods)
9
+ base.class_eval do
10
+ before_filter "authorized?"
11
+ end
12
+ end
13
+
14
+ module InstanceMethods
15
+ def authorized?
16
+ begin
17
+ name = "#{controller_path.gsub('/', '__')}_controller".to_sym
18
+ if Polar::Permissions.for_controller.has_key?(name)
19
+ perm_info = Polar::Permissions.for_controller[name]
20
+ action = perm_info.has_key?(action_name.to_sym) ? action_name.to_sym : :all
21
+ user = current_user
22
+ if perm_info[:action].present?
23
+ perm_info[action][:deny].each do |deny_perm|
24
+ raise Polar::AuthorizationFailureNoUser if user.nil?
25
+ raise Polar::AuthorizationFailureDenyPermission if user.can?(deny_perm)
26
+ end
27
+ perm_info[action][:allow].each do |allow_perm|
28
+ raise Polar::AuthorizationFailureNoUser if user.nil?
29
+ raise Polar::AuthorizationFailureMissedPermission unless user.can?(allow_perm)
30
+ end
31
+ end
32
+ end
33
+ rescue Polar::AuthorizationFailureNoUser
34
+ logger.debug "=> No valid User found"
35
+ redirect_to root_path
36
+ rescue Polar::AuthorizationFailureDenyPermission
37
+ logger.debug "=> User #{current_user.id} has :deny permission on this action"
38
+ redirect_to root_path
39
+ rescue Polar::AuthorizationFailureMissedPermission
40
+ logger.debug "=> Authorization Failure :: User #{current_user.id} doesn't have required permissions"
41
+ redirect_to root_path
42
+ end
43
+ return true
44
+ end
45
+ end
46
+
47
+ module ClassMethods
48
+
49
+ end
50
+ end
51
+ end
52
+
53
+ if defined? ActionController::Base
54
+ ActionController::Base.send(:include, Polar::ActionControllerExtensions)
55
+ end
@@ -0,0 +1,71 @@
1
+ module Polar #nodoc
2
+ class DefaultGroups
3
+
4
+ # This method is executed whenever a default group is defined
5
+ # in subject's model
6
+ def method_missing(method, *params)
7
+ Groups.instance.subject_store << method
8
+ self
9
+ end
10
+
11
+ # Protects from creating more than one instance of this class
12
+ def self.instance
13
+ @__instance__ ||= new
14
+ end
15
+
16
+ end
17
+
18
+ class Groups
19
+ attr_accessor :defined_groups_store
20
+ attr_accessor :subject_store
21
+
22
+ def initialize(instance_object = false)
23
+ @defined_groups_store ||= []
24
+ @subject_store ||= []
25
+ unless instance_object
26
+ @defined_groups_store = self.class.instance.defined_groups_store.clone
27
+ @subject_store = self.class.instance.subject_store.clone
28
+ end
29
+
30
+ self
31
+ end
32
+
33
+ def self.instance
34
+ @__instance__ ||= new(true)
35
+ end
36
+
37
+ def self.define(&block)
38
+ self
39
+ end
40
+
41
+ def self.method_missing(method, &block)
42
+ yield GroupHash.new(method) if block_given?
43
+ end
44
+
45
+ def self.defined_store
46
+ @defined_groups_store ||= {}
47
+ end
48
+
49
+ def fill_subject_from_external_store(subject_id, storage)
50
+ storage.get_for_subject(subject_id).each do |group|
51
+ self.subject_store << group.group_name.to_sym
52
+ end
53
+ end
54
+ end
55
+
56
+ class GroupHash < Hash
57
+
58
+ def initialize(method)
59
+ self[:group_name] = method.to_sym
60
+ end
61
+
62
+ def have(*params)
63
+ self[:params] = params
64
+ Polar::Groups.defined_store[self[:group_name]] = self
65
+ end
66
+
67
+ def deny(*params)
68
+
69
+ end
70
+ end
71
+ end
@@ -0,0 +1,101 @@
1
+ module Polar #nodoc
2
+ class DefaultPermissions
3
+
4
+ # This method is executed whenever a default permission is defined
5
+ # in subject's model
6
+ def method_missing(method, *params)
7
+ Permissions.instance.subject_store << method.to_sym
8
+ self
9
+ end
10
+
11
+ # Protects from creating more than one instance of this class
12
+ def self.instance
13
+ @__instance__ ||= new
14
+ end
15
+
16
+ end
17
+
18
+ class Permissions
19
+ attr_accessor :defined_permissions_store
20
+ attr_accessor :subject_store
21
+ attr_accessor :permissions_for_controller
22
+
23
+ def initialize(instance_object = false)
24
+ @defined_permissions_store ||= []
25
+ @subject_store ||= []
26
+ unless instance_object
27
+ @defined_permissions_store = self.class.instance.defined_permissions_store.clone
28
+ @subject_store = self.class.instance.subject_store.clone
29
+ end
30
+
31
+ self
32
+ end
33
+
34
+ def self.instance
35
+ @__instance__ ||= new(true)
36
+ end
37
+
38
+ def self.define(&block)
39
+ self
40
+ end
41
+
42
+ def self.method_missing(method, &block)
43
+ yield PermissionHash.new(method) if block_given?
44
+ end
45
+
46
+ def self.defined_store
47
+ @defined_permissions_store ||= {}
48
+ end
49
+
50
+ def self.for_controller
51
+ @permissions_for_controller ||= {}
52
+ end
53
+
54
+ def self.add_for_controller(perm_hash)
55
+ controller = perm_hash[:object].to_sym
56
+ actions = perm_hash[:params].present? && perm_hash[:params].has_key?(:only) ? perm_hash[:params][:only] : [:all]
57
+ for_controller[controller] ||= {}
58
+ actions.each do |action|
59
+ for_controller[controller][action] ||= {:allow => [], :deny => []}
60
+ for_controller[controller][action][perm_hash[:access_type]] << perm_hash[:permission_name]
61
+ end
62
+ end
63
+
64
+ def fill_subject_from_external_store(subject_id, perm_storage, group_storage)
65
+ perm_storage.get_for_subject(subject_id).each do |perm|
66
+ self.subject_store << perm.permission_name.to_sym
67
+ end
68
+ groups = Polar::Groups.new
69
+ groups.fill_subject_from_external_store(subject_id, group_storage)
70
+ groups.subject_store.each do |group|
71
+ if Polar::Groups.defined_store.has_key?(group.to_sym)
72
+ self.subject_store.concat(Polar::Groups.defined_store[group.to_sym][:params])
73
+ end
74
+ end
75
+ end
76
+ end
77
+
78
+ class PermissionHash < Hash
79
+
80
+ def initialize(method)
81
+ self[:permission_name] = method.to_sym
82
+ end
83
+
84
+ def allow(*params)
85
+ add(:allow, params)
86
+ end
87
+
88
+ def deny(*params)
89
+ add(:deny, params)
90
+ end
91
+
92
+ def add(perm_type, params)
93
+ self[:access_type] = perm_type
94
+ self[:object] = params.shift
95
+ self[:params] = params.first
96
+ Polar::Permissions.add_for_controller(self)
97
+ Polar::Permissions.defined_store[self[:permission_name]] ||= []
98
+ Polar::Permissions.defined_store[self[:permission_name]] << self
99
+ end
100
+ end
101
+ end
@@ -0,0 +1,54 @@
1
+ require File.expand_path(File.dirname(__FILE__) + '/spec_helper')
2
+
3
+ describe Polar do
4
+ before do
5
+ @user = User.create
6
+ end
7
+
8
+ it "should respond to default" do
9
+ User.should respond_to(:default)
10
+ end
11
+
12
+ it "should respond to owner" do
13
+ User.should respond_to(:owner)
14
+ end
15
+
16
+ it "should return default permissions for user" do
17
+ @user.permissions
18
+ end
19
+
20
+ it "should check if user is a member of specific group" do
21
+ @user.member_of?(:clients).should be(true)
22
+ end
23
+
24
+ it "should return true if user is a member of a group stored in database" do
25
+ UserGroup.create(:user_id => @user.id, :group_name => "test_group")
26
+ UserGroup.create(:user_id => @user.id, :group_name => "another_group")
27
+ @user.member_of?(:test_group).should be(true)
28
+ end
29
+
30
+ it "should check and return false if user is NOT a member of specific group" do
31
+ @user.member_of?(:not_existing_group).should be(false)
32
+ end
33
+
34
+ it "should check if user has specific permission" do
35
+ @user.can?(:edit_profile).should be(true)
36
+ end
37
+
38
+ it "should return false for permission NOT assigned for specific, even in database" do
39
+ @user.can?(:add_addresses).should be(false)
40
+ end
41
+
42
+ it "should return true for permission assigned for specific user in database" do
43
+ UserPermission.create(:user_id => @user.id, :permission_name => "add_addresses")
44
+ @user.can?(:add_addresses).should be(true)
45
+ end
46
+
47
+ it "should return false if user DO NOT have specific permission" do
48
+ lambda {
49
+ @user.can?(:do_something_that_doesnt_exist)
50
+ }.should raise_error(Polar::PermissionNotDefined)
51
+ end
52
+
53
+ end
54
+
@@ -0,0 +1,94 @@
1
+ $LOAD_PATH.unshift(File.dirname(__FILE__))
2
+ $LOAD_PATH.unshift(File.join(File.dirname(__FILE__), '..', 'lib'))
3
+
4
+ require 'rubygems'
5
+ require 'polar'
6
+ require 'spec'
7
+ require 'spec/autorun'
8
+ require 'active_record'
9
+
10
+ Spec::Runner.configure do |config|
11
+ #EMPTY
12
+ end
13
+
14
+
15
+ ##########################################################################
16
+ # Active Record connection
17
+ ##########################################################################
18
+
19
+ begin
20
+ ActiveRecord::Base.establish_connection(:adapter => "sqlite3", :database => ":memory:")
21
+ rescue ArgumentError
22
+ ActiveRecord::Base.establish_connection(:adapter => "sqlite3", :dbfile => ":memory:")
23
+ end
24
+
25
+
26
+ ##########################################################################
27
+ # Database schema
28
+ ##########################################################################
29
+
30
+ ActiveRecord::Base.configurations = true
31
+ ActiveRecord::Schema.define(:version => 1) do
32
+ create_table :users do |t|
33
+ t.string :name
34
+ t.datetime :created_at
35
+ t.datetime :updated_at
36
+ end
37
+
38
+ create_table :user_permissions do |t|
39
+ t.integer :user_id
40
+ t.string :permission_name
41
+ end
42
+
43
+ create_table :user_groups do |t|
44
+ t.integer :user_id
45
+ t.string :group_name
46
+ end
47
+
48
+ create_table :groups do |t|
49
+ t.string :group_name
50
+ end
51
+
52
+ create_table :permission_groups do |t|
53
+ t.string :permission_name
54
+ t.integer :group_id
55
+ end
56
+
57
+ end
58
+
59
+ ##########################################################################
60
+ # Define permissions
61
+ ##########################################################################
62
+
63
+ Polar.define :permissions do |gp|
64
+ gp.edit_profile do |c|
65
+ c.allow :users_controller, :only => [:edit, :update]
66
+ end
67
+
68
+ gp.add_addresses do |c|
69
+ c.allow :addresses_controller, :only => [:new, :create]
70
+ end
71
+ end
72
+
73
+ ##########################################################################
74
+ # Define groups
75
+ ##########################################################################
76
+
77
+ Polar.define :groups do |gg|
78
+ gg.administrators do |a|
79
+ a.have :add_addresses, :edit_profile
80
+ end
81
+
82
+ gg.clients do |c|
83
+ c.have :edit_profile
84
+ end
85
+ end
86
+
87
+ class User < ActiveRecord::Base
88
+ include Polar::ActiveRecordExtensions
89
+ acts_as_polar
90
+
91
+ default :groups do |g|
92
+ g.clients
93
+ end
94
+ end
metadata ADDED
@@ -0,0 +1,83 @@
1
+ --- !ruby/object:Gem::Specification
2
+ name: polar
3
+ version: !ruby/object:Gem::Version
4
+ hash: 21
5
+ prerelease: false
6
+ segments:
7
+ - 0
8
+ - 2
9
+ - 1
10
+ version: 0.2.1
11
+ platform: ruby
12
+ authors:
13
+ - Grzegorz Kazulak
14
+ - Lukasz Tackowiak
15
+ autorequire:
16
+ bindir: bin
17
+ cert_chain: []
18
+
19
+ date: 2010-07-29 00:00:00 +02:00
20
+ default_executable:
21
+ dependencies: []
22
+
23
+ description: Control access like a bear
24
+ email: grzegorz.kazulak@gmail.com
25
+ executables: []
26
+
27
+ extensions: []
28
+
29
+ extra_rdoc_files:
30
+ - README.md
31
+ files:
32
+ - .gitignore
33
+ - Polar.gemspec
34
+ - README.md
35
+ - Rakefile
36
+ - VERSION
37
+ - init.rb
38
+ - lib/polar.rb
39
+ - lib/polar/adapter.rb
40
+ - lib/polar/adapters/active_record.rb
41
+ - lib/polar/errors.rb
42
+ - lib/polar/frameworks/rails.rb
43
+ - lib/polar/groups.rb
44
+ - lib/polar/permissions.rb
45
+ - spec/polar_spec.rb
46
+ - spec/spec_helper.rb
47
+ has_rdoc: true
48
+ homepage: http://github.com/grzegorzkazulak/polar
49
+ licenses: []
50
+
51
+ post_install_message:
52
+ rdoc_options:
53
+ - --charset=UTF-8
54
+ require_paths:
55
+ - lib
56
+ required_ruby_version: !ruby/object:Gem::Requirement
57
+ none: false
58
+ requirements:
59
+ - - ">="
60
+ - !ruby/object:Gem::Version
61
+ hash: 3
62
+ segments:
63
+ - 0
64
+ version: "0"
65
+ required_rubygems_version: !ruby/object:Gem::Requirement
66
+ none: false
67
+ requirements:
68
+ - - ">="
69
+ - !ruby/object:Gem::Version
70
+ hash: 3
71
+ segments:
72
+ - 0
73
+ version: "0"
74
+ requirements: []
75
+
76
+ rubyforge_project: polar
77
+ rubygems_version: 1.3.7
78
+ signing_key:
79
+ specification_version: 3
80
+ summary: Access control for polar bears
81
+ test_files:
82
+ - spec/polar_spec.rb
83
+ - spec/spec_helper.rb