coalescing_panda 5.0.0.beta.2 → 5.0.4

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: b23ff734783865921d2c6b6b1513a444f409a9b3b8e223cdb22181bd6a10b436
4
- data.tar.gz: cb79054a936298ec5af8ce5fa2c75c852cfca4806349241bec1acb3e1a5d102e
3
+ metadata.gz: '0191513dcb57ac4c2146d650ff1b6d03af0cc52ac7aa7f62571b74f018ec3906'
4
+ data.tar.gz: 1f938c10ebea3510455f6e0f077bb531fc7eca49086df42792ab0ab23f96f6fd
5
5
  SHA512:
6
- metadata.gz: d2f03495f78ec52dc05044806a0753f47eece4ae109c60d69d9d41fa8a90c287413657615765b50209a28a22ab0d64489aec3977a47411d4f5255a2e7101f85a
7
- data.tar.gz: 255676120a18eb0ce8b7302246e66972b1cb4718e6d0359050649f507e400ca77f88f576ad85edbd16133b2790f1a611c9ac84c2989df73626e80a81d01f2ab6
6
+ metadata.gz: 75ffaa346308463f9beb170800fafa30a6303613a52e8c7ce527efee418369e0ae4a94ef7f2dbb1ef12b5a5f8a7d43ef33b59114064ee4eb63fca72cc3843305
7
+ data.tar.gz: bb268446450390d6af368149529ca6f23e34596155dc2151fcf5ee8cc2d604d25eb575cee4627b039894a8f8f439a52f6c8e959f4b8e0ff53979fe56128c1240
@@ -0,0 +1,3 @@
1
+ //= link_tree ../../images
2
+ //= link_directory ../../javascripts/coalescing_panda/ .js
3
+ //= link_directory ../../stylesheets/coalescing_panda/ .css
@@ -17,7 +17,7 @@ module CoalescingPanda
17
17
  lti_nav[:account][:text] = params[:account_navigation_label] if params[:account_navigation_label].present?
18
18
  platform = 'canvas.instructure.com'
19
19
  host = "#{request.scheme}://#{request.host_with_port}"
20
- tc = IMS::LTI::Services::ToolConfig.new(:title => lti_options[:title], :launch_url => ("#{host}#{lti_options[:launch_route]}") || 'ABC')
20
+ tc = IMS::LTI::ToolConfig.new(:title => lti_options[:title], :launch_url => ("#{host}#{lti_options[:launch_route]}") || 'ABC')
21
21
  tc.set_ext_param(platform, :domain, request.host)
22
22
  tc.set_ext_param(platform, :privacy_level, 'public')
23
23
  tc.set_custom_param(:custom_canvas_role, '$Canvas.membership.roles')
@@ -7,6 +7,8 @@ module CoalescingPanda
7
7
  end
8
8
 
9
9
  def redirect
10
+ use_secure_headers_override(:allow_inline_scripts)
11
+
10
12
  if !params[:error] && retrieve_oauth_state
11
13
  lti_account = LtiAccount.find_by_key(@oauth_state.data[:key])
12
14
  client_id = lti_account.oauth2_client_id
@@ -0,0 +1,13 @@
1
+ module CoalescingPanda
2
+ class JSONWithIndifferentAccess
3
+ def self.load(str)
4
+ return nil unless str.present?
5
+ parsed = JSON.parse(str)
6
+ parsed.is_a?(Hash) ? HashWithIndifferentAccess.new(parsed) : parsed
7
+ end
8
+
9
+ def self.dump(obj)
10
+ JSON.dump(obj)
11
+ end
12
+ end
13
+ end
@@ -1,10 +1,11 @@
1
1
  module CoalescingPanda
2
2
  class PersistentSession < ActiveRecord::Base
3
- serialize :data, Hash
3
+ serialize :data, JSONWithIndifferentAccess
4
4
  belongs_to :coalescing_panda_lti_account, :class_name => 'CoalescingPanda::LtiAccount'
5
5
  validates :coalescing_panda_lti_account_id, presence: true
6
6
 
7
7
  after_initialize do
8
+ self.data ||= {}
8
9
  self.session_key ||= SecureRandom.urlsafe_base64(60)
9
10
  end
10
11
 
