Description:
add ip whitelisting
Commit status:
[Not Reviewed]
References:
Comments:
0 Commit comments 0 Inline Comments
Unresolved TODOs:
There are no unresolved TODOs
Add another comment

r755:17c54fa350f2 - - 2 files changed: 55 inserted, 13 deleted

@@ -1,19 +1,23
1 + require 'ipaddr'
2 +
1 class ApplicationController < ActionController::Base
3 class ApplicationController < ActionController::Base
2 protect_from_forgery
4 protect_from_forgery
3
5
4 before_action :current_user
6 before_action :current_user
5
7
6 SINGLE_USER_MODE_CONF_KEY = 'system.single_user_mode'
8 SINGLE_USER_MODE_CONF_KEY = 'system.single_user_mode'
7 MULTIPLE_IP_LOGIN_CONF_KEY = 'right.multiple_ip_login'
9 MULTIPLE_IP_LOGIN_CONF_KEY = 'right.multiple_ip_login'
10 + ALLOW_WHITELIST_IP_ONLY_CONF_KEY = 'right.allow_whitelist_ip_only'
11 + WHITELIST_IP_CONF_KEY = 'right.whitelist_ip'
8
12
9 #report and redirect for unauthorized activities
13 #report and redirect for unauthorized activities
10 def unauthorized_redirect
14 def unauthorized_redirect
11 flash[:notice] = 'You are not authorized to view the page you requested'
15 flash[:notice] = 'You are not authorized to view the page you requested'
12 redirect_to :controller => 'main', :action => 'login'
16 redirect_to :controller => 'main', :action => 'login'
13 end
17 end
14
18
15 # Returns the current logged-in user (if any).
19 # Returns the current logged-in user (if any).
16 def current_user
20 def current_user
17 return nil unless session[:user_id]
21 return nil unless session[:user_id]
18 @current_user ||= User.find(session[:user_id])
22 @current_user ||= User.find(session[:user_id])
19 end
23 end
@@ -37,102 +41,127
37 end
41 end
38 end
42 end
39
43
40 def testcase_authorization
44 def testcase_authorization
41 #admin always has privileged
45 #admin always has privileged
42 if @current_user.admin?
46 if @current_user.admin?
43 return true
47 return true
44 end
48 end
45
49
46 unauthorized_redirect unless GraderConfiguration["right.view_testcase"]
50 unauthorized_redirect unless GraderConfiguration["right.view_testcase"]
47 end
51 end
48
52
53 +
49 protected
54 protected
50
55
56 + #redirect to root (and also force logout)
57 + #if the user is not logged_in or the system is in "ADMIN ONLY" mode
51 def authenticate
58 def authenticate
52 unless session[:user_id]
59 unless session[:user_id]
53 flash[:notice] = 'You need to login'
60 flash[:notice] = 'You need to login'
54 if GraderConfiguration[SINGLE_USER_MODE_CONF_KEY]
61 if GraderConfiguration[SINGLE_USER_MODE_CONF_KEY]
55 flash[:notice] = 'You need to login but you cannot log in at this time'
62 flash[:notice] = 'You need to login but you cannot log in at this time'
56 end
63 end
57 redirect_to :controller => 'main', :action => 'login'
64 redirect_to :controller => 'main', :action => 'login'
58 return false
65 return false
59 end
66 end
60
67
61 -
62 # check if run in single user mode
68 # check if run in single user mode
63 if GraderConfiguration[SINGLE_USER_MODE_CONF_KEY]
69 if GraderConfiguration[SINGLE_USER_MODE_CONF_KEY]
64 - if @current_user==nil or (not @current_user.admin?)
70 + if @current_user==nil || (not @current_user.admin?)
65 flash[:notice] = 'You cannot log in at this time'
71 flash[:notice] = 'You cannot log in at this time'
66 redirect_to :controller => 'main', :action => 'login'
72 redirect_to :controller => 'main', :action => 'login'
67 return false
73 return false
68 end
74 end
69 - return true
70 end
75 end
71
76
72 # check if the user is enabled
77 # check if the user is enabled
73 - unless @current_user.enabled? or @current_user.admin?
78 + unless @current_user.enabled? || @current_user.admin?
74 flash[:notice] = 'Your account is disabled'
79 flash[:notice] = 'Your account is disabled'
75 redirect_to :controller => 'main', :action => 'login'
80 redirect_to :controller => 'main', :action => 'login'
76 return false
81 return false
77 end
82 end
78
83
84 + # check if user ip is allowed
85 + unless @current_user.admin? || !GraderConfiguration[ALLOW_WHITELIST_IP_ONLY_CONF_KEY]
86 + unless is_request_ip_allowed?
87 + flash[:notice] = 'Your IP is not allowed'
88 + redirect_to root_path
89 + end
90 + end
91 +
79 if GraderConfiguration.multicontests?
92 if GraderConfiguration.multicontests?
80 return true if @current_user.admin?
93 return true if @current_user.admin?
81 begin
94 begin
82 if @current_user.contest_stat(true).forced_logout
95 if @current_user.contest_stat(true).forced_logout
83 flash[:notice] = 'You have been automatically logged out.'
96 flash[:notice] = 'You have been automatically logged out.'
84 redirect_to :controller => 'main', :action => 'index'
97 redirect_to :controller => 'main', :action => 'index'
85 end
98 end
86 rescue
99 rescue
87 end
100 end
88 end
101 end
89 return true
102 return true
90 end
103 end
91
104
105 + #redirect to root (and also force logout)
106 + #if the user use different ip from the previous connection
107 + # only applicable when MULTIPLE_IP_LOGIN options is false only
92 def authenticate_by_ip_address
108 def authenticate_by_ip_address
93 #this assume that we have already authenticate normally
109 #this assume that we have already authenticate normally
94 unless GraderConfiguration[MULTIPLE_IP_LOGIN_CONF_KEY]
110 unless GraderConfiguration[MULTIPLE_IP_LOGIN_CONF_KEY]
95 user = User.find(session[:user_id])
111 user = User.find(session[:user_id])
96 - if (not user.admin? and user.last_ip and user.last_ip != request.remote_ip)
112 + if (not @current_user.admin? && user.last_ip && user.last_ip != request.remote_ip)
97 flash[:notice] = "You cannot use the system from #{request.remote_ip}. Your last ip is #{user.last_ip}"
113 flash[:notice] = "You cannot use the system from #{request.remote_ip}. Your last ip is #{user.last_ip}"
98 redirect_to :controller => 'main', :action => 'login'
114 redirect_to :controller => 'main', :action => 'login'
99 puts "CHEAT: user #{user.login} tried to login from '#{request.remote_ip}' while last ip is '#{user.last_ip}' at #{Time.zone.now}"
115 puts "CHEAT: user #{user.login} tried to login from '#{request.remote_ip}' while last ip is '#{user.last_ip}' at #{Time.zone.now}"
100 return false
116 return false
101 end
117 end
102 unless user.last_ip
118 unless user.last_ip
103 user.last_ip = request.remote_ip
119 user.last_ip = request.remote_ip
104 user.save
120 user.save
105 end
121 end
106 end
122 end
107 return true
123 return true
108 end
124 end
109
125
110 def authorization
126 def authorization
111 return false unless authenticate
127 return false unless authenticate
112 user = User.find(session[:user_id])
128 user = User.find(session[:user_id])
113 unless user.roles.detect { |role|
129 unless user.roles.detect { |role|
114 role.rights.detect{ |right|
130 role.rights.detect{ |right|
115 right.controller == self.class.controller_name and
131 right.controller == self.class.controller_name and
116 - (right.action == 'all' or right.action == action_name)
132 + (right.action == 'all' || right.action == action_name)
117 }
133 }
118 }
134 }
119 flash[:notice] = 'You are not authorized to view the page you requested'
135 flash[:notice] = 'You are not authorized to view the page you requested'
120 #request.env['HTTP_REFERER'] ? (redirect_to :back) : (redirect_to :controller => 'login')
136 #request.env['HTTP_REFERER'] ? (redirect_to :back) : (redirect_to :controller => 'login')
121 redirect_to :controller => 'main', :action => 'login'
137 redirect_to :controller => 'main', :action => 'login'
122 return false
138 return false
123 end
139 end
124 end
140 end
125
141
126 def verify_time_limit
142 def verify_time_limit
127 return true if session[:user_id]==nil
143 return true if session[:user_id]==nil
128 user = User.find(session[:user_id], :include => :site)
144 user = User.find(session[:user_id], :include => :site)
129 - return true if user==nil or user.site == nil
145 + return true if user==nil || user.site == nil
130 if user.contest_finished?
146 if user.contest_finished?
131 flash[:notice] = 'Error: the contest you are participating is over.'
147 flash[:notice] = 'Error: the contest you are participating is over.'
132 redirect_to :back
148 redirect_to :back
133 return false
149 return false
134 end
150 end
135 return true
151 return true
136 end
152 end
137
153
154 + def is_request_ip_allowed?
155 + if GraderConfiguration[ALLOW_WHITELIST_IP_ONLY_CONF_KEY]
156 + user_ip = IPAddr.new(request.remote_ip)
157 + GraderConfiguration[WHITELIST_IP_LIST_CONF_KEY].delete(' ').split(',').each do |ips|
158 + allow_ips = IPAddr.new(ips)
159 + unless allow_ips.includes(user_ip)
160 + return false
161 + end
162 + end
163 + end
164 + return true
165 + end
166 +
138 end
167 end
@@ -164,69 +164,82
164 :default_value => 'none',
164 :default_value => 'none',
165 :description => "New user will be assigned to this contest automatically, if it exists. Set to 'none' if there is no default contest."
165 :description => "New user will be assigned to this contest automatically, if it exists. Set to 'none' if there is no default contest."
166 },
166 },
167
167
168 {
168 {
169 :key => 'system.use_problem_group',
169 :key => 'system.use_problem_group',
170 :value_type => 'boolean',
170 :value_type => 'boolean',
171 :default_value => 'false',
171 :default_value => 'false',
172 :description => "If true, available problem to the user will be only ones associated with the group of the user."
172 :description => "If true, available problem to the user will be only ones associated with the group of the user."
173 },
173 },
174
174
175
175
176 + {
177 + :key => 'right.whitelist_ip_only',
178 + :value_type => 'boolean',
179 + :default_value => 'false',
180 + :description => "If true, non-admin user will be able to use the system only when their ip is in the 'whitelist_ip'."
181 + },
182 +
183 + {
184 + :key => 'right.whitelist_ip',
185 + :value_type => 'string',
186 + :default_value => '0.0.0.0/0',
187 + :description => "list of whitelist ip, given in comma separated CIDR notation. For example '161.200.92.0/23, 161.200.80.1/32'"
188 + },
176
189
177 ]
190 ]
178
191
179
192
180 - def create_configuration_key(key,
193 + def create_configuration_key(key,
181 - value_type,
194 + value_type,
182 - default_value,
195 + default_value,
183 description='')
196 description='')
184 - conf = (GraderConfiguration.find_by_key(key) ||
197 + conf = (GraderConfiguration.find_by_key(key) ||
185 GraderConfiguration.new(:key => key,
198 GraderConfiguration.new(:key => key,
186 :value_type => value_type,
199 :value_type => value_type,
187 :value => default_value))
200 :value => default_value))
188 conf.description = description
201 conf.description = description
189 conf.save
202 conf.save
190 end
203 end
191
204
192 def seed_config
205 def seed_config
193 CONFIGURATIONS.each do |conf|
206 CONFIGURATIONS.each do |conf|
194 if conf.has_key? :description
207 if conf.has_key? :description
195 desc = conf[:description]
208 desc = conf[:description]
196 else
209 else
197 desc = ''
210 desc = ''
198 end
211 end
199 - create_configuration_key(conf[:key],
212 + create_configuration_key(conf[:key],
200 conf[:value_type],
213 conf[:value_type],
201 conf[:default_value],
214 conf[:default_value],
202 desc)
215 desc)
203 end
216 end
204 end
217 end
205
218
206 def seed_roles
219 def seed_roles
207 return if Role.find_by_name('admin')
220 return if Role.find_by_name('admin')
208
221
209 role = Role.create(:name => 'admin')
222 role = Role.create(:name => 'admin')
210 user_admin_right = Right.create(:name => 'user_admin',
223 user_admin_right = Right.create(:name => 'user_admin',
211 :controller => 'user_admin',
224 :controller => 'user_admin',
212 :action => 'all')
225 :action => 'all')
213 problem_admin_right = Right.create(:name=> 'problem_admin',
226 problem_admin_right = Right.create(:name=> 'problem_admin',
214 :controller => 'problems',
227 :controller => 'problems',
215 :action => 'all')
228 :action => 'all')
216
229
217 graders_right = Right.create(:name => 'graders_admin',
230 graders_right = Right.create(:name => 'graders_admin',
218 :controller => 'graders',
231 :controller => 'graders',
219 :action => 'all')
232 :action => 'all')
220 -
233 +
221 role.rights << user_admin_right;
234 role.rights << user_admin_right;
222 role.rights << problem_admin_right;
235 role.rights << problem_admin_right;
223 role.rights << graders_right;
236 role.rights << graders_right;
224 role.save
237 role.save
225 end
238 end
226
239
227 def seed_root
240 def seed_root
228 return if User.find_by_login('root')
241 return if User.find_by_login('root')
229
242
230 root = User.new(:login => 'root',
243 root = User.new(:login => 'root',
231 :full_name => 'Administrator',
244 :full_name => 'Administrator',
232 :alias => 'root')
245 :alias => 'root')
You need to be logged in to leave comments. Login now