refs #9 - CAS-login for redmine with public content.

This is my second attempt. If authentication is required, you will
be redirected to the CAS login page whenever you are not authenticated.
(Except when you visit the default login page.)

If authentication is not required, the login page will show a link,
that allows you to login using CAS.
This commit is contained in:
Johan Vervloet 2014-06-26 15:06:00 +02:00
parent ce83b43e42
commit 86900837ef
7 changed files with 78 additions and 46 deletions

View File

@ -19,8 +19,12 @@ We use [CASino](http://casino.rbcas.com) as CAS server, but it might work with o
### Usage
This plugin was made for redmine installations without public areas ("Authentication required").
The default login page will still work when you access it directly (http://example.com/path-to-redmine/login).
If your installation has no public areas ("Authentication required") and you are not logged in, you will be
redirected to the CAS-login page. The default login page will still work when you access it directly
(http://example.com/path-to-redmine/login).
If your installation is not "Authentication required", the login page will show a link that lets you login
with CAS.
### Single Sign Out, Single Logout

View File

@ -0,0 +1,5 @@
<% if Setting.plugin_redmine_cas[:enabled] %>
<p style="text-align:center;">
<strong><%= link_to("Login with CAS", :controller => "account", :action => "cas") %></strong>
</p>
<% end %>

3
config/routes.rb Normal file
View File

@ -0,0 +1,3 @@
RedmineApp::Application.routes.draw do
get 'cas', :to => 'account#cas'
end

View File

@ -3,6 +3,8 @@ require 'redmine_cas'
require 'redmine_cas/application_controller_patch'
require 'redmine_cas/account_controller_patch'
require_dependency 'redmine_cas_hook_listener'
Redmine::Plugin.register :redmine_cas do
name 'Redmine CAS'
author 'Nils Caspar (Nine Internet Solutions AG)'

View File

@ -15,6 +15,61 @@ module RedmineCAS
logout_user
CASClient::Frameworks::Rails::Filter.logout(self, home_url)
end
def cas
return redirect_to_action('login') unless RedmineCAS.enabled?
if User.current.logged?
# User already logged in.
redirect_back_or_default my_page_path
return
end
# The rest of this file just contains what was in
# application_controller_patch.rb before.
if CASClient::Frameworks::Rails::Filter.filter(self)
user = User.find_by_login(session[:cas_user])
# Auto-create user if possible
if user.nil? && RedmineCAS.autocreate_users?
user = User.new
user.login = session[:cas_user]
user.assign_attributes(RedmineCAS.user_extra_attributes_from_session(session))
return cas_user_not_created(user) if !user.save
user.reload
end
return cas_user_not_found if user.nil?
return cas_account_pending unless user.active?
user.update_attribute(:last_login_on, Time.now)
user.update_attributes(RedmineCAS.user_extra_attributes_from_session(session))
if RedmineCAS.single_sign_out_enabled?
# logged_user= would start a new session and break single sign-out
User.current = user
start_user_session(user)
else
self.logged_user = user
end
redirect_to url_for(params.merge(:ticket => nil))
else
# CASClient called redirect_to
end
end
def cas_account_pending
render_403 :message => l(:notice_account_pending)
end
def cas_user_not_found
render_403 :message => l(:redmine_cas_user_not_found, :user => session[:cas_user])
end
def cas_user_not_created(user)
logger.error "Could not auto-create user: #{user.errors.full_messages.to_sentence}"
render_403 :message => l(:redmine_cas_user_not_created, :user => session[:cas_user])
end
end
end
end

View File

@ -15,8 +15,8 @@ module RedmineCAS
return require_login_without_cas unless RedmineCAS.enabled?
if !User.current.logged?
respond_to do |format|
format.html { login_with_cas }
format.atom { login_with_cas }
format.html { redirect_to :controller => 'account', :action => 'cas' }
format.atom { redirect_to :controller => 'account', :action => 'cas' }
format.xml { head :unauthorized, 'WWW-Authenticate' => 'Basic realm="Redmine API"' }
format.js { head :unauthorized, 'WWW-Authenticate' => 'Basic realm="Redmine API"' }
format.json { head :unauthorized, 'WWW-Authenticate' => 'Basic realm="Redmine API"' }
@ -26,36 +26,6 @@ module RedmineCAS
true
end
def login_with_cas
if CASClient::Frameworks::Rails::Filter.filter(self)
user = User.find_by_login(session[:cas_user])
# Auto-create user if possible
if user.nil? && RedmineCAS.autocreate_users?
user = User.new
user.login = session[:cas_user]
user.assign_attributes(RedmineCAS.user_extra_attributes_from_session(session))
return cas_user_not_created(user) if !user.save
user.reload
end
return cas_user_not_found if user.nil?
return cas_account_pending unless user.active?
user.update_attribute(:last_login_on, Time.now)
user.update_attributes(RedmineCAS.user_extra_attributes_from_session(session))
if RedmineCAS.single_sign_out_enabled?
# logged_user= would start a new session and break single sign-out
User.current = user
start_user_session(user)
else
self.logged_user = user
end
redirect_to url_for(params.merge(:ticket => nil))
else
# CASClient called redirect_to
end
end
def verify_authenticity_token_with_cas
if cas_logout_request?
logger.info 'CAS logout request detected: Skipping validation of authenticity token'
@ -68,18 +38,6 @@ module RedmineCAS
request.post? && params.has_key?('logoutRequest')
end
def cas_account_pending
render_403 :message => l(:notice_account_pending)
end
def cas_user_not_found
render_403 :message => l(:redmine_cas_user_not_found, :user => session[:cas_user])
end
def cas_user_not_created(user)
logger.error "Could not auto-create user: #{user.errors.full_messages.to_sentence}"
render_403 :message => l(:redmine_cas_user_not_created, :user => session[:cas_user])
end
end
end
end

View File

@ -0,0 +1,5 @@
module RedmineCAS
class RedmineCASHookListener < Redmine::Hook::ViewListener
render_on :view_account_login_top, :partial => 'redmine_cas/cas_login_link'
end
end