@@ -2,15 +2,32 @@ require 'browser'
2
2
 
3
3
  module CoalescingPanda
4
4
  module ControllerHelpers
5
+ extend ActiveSupport::Concern
6
+
7
+ included do
8
+ alias_method :rails_session, :session
9
+
10
+ helper_method :encrypted_session_key, :current_session_data, :current_session
11
+ append_after_action :save_session, if: -> { @current_session && session_changed? }
12
+ end
13
+
14
+ class_methods do
15
+ def use_native_sessions
16
+ after_action do
17
+ rails_session['persistent_session_key'] = current_session.session_key if @current_session.present?
18
+ end
19
+ end
20
+ end
21
+
5
22
  def current_session
6
- @current_session ||= CoalescingPanda::PersistentSession.find_by(session_key: session_key) if session_key
7
- @current_session ||= CoalescingPanda::PersistentSession.create_from_launch(params, current_lti_account.id)
23
+ @current_session ||= (CoalescingPanda::PersistentSession.find_by(session_key: session_key) if session_key)
24
+ @current_session ||= (CoalescingPanda::PersistentSession.create_from_launch(params, current_lti_account.id) if current_lti_account.present?)
8
25
  @current_session
9
26
  end
10
27
 
11
28
  def current_lti_account
12
- @account ||= CoalescingPanda::LtiAccount.find_by!(key: organization_key) if organization_key
13
- @account ||= CoalescingPanda::LtiAccount.find_by(id: organization_id) if organization_id
29
+ @account ||= (CoalescingPanda::LtiAccount.find_by!(key: organization_key) if organization_key)
30
+ @account ||= (CoalescingPanda::LtiAccount.find_by(id: organization_id) if organization_id)
14
31
  @account
15
32
  end
16
33
 
@@ -83,42 +100,42 @@ module CoalescingPanda
83
100
  end
84
101
 
85
102
  def check_refresh_token
86
- return unless session['uri'] && session['user_id'] && session['oauth_consumer_key']
87
- uri = BearcatUri.new(session['uri'])
88
- api_auth = CanvasApiAuth.find_by(user_id: session['user_id'], api_domain: uri.api_domain)
89
- @lti_account = LtiAccount.find_by(key: session['oauth_consumer_key'])
103
+ return unless current_session_data['uri'] && current_session_data['user_id'] && current_session_data['oauth_consumer_key']
104
+ uri = BearcatUri.new(current_session_data['uri'])
105
+ api_auth = CanvasApiAuth.find_by(user_id: current_session_data['user_id'], api_domain: uri.api_domain)
106
+ @lti_account = LtiAccount.find_by(key: current_session_data['oauth_consumer_key'])
90
107
  return if @lti_account.nil? || api_auth.nil? # Not all tools use oauth
91
108
 
92
109
  refresh_token(uri, api_auth) if api_auth.expired?
93
110
  rescue Footrest::HttpError::BadRequest
94
- render_oauth2_page uri, session['user_id']
111
+ render_oauth2_page uri, current_session_data['user_id']
95
112
  end
96
113
 
97
114
  def set_session(launch_presentation_return_url)
98
- session['user_id'] = params['user_id']
99
- session['uri'] = launch_presentation_return_url
100
- session['lis_person_sourcedid'] = params['lis_person_sourcedid']
101
- session['oauth_consumer_key'] = params['oauth_consumer_key']
102
- session['custom_canvas_account_id'] = params['custom_canvas_account_id']
115
+ current_session_data['user_id'] = params['user_id']
116
+ current_session_data['uri'] = launch_presentation_return_url
117
+ current_session_data['lis_person_sourcedid'] = params['lis_person_sourcedid']
118
+ current_session_data['oauth_consumer_key'] = params['oauth_consumer_key']
119
+ current_session_data['custom_canvas_account_id'] = params['custom_canvas_account_id']
103
120
  end
104
121
 
105
122
  def have_session?
106
- if params['tool_consumer_instance_guid'] && session['user_id'] != params['user_id']
123
+ if params['tool_consumer_instance_guid'] && current_session_data['user_id'] != params['user_id']
107
124
  reset_session
108
125
  logger.info("resetting session params")
