Skip to content

Commit

Permalink
Merge pull request #86 from nycrecords/feature/GPP-357
Browse files Browse the repository at this point in the history
Feature/GPP-357: T429: Limit the number of concurrent sessions for each account
  • Loading branch information
johnyu95 authored Feb 4, 2020
2 parents 051b767 + efb38c8 commit 4ad78b0
Show file tree
Hide file tree
Showing 9 changed files with 53 additions and 7 deletions.
21 changes: 21 additions & 0 deletions app/controllers/application_controller.rb
Original file line number Diff line number Diff line change
@@ -1,4 +1,6 @@
class ApplicationController < ActionController::Base
before_action :check_concurrent_session

auto_session_timeout 30.minutes
before_timedout_action

Expand All @@ -15,10 +17,29 @@ class ApplicationController < ActionController::Base

protect_from_forgery with: :exception, except: [:saml]

# Redirect user to sign_out if user is has another session
def check_concurrent_session
return unless is_already_logged_in?
session[:duplicate] = true
redirect_to main_app.destroy_user_session_path
end

# Return boolean value of whether user is logged in
def is_already_logged_in?
current_user && (session.id != current_user.unique_session_id)
end

# Redirect to location that triggered authentication or to homepage
def after_sign_in_path_for(resource)
# Generate new session id and update in user.unique_session_id
session.options[:id] = session.instance_variable_get(:@by).generate_sid
session.options[:renew] = false
resource.update_attributes(unique_session_id: session.id)

# Get path to Government Publications collection or homepage if collection not found
gpp_collection = Collection.where(title: 'Government Publications').first
path = gpp_collection.present? ? hyrax.collection_path(gpp_collection) : root_path

stored_location_for(resource) || path
end
end
5 changes: 5 additions & 0 deletions app/controllers/sessions_controller.rb
Original file line number Diff line number Diff line change
@@ -1,11 +1,16 @@
class SessionsController < Devise::SessionsController
skip_before_action :check_concurrent_session

auto_session_timeout_actions
SAML_SETTINGS = Devise.omniauth_configs[:saml].strategy

def destroy
# Preserve the saml_uid in the session
saml_uid = session['saml_uid']
duplicate = session[:duplicate]
user = current_user
super do
user.update_attributes(unique_session_id: nil) unless duplicate
session['saml_uid'] = saml_uid
response.headers['Clear-Site-Data'] = '"*"'
end
Expand Down
2 changes: 2 additions & 0 deletions app/controllers/users/omniauth_callbacks_controller.rb
Original file line number Diff line number Diff line change
@@ -1,5 +1,7 @@
# Controller which implements Omniauth callbacks.
class Users::OmniauthCallbacksController < Devise::OmniauthCallbacksController
skip_before_action :check_concurrent_session

include NYCID
def saml
saml_attrs = request.env['omniauth.auth'].extra.response_object.attributes
Expand Down
2 changes: 1 addition & 1 deletion app/views/_user_util_links.html.erb
Original file line number Diff line number Diff line change
Expand Up @@ -31,7 +31,7 @@
<% end %>
<% else %>
<li class="nav-item">
<%= link_to t("hyrax.toolbar.profile.login"), main_app.new_user_session_path, role: 'button' %>
<%= link_to t("hyrax.toolbar.profile.login"), main_app.user_saml_omniauth_authorize_path %>
</li>
<% end %>

Expand Down
6 changes: 3 additions & 3 deletions config/devise_saml.yml
Original file line number Diff line number Diff line change
Expand Up @@ -11,9 +11,9 @@ default: &default
want_assertions_signed: true
want_assertions_encrypted: false
want_messages_signed: false
metadata_signed: false
signature_method: "http://www.w3.org/2000/09/xmldsig#rsa-sha1"
digest_method: "http://www.w3.org/2000/09/xmldsig#sha1"
metadata_signed: true
signature_method: "http://www.w3.org/2001/04/xmldsig-more#rsa-sha256"
digest_method: "http://www.w3.org/2001/04/xmlenc#sha256"


development:
Expand Down
14 changes: 14 additions & 0 deletions config/initializers/controller_override.rb
Original file line number Diff line number Diff line change
@@ -0,0 +1,14 @@
# frozen_string_literal: true

# OVERRIDE: This overrides deny_access_for_anonymous_user on Controller and renders unauthorized.
#
# Base file: https://github.com/samvera/hyrax/blob/2.5.1/app/controllers/concerns/hyrax/controller.rb
Hyrax::Controller.class_eval do
def deny_access_for_anonymous_user(exception, json_message)
session['user_return_to'.freeze] = request.url
respond_to do |wants|
wants.html { render 'hyrax/base/unauthorized', status: :unauthorized }
wants.json { render_json_response(response_type: :unauthorized, message: json_message) }
end
end
end
2 changes: 0 additions & 2 deletions config/routes.rb
Original file line number Diff line number Diff line change
Expand Up @@ -13,8 +13,6 @@
devise_for :users, controllers: { omniauth_callbacks: 'users/omniauth_callbacks' }

devise_scope :user do
get 'sign_in', to: 'omniauth#new', as: :new_user_session
post 'sign_in', to: 'omniauth_callbacks#saml', as: :new_session
get 'sign_out', to: 'sessions#destroy', as: :destroy_user_session
get 'active' => 'sessions#active'
get 'timeout' => 'sessions#timeout'
Expand Down
5 changes: 5 additions & 0 deletions db/migrate/20200130152004_add_unique_session_id_to_users.rb
Original file line number Diff line number Diff line change
@@ -0,0 +1,5 @@
class AddUniqueSessionIdToUsers < ActiveRecord::Migration[5.1]
def change
add_column :users, :unique_session_id, :string
end
end
3 changes: 2 additions & 1 deletion db/schema.rb
Original file line number Diff line number Diff line change
Expand Up @@ -10,7 +10,7 @@
#
# It's strongly recommended that you check this file into your version control system.

ActiveRecord::Schema.define(version: 20200108193343) do
ActiveRecord::Schema.define(version: 20200130152004) do

# These are extensions that must be enabled in order to support this database
enable_extension "plpgsql"
Expand Down Expand Up @@ -598,6 +598,7 @@
t.boolean "active", default: false
t.boolean "nyc_employee", default: false
t.boolean "has_nyc_account", default: false
t.string "unique_session_id"
t.index ["email"], name: "index_users_on_email", unique: true
t.index ["reset_password_token"], name: "index_users_on_reset_password_token", unique: true
end
Expand Down

0 comments on commit 4ad78b0

Please sign in to comment.