Removing .DS_Store and .pid files from repository.
[merb_radiant.git] / lib / login_system.rb
blob0b0bc900a9cab6228e67884dcac4352b2ab50e48
1 module LoginSystem
2   def self.append_features(base)
3     base.class_eval %{
4       before :authenticate
5       
6       @@controllers_where_no_login_required = []
7       @@controller_permissions = Hash.new { |h, k| h[k] = Hash.new { |h, k| h[k] = Hash.new } }
8       helper_method :current_user
9     }
10     base.extend ClassMethods
11     super
12   end
13   
14   protected
15   
16     def current_user
17       @current_user ||= User.find(session['user_id']) rescue nil
18     end
19     
20     def current_user=(value=nil)
21       if value && value.is_a?(User)
22         @current_user = value
23         session['user_id'] = value.id 
24       else
25         @current_user = nil
26         session['user_id'] = nil
27       end
28       @current_user
29     end
30     
31     def authenticate
32       action = params['action'].to_s.intern
33       if no_login_required? or (current_user and user_has_access_to_action?(action))
34         true
35       else
36         if current_user
37           permissions = self.class.controller_permissions[self.class][action]
38           flash[:error] = permissions[:denied_message] || 'Access denied.'
39           redirect_to permissions[:denied_url] || { :action => :index }
40         else
41           redirect_to login_url
42         end
43         false
44       end
45     end
46   
47     def no_login_required?
48       controllers = self.class.controllers_where_no_login_required
49       controllers.include?(self.class)
50     end
51   
52     def user_has_role?(role)
53       current_user.send("#{role}?")
54     end
55     
56     def user_has_access_to_action?(action)
57       permissions = self.class.controller_permissions[self.class][action]
58       case
59       when allowed_roles = permissions[:when]
60         allowed_roles = [allowed_roles].flatten
61         allowed_roles.each do |role|
62           return true if user_has_role?(role)
63         end
64         false
65       when condition_method = permissions[:if]
66         send(condition_method)
67       else
68         true
69       end
70     end
71   
72   module ClassMethods
73     def no_login_required
74       controllers_where_no_login_required << self
75     end
76     
77     def only_allow_access_to(*args)
78       options = {}
79       options = args.pop.dup if args.last.kind_of?(Hash)
80       options.symbolize_keys!
81       actions = args.map { |a| a.to_s.intern }
82       actions.each do |action|
83         controller_permissions[self][action] = options
84       end
85     end
86     
87     def controller_permissions
88       self.class_eval %{ @@controller_permissions }
89     end
90     
91     def controllers_where_no_login_required
92       self.class_eval %{ @@controllers_where_no_login_required }
93     end
94   end
95 end