109
- session['user_id'] = params['user_id']
126
+ current_session_data['user_id'] = params['user_id']
110
127
  end
111
128
 
112
- if (session['user_id'] && session['uri'])
113
- uri = BearcatUri.new(session['uri'])
114
- api_auth = CanvasApiAuth.find_by('user_id = ? and api_domain = ?', session['user_id'], uri.api_domain)
129
+ if (current_session_data['user_id'] && current_session_data['uri'])
130
+ uri = BearcatUri.new(current_session_data['uri'])
131
+ api_auth = CanvasApiAuth.find_by('user_id = ? and api_domain = ?', current_session_data['user_id'], uri.api_domain)
115
132
  if api_auth && !api_auth.expired?
116
133
  @client = Bearcat::Client.new(token: api_auth.api_token, prefix: uri.prefix)
117
134
  @client.user_profile 'self'
118
135
  end
119
136
  end
120
137
 
121
- @lti_account = LtiAccount.find_by_key(session['oauth_consumer_key']) if session['oauth_consumer_key']
138
+ @lti_account = LtiAccount.find_by_key(current_session_data['oauth_consumer_key']) if current_session_data['oauth_consumer_key']
122
139
 
123
140
  !!@client
124
141
  rescue Footrest::HttpError::Unauthorized
@@ -129,8 +146,8 @@ module CoalescingPanda
129
146
  authorized = false
130
147
  if (@lti_account = params['oauth_consumer_key'] && LtiAccount.find_by_key(params['oauth_consumer_key']))
131
148
  sanitized_params = sanitize_params
132
- authenticator = IMS::LTI::Services::MessageAuthenticator.new(request.original_url, sanitized_params, @lti_account.secret)
133
- authorized = authenticator.valid_signature?
149
+ @tp = IMS::LTI::ToolProvider.new(@lti_account.key, @lti_account.secret, sanitized_params)
150
+ authorized = @tp.valid_request?(request)
134
151
  end
135
152
  logger.info 'not authorized on tp valid request' unless authorized
136
153
  authorized = authorized && (roles.count == 0 || (roles & lti_roles).count > 0)
@@ -198,7 +215,7 @@ module CoalescingPanda
198
215
  if params[:encrypted_session_key]
199
216
  return msg_encryptor.decrypt_and_verify(params[:encrypted_session_key])
200
217
  end
201
- params[:session_key] || session_key_header
218
+ params[:session_key] || session_key_header || rails_session['persistent_session_key']
202
219
  end
203
220
 
204
221
  def session_key_header
@@ -218,26 +235,26 @@ module CoalescingPanda
218
235
  # nicely with webpack-dev-server live reloading (otherwise
219
236
  # you get an access error every time it tries to live reload).
220
237
 
221
- def redirect_with_session_to(path, id_or_resource = nil, params = {})
222
- if Rails.env.development?
223
- redirect_development_mode(path, id_or_resource, params)
238
+ def redirect_with_session_to(path, id_or_resource = nil, redirect_params = {})
239
+ if Rails.env.development? || Rails.env.test?
240
+ redirect_development_mode(path, id_or_resource, redirect_params)
224
241
  else
225
- redirect_production_mode(path, id_or_resource, params)
242
+ redirect_production_mode(path, id_or_resource, redirect_params)
226
243
  end
227
244
  end
228
245
 
229
- def redirect_development_mode(path, id_or_resource = nil, params)
246
+ def redirect_development_mode(path, id_or_resource = nil, redirect_params)
230
247
  redirect_to send(path, id_or_resource, {
231
248
  session_key: current_session.session_key,
232
249
  organization_id: current_lti_account.id
233
- }.merge(params))
250
+ }.merge(redirect_params))
234
251
  end
235
252
 
236
- def redirect_production_mode(path, id_or_resource = nil, params)
253
+ def redirect_production_mode(path, id_or_resource = nil, redirect_params)
237
254
  redirect_to send(path, id_or_resource, {
238
255
  encrypted_session_key: encrypted_session_key,
239
256
  organization_id: current_lti_account.id
240
- }.merge(params))
257
+ }.merge(redirect_params))
241
258
  end
242
259
 
243
260
  end
@@ -25,6 +25,10 @@ module CoalescingPanda
25
25
  end
