Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

expand indirect group memberships #90

Closed
wants to merge 14 commits into from
Closed
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Jump to
Jump to file
Failed to load files.
Diff view
Diff view
2 changes: 2 additions & 0 deletions .gitignore
Expand Up @@ -16,3 +16,5 @@ custom/*
resources/dev
.rvmrc
.bundle
vendor/bundle
tmp
2 changes: 2 additions & 0 deletions Gemfile
Expand Up @@ -4,6 +4,8 @@ gem "activesupport", "~> 3.0.0"
gem "sinatra", "~> 1.0"
gem "gettext", "~> 2.1.0"
gem "crypt-isaac", "~> 0.9.1"
gem "pg"
gem "net-ldap", "~> 0.1.1"

group :development do
gem "rack-test"
Expand Down
9 changes: 9 additions & 0 deletions Gemfile.lock
Expand Up @@ -36,7 +36,9 @@ GEM
json_pure (1.4.6)
locale (2.0.5)
mime-types (1.16)
net-ldap (0.1.1)
nokogiri (1.4.4)
pg (0.9.0)
rack (1.2.1)
rack-test (0.5.6)
rack (>= 1.0)
Expand Down Expand Up @@ -70,6 +72,13 @@ PLATFORMS
DEPENDENCIES
activerecord (~> 3.0.0)
activesupport (~> 3.0.0)
capybara
crypt-isaac (~> 0.9.1)
gettext (~> 2.1.0)
net-ldap (~> 0.1.1)
pg
rack-test
rspec
rspec-core
sinatra (~> 1.0)
sqlite3-ruby (~> 1.3.1)
21 changes: 21 additions & 0 deletions lib/casserver/authenticators/ldap.rb
Expand Up @@ -122,6 +122,22 @@ def find_user
return results.first
end

def find_groups(groups)
filter = Array(groups).map { |group| Net::LDAP::Filter.eq('distinguishedName', group) }.reduce(:|)
return @ldap.search(:base => options[:ldap][:base], :filter => filter)
end

def expand_indirect_membership(groups)
indirect_memberof = find_groups(groups).collect { |group| group['memberof'] }.flatten - groups
if indirect_memberof.any?
$LOG.debug "#{self.class}: Indirect memberof: #{indirect_memberof.inspect}"
groups |= indirect_memberof
expand_indirect_membership(groups)
else
groups
end
end

def extract_extra_attributes(ldap_entry)
@extra_attributes = {}
extra_attributes_to_extract.each do |attr|
Expand All @@ -135,6 +151,11 @@ def extract_extra_attributes(ldap_entry)
else
@extra_attributes[attr] = v.to_s
end
if attr == 'memberof' && @options[:ldap][:expand_indirect_membership]
$LOG.debug "#{self.class}: Direct memberof: #{@extra_attributes[attr].inspect}"
@extra_attributes[attr] = expand_indirect_membership(@extra_attributes[attr])
$LOG.debug "#{self.class}: memberof: #{@extra_attributes[attr].inspect}"
end
end
end

Expand Down
7 changes: 7 additions & 0 deletions lib/casserver/server.rb
Expand Up @@ -274,6 +274,7 @@ def self.init_database!
@organization = settings.config[:organization]
@uri_path = settings.config[:uri_path]
@infoline = settings.config[:infoline]
@custom_views = settings.config[:custom_views]
end

# The #.#.# comments (e.g. "2.1.3") refer to section numbers in the CAS protocol spec
Expand Down Expand Up @@ -676,6 +677,12 @@ def serialize_extra_attribute(builder, value)
builder.cdata! value.to_yaml
end
end

def compile_template(engine, data, options, views)
super engine, data, options, settings.config[:custom_views]
rescue Errno::ENOENT
super engine, data, options, views
end
end
end

16 changes: 16 additions & 0 deletions lib/casserver/views/mosaic/_login_form.erb
@@ -0,0 +1,16 @@
<form method="post" action="<%= @form_action || "login" %>">
<input type="hidden" id="lt" name="lt" value="<%= @lt %>" />
<input type="hidden" id="service" name="service" value="<%= @service %>" />
<% if @message %>
<p class="<%= @message[:type] %>"><%= @message[:message] %></p>
<% end %>
<fieldset class='text'>
<label for="login">Login</label>
<input id="login" name="username" type="text" />
</fieldset>
<fieldset class='text'>
<label for="password">Password</label>
<input id="password" name="password" type="password" />
</fieldset>
<a href="#" class="login_submit login_btn">Log in</a>
</form>
23 changes: 23 additions & 0 deletions lib/casserver/views/mosaic/layout.erb
@@ -0,0 +1,23 @@
<!DOCTYPE html>
<html lang='en' xml:lang='en' xmlns='http://www.w3.org/1999/xhtml'>
<head>
<meta content='text/html; charset=utf-8' http-equiv='Content-Type'>
<meta content='IE=7' http-equiv='X-UA-Compatible'>
<meta name='viewport' content='width=device-width, initial-scale=1.0'>

<title><%= @organization %> Login</title>

<link href="<%= "#{@uri_path}/themes/#{@theme}/stylesheets/reset.css" %>" media="screen" rel="stylesheet" type="text/css" />
<link href="<%= "#{@uri_path}/themes/#{@theme}/stylesheets/typography.css" %>" media="screen" rel="stylesheet" type="text/css" />
<link href="<%= "#{@uri_path}/themes/#{@theme}/stylesheets/forms.css" %>" media="screen" rel="stylesheet" type="text/css" />
<link href="<%= "#{@uri_path}/themes/#{@theme}/stylesheets/login.css" %>" media="screen" rel="stylesheet" type="text/css" />
</head>
<body>
<div id='wrapper'>
<%= yield %>
</div>

<script src="https://ajax.googleapis.com/ajax/libs/jquery/1.5.0/jquery.min.js" type="text/javascript"></script>
<script src="<%= "#{@uri_path}/themes/#{@theme}/javascripts/application.js" %>" type="text/javascript"></script>
</body>
</html>
9 changes: 9 additions & 0 deletions lib/casserver/views/mosaic/login.erb
@@ -0,0 +1,9 @@
<h1 class='login_header'><%= @organization %> Login</h1>
<div id='login_box'>
<div class='login_form'>
<%= erb(:_login_form, :layout => false) %>
</div>
</div>
<div class='footer'>
<%= @infoline %>
</div>
Binary file not shown.