Module: SamlCamel::SamlHelpers
- Extended by:
- ActiveSupport::Concern
- Included in:
- SamlController
- Defined in:
- app/controllers/concerns/saml_camel/saml_helpers.rb
Constant Summary collapse
- SP_SETTINGS =
JSON.parse(File.read("saml/#{Rails.env}/settings.json"))
Instance Method Summary collapse
- #assign_permit_key ⇒ Object
- #cache_available?(app_cache) ⇒ Boolean
-
#duplicate_response_id?(response_id) ⇒ Boolean
ensures that a saml response can not be used more than once.
-
#expired_session? ⇒ Boolean
Make it so sp sessions only last 1 hour, sp_session is set on a succesfull saml response.
-
#saml_protect ⇒ Object
saml_protect is what is called in the app.
-
#saml_request(host_request) ⇒ Object
this generates a call to the idp, which will then be returned to the consume action the in saml_contorller.
- #set_saml_session_lifetime(permit_key) ⇒ Object
- #valid_ip?(remote_ip) ⇒ Boolean
- #verify_sha_type(response) ⇒ Object
Instance Method Details
#assign_permit_key ⇒ Object
130 131 132 |
# File 'app/controllers/concerns/saml_camel/saml_helpers.rb', line 130 def assign_permit_key session[:saml_session_id] = SecureRandom.base64.chomp.gsub( /\W/, '' ) end |
#cache_available?(app_cache) ⇒ Boolean
112 113 114 115 116 117 118 119 |
# File 'app/controllers/concerns/saml_camel/saml_helpers.rb', line 112 def cache_available?(app_cache) if app_cache true else session[:sp_session] = nil false end end |
#duplicate_response_id?(response_id) ⇒ Boolean
ensures that a saml response can not be used more than once. stores response ids and checks to see if the response id has already been used.
26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 |
# File 'app/controllers/concerns/saml_camel/saml_helpers.rb', line 26 def duplicate_response_id?(response_id) ids = Rails.cache.fetch("response_ids") if ids if ids.include?(response_id) session[:sp_session] = nil raise "SAML response ID already issued." else ids << response_id Rails.cache.fetch("response_ids", expires_in: 1.hours) do ids end end else Rails.cache.fetch("response_ids", expires_in: 1.hours) do [] end end end |
#expired_session? ⇒ Boolean
Make it so sp sessions only last 1 hour, sp_session is set on a succesfull saml response. We check that the session time is less than in hour if so we refresh, otherwise we delete the session
56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 |
# File 'app/controllers/concerns/saml_camel/saml_helpers.rb', line 56 def expired_session? permit_key = session[:saml_session_id].to_sym user_cache = Rails.cache.fetch(permit_key) cache_available?(user_cache) sp_timeout = SP_SETTINGS["settings"]["sp_session_timeout"] sp_lifetime = SP_SETTINGS['settings']["sp_session_lifetime"] set_saml_session_lifetime(permit_key) if user_cache[:session_start_time].nil? sp_session_init_time = user_cache[:session_start_time] if session[:sp_session] #if the session has timed out remove session, otherwise refresh if (Time.now - Time.parse(session[:sp_session])) < sp_timeout.hour session[:sp_session] = Time.now else SamlCamel::Logging.expired_session(session[:saml_attributes]) session[:sp_session] = nil end #if the session has exceeded the allowed lifetime, remove session if (Time.now - sp_session_init_time) > sp_lifetime.hour SamlCamel::Logging.expired_session(session[:saml_attributes]) session[:sp_session] = nil end end end |
#saml_protect ⇒ Object
saml_protect is what is called in the app. it initiates the saml request if there is no active session, or if a user has been idle for over an hour
97 98 99 100 101 102 103 104 105 106 107 108 109 |
# File 'app/controllers/concerns/saml_camel/saml_helpers.rb', line 97 def saml_protect user_cache = cache_available?(Rails.cache.fetch(session[:saml_session_id])) if session[:saml_session_id] && user_cache #sets session[:sp_session] to nil if expired, of if the ip adress changes expired_session? valid_ip?(request.remote_ip) saml_request(request) unless (session[:saml_response_success] || session[:sp_session]) else saml_request(request) end session[:saml_response_success] = nil #keeps us from looping end |
#saml_request(host_request) ⇒ Object
this generates a call to the idp, which will then be returned to the consume action the in saml_contorller
8 9 10 11 12 13 14 15 16 17 18 19 20 21 |
# File 'app/controllers/concerns/saml_camel/saml_helpers.rb', line 8 def saml_request(host_request) request = OneLogin::RubySaml::Authrequest.new assign_permit_key lifetime = SP_SETTINGS['settings']["sp_session_lifetime"] permit_key = session[:saml_session_id].to_sym #store ip address and original url request in memory to be used for verification and redirect after response Rails.cache.fetch(permit_key, expires_in: lifetime.hours) do {ip_address: host_request.remote_ip, redirect_url: host_request.url } end saml_request_url = request.create(SamlCamel::Transaction.saml_settings) redirect_to(saml_request_url) end |
#set_saml_session_lifetime(permit_key) ⇒ Object
45 46 47 48 49 50 51 |
# File 'app/controllers/concerns/saml_camel/saml_helpers.rb', line 45 def set_saml_session_lifetime(permit_key) user_saml_cache = Rails.cache.fetch(permit_key) user_saml_cache[:session_start_time] = Time.now Rails.cache.fetch(permit_key, expires_in: 8.hours) do user_saml_cache end end |
#valid_ip?(remote_ip) ⇒ Boolean
85 86 87 88 89 90 91 92 93 |
# File 'app/controllers/concerns/saml_camel/saml_helpers.rb', line 85 def valid_ip?(remote_ip) permit_key = session[:saml_session_id].to_sym saml_cache = Rails.cache.fetch(permit_key) cache_available?(saml_cache) unless remote_ip == saml_cache[:ip_address] SamlCamel::Logging.bad_ip(session[:saml_attributes], saml_cache[:ip_address], remote_ip) session[:sp_session] = nil end end |
#verify_sha_type(response) ⇒ Object
122 123 124 125 126 127 128 |
# File 'app/controllers/concerns/saml_camel/saml_helpers.rb', line 122 def verify_sha_type(response) raw_xml_string = response.decrypted_document.to_s attr_scan = raw_xml_string.scan(/<ds:SignatureMethod.*\/>/) is_sha1 = attr_scan[0].match("sha1") raise "SHA1 algorithm not supported " if is_sha1 end |