26
26
  end
27
27
 
28
+ initializer 'coalescing_panda.assets' do |app|
29
+ app.config.assets.precompile << 'coalescing_panda/manifest.js'
30
+ end
31
+
28
32
  initializer 'cloaescing_panda.route_helper' do |route|
29
33
  ActionDispatch::Routing::Mapper.send :include, CoalescingPanda::RouteHelpers
30
34
  end
@@ -83,6 +87,10 @@ module CoalescingPanda
83
87
  SecureHeaders::Configuration.override(:safari_override) do |config|
84
88
  config.cookies = SecureHeaders::OPT_OUT
85
89
  end
90
+
91
+ SecureHeaders::Configuration.override(:allow_inline_scripts) do |config|
92
+ config.csp[:script_src] << "'unsafe-inline'"
93
+ end
86
94
  end
87
95
 
88
96
  end
@@ -1,3 +1,3 @@
1
1
  module CoalescingPanda
2
- VERSION = '5.0.0.beta.2'
2
+ VERSION = '5.0.4'
3
3
  end
metadata CHANGED
@@ -1,7 +1,7 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: coalescing_panda
3
3
  version: !ruby/object:Gem::Version
4
- version: 5.0.0.beta.2
4
+ version: 5.0.4
5
5
  platform: ruby
6
6
  authors:
7
7
  - Nathan Mills
@@ -10,7 +10,7 @@ authors:
10
10
  autorequire:
11
11
  bindir: bin
12
12
  cert_chain: []
13
- date: 2020-06-04 00:00:00.000000000 Z
13
+ date: 2020-07-29 00:00:00.000000000 Z
14
14
  dependencies:
15
15
  - !ruby/object:Gem::Dependency
16
16
  name: rails
@@ -72,16 +72,22 @@ dependencies:
72
72
  name: ims-lti
73
73
  requirement: !ruby/object:Gem::Requirement
74
74
  requirements:
75
- - - ">="
75
+ - - "~>"
76
76
  - !ruby/object:Gem::Version
77
- version: 2.1.0
77
+ version: 1.2.0
78
+ - - "<"
79
+ - !ruby/object:Gem::Version
80
+ version: '2.0'
78
81
  type: :runtime
79
82
  prerelease: false
80
83
  version_requirements: !ruby/object:Gem::Requirement
81
84
  requirements:
82
- - - ">="
85
+ - - "~>"
86
+ - !ruby/object:Gem::Version
87
+ version: 1.2.0
88
+ - - "<"
83
89
  - !ruby/object:Gem::Version
84
- version: 2.1.0
90
+ version: '2.0'
85
91
  - !ruby/object:Gem::Dependency
86
92
  name: haml-rails
87
93
  requirement: !ruby/object:Gem::Requirement
@@ -400,6 +406,7 @@ extensions: []
400
406
  extra_rdoc_files: []
401
407
  files:
402
408
  - Rakefile
409
+ - app/assets/config/coalescing_panda/manifest.js
403
410
  - app/assets/images/bootstrap/glyphicons-halflings-white.png
404
411
  - app/assets/images/bootstrap/glyphicons-halflings.png
405
412
  - app/assets/javascripts/coalescing_panda/application.js
@@ -422,6 +429,7 @@ files:
422
429
  - app/models/coalescing_panda/group.rb
423
430
  - app/models/coalescing_panda/group_category.rb
424
431
  - app/models/coalescing_panda/group_membership.rb
432
+ - app/models/coalescing_panda/json_with_indifferent_access.rb
425
433
  - app/models/coalescing_panda/lti_account.rb
426
434
  - app/models/coalescing_panda/lti_nonce.rb
427
435
  - app/models/coalescing_panda/oauth_state.rb
@@ -563,9 +571,9 @@ required_ruby_version: !ruby/object:Gem::Requirement
563
571
  version: '0'
564
572
  required_rubygems_version: !ruby/object:Gem::Requirement
565
573
  requirements:
566
- - - ">"
574
+ - - ">="
567
575
  - !ruby/object:Gem::Version
568
- version: 1.3.1
576
+ version: '0'
569
577
  requirements: []
570
578
  rubygems_version: 3.1.2
571
579
  signing_key: