noresponse 2.0.19 → 2.1.0

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: b943969974c1baa6424c9a385a9197719df01f57f2b901df3737e601ccd85bd8
4
- data.tar.gz: 5c6e129ac29f9ab0a2bdd3a6ec3bd19b2e25c67973f60ead05f30a1c15e2a463
3
+ metadata.gz: f7f2f99e8a5df281a10706ca39f72c60dd4e0c945f6a895e95644921ef902125
4
+ data.tar.gz: 5c9a7bcdd021bbec006baa70a1e70c30e27845fbb0f3244e9657aefa22deb8bf
5
5
  SHA512:
6
- metadata.gz: 9271c0b0010bd1c14933def2ba875a5f9f033ddfca6daa77f6699157d6ca881668f5a79ed2798780eedea552837d717ea8d8f7b87b246f62d7e57e4992e9a5ea
7
- data.tar.gz: dbc5b7a75472be7c169fbdca7d3b17fbcbfbbc8e926a3b25800e61c757e8d0d5a245c62dc7c71528ba0f164f15adbd9d1041a8b829ba6d524a06eb6f91966b33
6
+ metadata.gz: bc80309fad1e4e052a6fdb5bd3a9df90c3d9aab591a940b344678fa6ab9c7026c9f528b100a6ab0c68c1ed5b6ad824164600576702106a6e422d9f77eecdc8f4
7
+ data.tar.gz: 60e634af7afff07030476d5697bafecea730ef81062cdaad669f73c742b82f39b30f446fb094ee2ae9fbf02923703daf3baad858868f61844654a32cc69c69a7
@@ -706,7 +706,7 @@ module NoResponse
706
706
  response: http_response
707
707
  )
708
708
  return Models::Operations::DeleteIntegrationResponse.new(
709
- headers: {}
709
+ headers: http_response.headers
710
710
  )
711
711
  elsif Utils.match_status_code(http_response.status, ["400"])
712
712
  if Utils.match_content_type(content_type, "application/problem+json")
@@ -11,7 +11,9 @@
11
11
  # user.
12
12
  #
13
13
  # The handler verifies the delivery itself, so it never acts on an unverified
14
- # event. The provider calls are thin: you pass the credentials, and each
14
+ # event, and it never acts on a test event from the send-test-event call. Every
15
+ # provider call treats a 404 (user or session already gone) as done, so a
16
+ # repeated delivery is safe. The provider calls are thin: you pass the credentials, and each
15
17
  # action is the provider's documented admin endpoint.
16
18
 
17
19
  require 'erb'
@@ -54,12 +56,12 @@ module NoResponse
54
56
 
55
57
  class << self
56
58
  # The action your policy names for a verified event. Only a served
57
- # assessment with a recommendation can act. policy maps allow, step_up
58
- # and review (as strings or symbols) to NONE, REVOKE_SESSIONS or BAN; a
59
- # recommendation you leave out does nothing. An unknown action raises
60
- # ArgumentError.
59
+ # assessment with a recommendation can act; a test event never does.
60
+ # policy maps allow, step_up and review (as strings or symbols) to NONE,
61
+ # REVOKE_SESSIONS or BAN; a recommendation you leave out does nothing. An
62
+ # unknown action raises ArgumentError.
61
63
  def action_for(event, policy = DEFAULT_POLICY)
62
- return NONE if event.type != 'assessment.updated' || event.expired?
64
+ return NONE if event.type != 'assessment.updated' || event.test? || event.expired?
63
65
 
64
66
  data = event.data
65
67
  recommendation = data.recommendation || data.risk&.recommendation
@@ -111,7 +113,8 @@ module NoResponse
111
113
  # Clerk Backend API. revoke_sessions lists the user's active sessions
112
114
  # (GET /sessions?user_id&status=active) and revokes each
113
115
  # (POST /sessions/{id}/revoke). ban is POST /users/{id}/ban, which
114
- # revokes every session and blocks sign-in.
116
+ # revokes every session and blocks sign-in. A 404 on any call (user or
117
+ # session already gone) counts as done, so a repeated delivery is safe.
115
118
  #
116
119
  # base_url defaults to https://api.clerk.com/v1. http_client is an
117
120
  # optional callable (method, uri, headers, body) returning
@@ -126,7 +129,9 @@ module NoResponse
126
129
  # GET /user_management/users/{id}/sessions and revokes each active one
127
130
  # with POST /user_management/sessions/revoke. WorkOS has no block or ban,
128
131
  # so ban revokes the sessions and then deletes the user
129
- # (DELETE /user_management/users/{id}); deletion is permanent.
132
+ # (DELETE /user_management/users/{id}); deletion is permanent. A 404 on
133
+ # any call (user or session already gone) counts as done, so a repeated
134
+ # delivery is safe.
130
135
  #
131
136
  # base_url defaults to https://api.workos.com.
132
137
  def workos(api_key:, base_url: 'https://api.workos.com', http_client: nil)
@@ -141,7 +146,8 @@ module NoResponse
141
146
  # (PATCH /users/{id}), then does the same. Pass domain (such as
142
147
  # example.eu.auth0.com; the API is https://{domain}/api/v2) or base_url.
143
148
  # token is a Management API access token with update:users,
144
- # delete:sessions and delete:refresh_tokens.
149
+ # delete:sessions and delete:refresh_tokens. A 404 on any call (user
150
+ # already gone) counts as done, so a repeated delivery is safe.
145
151
  def auth0(token:, domain: nil, base_url: nil, http_client: nil)
146
152
  raise ArgumentError, 'auth0 needs token' if token.to_s.empty?
147
153
 
@@ -232,16 +238,16 @@ module NoResponse
232
238
  (0...1000).each do |round|
233
239
  page = Segment.sessions(@call.call('GET', '/sessions', query: [['user_id', user_id], %w[status active],
234
240
  ['limit', PAGE.to_s],
235
- ['offset', (round * PAGE).to_s]]))
241
+ ['offset', (round * PAGE).to_s]], allow_404: true))
236
242
  active.concat(Segment.active_ids(page))
237
243
  break if page.length < PAGE
238
244
  end
239
- active.each { |id| @call.call('POST', "/sessions/#{ERB::Util.url_encode(id)}/revoke") }
245
+ active.each { |id| @call.call('POST', "/sessions/#{ERB::Util.url_encode(id)}/revoke", allow_404: true) }
240
246
  nil
241
247
  end
242
248
 
243
249
  def ban(user_id)
244
- @call.call('POST', "/users/#{Segment.encode(user_id)}/ban")
250
+ @call.call('POST', "/users/#{Segment.encode(user_id)}/ban", allow_404: true)
245
251
  nil
246
252
  end
247
253
  end
@@ -260,14 +266,14 @@ module NoResponse
260
266
  1000.times do
261
267
  query = T.let([%w[limit 100]], T::Array[T::Array[String]])
262
268
  query << ['after', after] if after
263
- body = @call.call('GET', "/user_management/users/#{user}/sessions", query: query)
269
+ body = @call.call('GET', "/user_management/users/#{user}/sessions", query: query, allow_404: true)
264
270
  active.concat(Segment.active_ids(Segment.sessions(body)))
265
271
  nxt = body.is_a?(Hash) && body['list_metadata'].is_a?(Hash) ? body['list_metadata']['after'] : nil
266
272
  break unless nxt.is_a?(String) && !nxt.empty?
267
273
 
268
274
  after = nxt
269
275
  end
270
- active.each { |id| @call.call('POST', '/user_management/sessions/revoke', body: { 'session_id' => id }) }
276
+ active.each { |id| @call.call('POST', '/user_management/sessions/revoke', body: { 'session_id' => id }, allow_404: true) }
271
277
  nil
272
278
  end
273
279
 
@@ -287,13 +293,13 @@ module NoResponse
287
293
 
288
294
  def revoke_sessions(user_id)
289
295
  user = Segment.encode(user_id)
290
- @call.call('DELETE', "/users/#{user}/sessions")
291
- @call.call('DELETE', "/users/#{user}/refresh-tokens")
296
+ @call.call('DELETE', "/users/#{user}/sessions", allow_404: true)
297
+ @call.call('DELETE', "/users/#{user}/refresh-tokens", allow_404: true)
292
298
  nil
293
299
  end
294
300
 
295
301
  def ban(user_id)
296
- @call.call('PATCH', "/users/#{Segment.encode(user_id)}", body: { 'blocked' => true })
302
+ @call.call('PATCH', "/users/#{Segment.encode(user_id)}", body: { 'blocked' => true }, allow_404: true)
297
303
  revoke_sessions(user_id)
298
304
  end
299
305
  end
@@ -134,6 +134,12 @@ module NoResponse
134
134
  Crystalline::Nilable.new(::String),
135
135
  {'format_json': {'letter_case': ::NoResponse::Utils.field_name("assessment_url")}}
136
136
  )
137
+ # The identity fields of the auth context the assessment was made with, echoed for the tenant's own correlation: the request's auth_context, or the one a hosted provider hook (POST /hooks/{integration_id}) built, with transport provider_hook and its hook_point. Present exactly when the request carried an auth_context, and the same on every revision of the assessment. Values are as the request or the hook sent them; tokens, timestamps, roles and scopes are not echoed, and the echo does not change the score.
138
+ field(
139
+ :auth_context,
140
+ Crystalline::Nilable.new(Models::Shared::AssessmentAuthContext),
141
+ {'format_json': {'letter_case': ::NoResponse::Utils.field_name("auth_context")}}
142
+ )
137
143
 
138
144
  sig {
139
145
  params(
@@ -154,7 +160,8 @@ module NoResponse
154
160
  risk: T.nilable(Models::Shared::Risk),
155
161
  signals: T.nilable(T::Array[Models::Shared::Signal]),
156
162
  policy_basis: ::String,
157
- assessment_url: T.nilable(::String)
163
+ assessment_url: T.nilable(::String),
164
+ auth_context: T.nilable(Models::Shared::AssessmentAuthContext)
158
165
  )
159
166
  .void
160
167
  }
@@ -176,7 +183,8 @@ module NoResponse
176
183
  risk: nil,
177
184
  signals: nil,
178
185
  policy_basis: "heuristic_unvalidated",
179
- assessment_url: nil
186
+ assessment_url: nil,
187
+ auth_context: nil
180
188
  )
181
189
  @assessment_id = assessment_id
182
190
  @account_id = account_id
@@ -204,6 +212,7 @@ module NoResponse
204
212
 
205
213
  @policy_basis = "heuristic_unvalidated"
206
214
  @assessment_url = assessment_url
215
+ @auth_context = auth_context
207
216
  end
208
217
 
209
218
  sig { params(other: T.untyped).returns(T::Boolean) }
@@ -227,6 +236,7 @@ module NoResponse
227
236
  return false unless @signals == other.signals
228
237
  return false unless @policy_basis == other.policy_basis
229
238
  return false unless @assessment_url == other.assessment_url
239
+ return false unless @auth_context == other.auth_context
230
240
  true
231
241
  end
232
242
  end
@@ -113,4 +113,10 @@ class NoResponse::Models::Shared::Assessment
113
113
 
114
114
  def assessment_url=(str_)
115
115
  end
116
+
117
+ def auth_context
118
+ end
119
+
120
+ def auth_context=(str_)
121
+ end
116
122
  end
@@ -0,0 +1,121 @@
1
+ # typed: true
2
+ # frozen_string_literal: true
3
+
4
+ module NoResponse
5
+ module Models
6
+ module Shared
7
+ # The identity fields of the auth context the assessment was made with, echoed for the tenant's own correlation: the request's auth_context, or the one a hosted provider hook (POST /hooks/{integration_id}) built, with transport provider_hook and its hook_point. Present exactly when the request carried an auth_context, and the same on every revision of the assessment. Values are as the request or the hook sent them; tokens, timestamps, roles and scopes are not echoed, and the echo does not change the score.
8
+ class AssessmentAuthContext
9
+ extend T::Sig
10
+ include Crystalline::MetadataFields
11
+
12
+ # The provider slug the context named.
13
+ field(
14
+ :provider,
15
+ ::String,
16
+ {'format_json': {'letter_case': ::NoResponse::Utils.field_name("provider"), required: true}}
17
+ )
18
+ # The issuer the context named.
19
+ field(
20
+ :issuer,
21
+ ::String,
22
+ {'format_json': {'letter_case': ::NoResponse::Utils.field_name("issuer"), required: true}}
23
+ )
24
+ # The verified flag the context carried. A provider_hook context is always false.
25
+ field(
26
+ :verified,
27
+ Crystalline::Boolean.new,
28
+ {'format_json': {'letter_case': ::NoResponse::Utils.field_name("verified"), required: true}}
29
+ )
30
+ # Where the context was derived: backend (also when the request named no transport), browser, or provider_hook for a hosted provider hook.
31
+ field(
32
+ :transport,
33
+ Models::Shared::Transport,
34
+ {
35
+ 'format_json': {
36
+ 'letter_case': ::NoResponse::Utils.field_name("transport"),
37
+ required: true,
38
+ 'decoder': ::NoResponse::Utils.open_enum_from_string(Models::Shared::Transport, false)
39
+ }
40
+ }
41
+ )
42
+ # The subject the context named; absent when it named none (a pre_registration hook).
43
+ field(
44
+ :subject,
45
+ Crystalline::Nilable.new(::String),
46
+ {'format_json': {'letter_case': ::NoResponse::Utils.field_name("subject")}}
47
+ )
48
+ # The session identifier the context named, when it named one.
49
+ field(
50
+ :session_id,
51
+ Crystalline::Nilable.new(::String),
52
+ {'format_json': {'letter_case': ::NoResponse::Utils.field_name("session_id")}}
53
+ )
54
+ # The organization identifier the context named, when it named one.
55
+ field(
56
+ :organization_id,
57
+ Crystalline::Nilable.new(::String),
58
+ {'format_json': {'letter_case': ::NoResponse::Utils.field_name("organization_id")}}
59
+ )
60
+ # The provider event a provider_hook context was sent for; absent for any other transport.
61
+ field(
62
+ :hook_point,
63
+ Crystalline::Nilable.new(Models::Shared::HookPoint),
64
+ {
65
+ 'format_json': {
66
+ 'letter_case': ::NoResponse::Utils.field_name("hook_point"),
67
+ 'decoder': ::NoResponse::Utils.open_enum_from_string(Models::Shared::HookPoint, true)
68
+ }
69
+ }
70
+ )
71
+
72
+ sig {
73
+ params(
74
+ provider: ::String,
75
+ issuer: ::String,
76
+ verified: T::Boolean,
77
+ transport: Models::Shared::Transport,
78
+ subject: T.nilable(::String),
79
+ session_id: T.nilable(::String),
80
+ organization_id: T.nilable(::String),
81
+ hook_point: T.nilable(Models::Shared::HookPoint)
82
+ )
83
+ .void
84
+ }
85
+ def initialize(
86
+ provider:,
87
+ issuer:,
88
+ verified:,
89
+ transport:,
90
+ subject: nil,
91
+ session_id: nil,
92
+ organization_id: nil,
93
+ hook_point: nil
94
+ )
95
+ @provider = provider
96
+ @issuer = issuer
97
+ @verified = verified
98
+ @transport = transport
99
+ @subject = subject
100
+ @session_id = session_id
101
+ @organization_id = organization_id
102
+ @hook_point = hook_point
103
+ end
104
+
105
+ sig { params(other: T.untyped).returns(T::Boolean) }
106
+ def ==(other)
107
+ return false unless other.is_a?(self.class)
108
+ return false unless @provider == other.provider
109
+ return false unless @issuer == other.issuer
110
+ return false unless @verified == other.verified
111
+ return false unless @transport == other.transport
112
+ return false unless @subject == other.subject
113
+ return false unless @session_id == other.session_id
114
+ return false unless @organization_id == other.organization_id
115
+ return false unless @hook_point == other.hook_point
116
+ true
117
+ end
118
+ end
119
+ end
120
+ end
121
+ end
@@ -0,0 +1,56 @@
1
+ # typed: true
2
+ # frozen_string_literal: true
3
+
4
+ class NoResponse::Models::Shared::AssessmentAuthContext
5
+ extend ::Crystalline::MetadataFields::ClassMethods
6
+ end
7
+
8
+ class NoResponse::Models::Shared::AssessmentAuthContext
9
+ def provider
10
+ end
11
+
12
+ def provider=(str_)
13
+ end
14
+
15
+ def issuer
16
+ end
17
+
18
+ def issuer=(str_)
19
+ end
20
+
21
+ def verified
22
+ end
23
+
24
+ def verified=(str_)
25
+ end
26
+
27
+ def transport
28
+ end
29
+
30
+ def transport=(str_)
31
+ end
32
+
33
+ def subject
34
+ end
35
+
36
+ def subject=(str_)
37
+ end
38
+
39
+ def session_id
40
+ end
41
+
42
+ def session_id=(str_)
43
+ end
44
+
45
+ def organization_id
46
+ end
47
+
48
+ def organization_id=(str_)
49
+ end
50
+
51
+ def hook_point
52
+ end
53
+
54
+ def hook_point=(str_)
55
+ end
56
+ end
@@ -128,25 +128,25 @@ module NoResponse
128
128
  Crystalline::Nilable.new(Crystalline::Boolean.new),
129
129
  {'format_json': {'letter_case': ::NoResponse::Utils.field_name("impersonated")}}
130
130
  )
131
- # Where this context was derived. Backend is the trusted integration path; browser values are treated as weak hints. provider_hook is a hosted provider hook (an Auth0 or WorkOS Action) calling at hook_point; it needs hook_point and verified false, and its authentication facts are not scored.
131
+ # Where the context was derived: backend (also when the request named no transport), browser, or provider_hook for a hosted provider hook.
132
132
  field(
133
133
  :transport,
134
134
  Crystalline::Nilable.new(Models::Shared::Transport),
135
135
  {
136
136
  'format_json': {
137
137
  'letter_case': ::NoResponse::Utils.field_name("transport"),
138
- 'decoder': ::NoResponse::Utils.enum_from_string(Models::Shared::Transport, true)
138
+ 'decoder': ::NoResponse::Utils.open_enum_from_string(Models::Shared::Transport, true)
139
139
  }
140
140
  }
141
141
  )
142
- # The provider event a provider_hook context was sent for. pre_registration runs before the user exists, so subject and the request's account_id may be absent there. Sent only with transport provider_hook.
142
+ # The provider event a provider_hook context was sent for; absent for any other transport.
143
143
  field(
144
144
  :hook_point,
145
145
  Crystalline::Nilable.new(Models::Shared::HookPoint),
146
146
  {
147
147
  'format_json': {
148
148
  'letter_case': ::NoResponse::Utils.field_name("hook_point"),
149
- 'decoder': ::NoResponse::Utils.enum_from_string(Models::Shared::HookPoint, true)
149
+ 'decoder': ::NoResponse::Utils.open_enum_from_string(Models::Shared::HookPoint, true)
150
150
  }
151
151
  }
152
152
  )
@@ -4,8 +4,9 @@
4
4
  module NoResponse
5
5
  module Models
6
6
  module Shared
7
- # HookPoint - The provider event a provider_hook context was sent for. pre_registration runs before the user exists, so subject and the request's account_id may be absent there. Sent only with transport provider_hook.
8
- class HookPoint < T::Enum
7
+ # HookPoint - The provider event a provider_hook context was sent for; absent for any other transport.
8
+ class HookPoint
9
+ include ::Crystalline::Enum
9
10
  enums do
10
11
  PRE_REGISTRATION = new("pre_registration")
11
12
  POST_REGISTRATION = new("post_registration")
@@ -13,6 +14,8 @@ module NoResponse
13
14
  POST_LOGIN = new("post_login")
14
15
  TOKEN_ISSUANCE = new("token_issuance")
15
16
  end
17
+
18
+ open!
16
19
  end
17
20
  end
18
21
  end
@@ -11,12 +11,12 @@ module NoResponse
11
11
 
12
12
  field(
13
13
  :api_key,
14
- ::String,
14
+ Crystalline::Nilable.new(::String),
15
15
  {'security': {'scheme': true, 'type': "http", 'sub_type': "bearer", 'field_name': "Authorization"}}
16
16
  )
17
17
 
18
- sig { params(api_key: ::String).void }
19
- def initialize(api_key:)
18
+ sig { params(api_key: T.nilable(::String)).void }
19
+ def initialize(api_key: nil)
20
20
  @api_key = api_key
21
21
  end
22
22
 
@@ -4,13 +4,16 @@
4
4
  module NoResponse
5
5
  module Models
6
6
  module Shared
7
- # Transport - Where this context was derived. Backend is the trusted integration path; browser values are treated as weak hints. provider_hook is a hosted provider hook (an Auth0 or WorkOS Action) calling at hook_point; it needs hook_point and verified false, and its authentication facts are not scored.
8
- class Transport < T::Enum
7
+ # Transport - Where the context was derived: backend (also when the request named no transport), browser, or provider_hook for a hosted provider hook.
8
+ class Transport
9
+ include ::Crystalline::Enum
9
10
  enums do
10
11
  BACKEND = new("backend")
11
12
  BROWSER = new("browser")
12
13
  PROVIDER_HOOK = new("provider_hook")
13
14
  end
15
+
16
+ open!
14
17
  end
15
18
  end
16
19
  end
@@ -5,6 +5,7 @@ module NoResponse
5
5
  module Models
6
6
  module Shared
7
7
  autoload :Assessment, "no_response/models/shared/assessment.rb"
8
+ autoload :AssessmentAuthContext, "no_response/models/shared/assessmentauthcontext.rb"
8
9
  autoload :AssessmentList, "no_response/models/shared/assessmentlist.rb"
9
10
  autoload :AssessmentOutcome, "no_response/models/shared/assessmentoutcome.rb"
10
11
  autoload :AssessmentOutcomeRequest, "no_response/models/shared/assessmentoutcomerequest.rb"
@@ -88,13 +88,16 @@ module NoResponse
88
88
  @security_source = security_source
89
89
  elsif !api_key.nil?
90
90
  @security_source = -> { Models::Shared::Security.new(api_key: api_key) }
91
+ elsif !ENV.fetch("NORESPONSE_API_KEY", "").empty?
92
+ env_security = Models::Shared::Security.new(api_key: ENV.fetch("NORESPONSE_API_KEY"))
93
+ @security_source = -> { env_security }
91
94
  end
92
95
 
93
96
  @language = "ruby"
94
97
  @openapi_doc_version = "1"
95
- @sdk_version = "2.0.19"
98
+ @sdk_version = "2.1.0"
96
99
  @gen_version = "internal"
97
- @user_agent = "noresponse-sdk/ruby 2.0.19 internal 1 noresponse"
100
+ @user_agent = "noresponse-sdk/ruby 2.1.0 internal 1 noresponse"
98
101
  end
99
102
 
100
103
  sig { returns([String, T::Hash[Symbol, String]]) }
@@ -706,7 +706,7 @@ module NoResponse
706
706
  response: http_response
707
707
  )
708
708
  return Models::Operations::DeleteWebhookEndpointResponse.new(
709
- headers: {}
709
+ headers: http_response.headers
710
710
  )
711
711
  elsif Utils.match_status_code(http_response.status, ["400"])
712
712
  if Utils.match_content_type(content_type, "application/problem+json")
@@ -50,9 +50,13 @@ module NoResponse
50
50
  # "assessment.updated", and an EndpointVerification for
51
51
  # "endpoint.verification". Deliveries are at least once and unordered:
52
52
  # deduplicate on id and keep the highest assessment_version.
53
- Event = Struct.new(:id, :type, :created_at, :data, keyword_init: true) do
53
+ Event = Struct.new(:id, :type, :created_at, :data, :test, keyword_init: true) do
54
54
  # True for the terminal expiry event: delete what you hold and fetch nothing.
55
55
  def expired? = data.is_a?(AssessmentExpired)
56
+
57
+ # True on an event sent by the send-test-event call: data is a fixed
58
+ # example assessment, not one of yours. Acknowledge it and apply nothing.
59
+ def test? = test == true
56
60
  end
57
61
 
58
62
  class << self
@@ -132,7 +136,8 @@ module NoResponse
132
136
  raise VerificationError.new(:invalid_payload, 'Webhook event envelope is malformed')
133
137
  end
134
138
 
135
- Event.new(id: body['id'], type: body['type'], created_at: body['created_at'], data: event_data(body['type'], data))
139
+ Event.new(id: body['id'], type: body['type'], created_at: body['created_at'], data: event_data(body['type'], data),
140
+ test: body['test'] == true && body['type'] == 'assessment.updated')
136
141
  end
137
142
 
138
143
  def event_data(type, data)
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: noresponse
3
3
  version: !ruby/object:Gem::Version
4
- version: 2.0.19
4
+ version: 2.1.0
5
5
  platform: ruby
6
6
  authors:
7
7
  - NoResponse
8
8
  autorequire:
9
9
  bindir: bin
10
10
  cert_chain: []
11
- date: 2026-10-22 00:00:00.000000000 Z
11
+ date: 2026-10-23 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: base64
@@ -326,6 +326,8 @@ files:
326
326
  - lib/no_response/models/shared/alternate_name_union.rbi
327
327
  - lib/no_response/models/shared/assessment.rb
328
328
  - lib/no_response/models/shared/assessment.rbi
329
+ - lib/no_response/models/shared/assessmentauthcontext.rb
330
+ - lib/no_response/models/shared/assessmentauthcontext.rbi
329
331
  - lib/no_response/models/shared/assessmentlist.rb
330
332
  - lib/no_response/models/shared/assessmentlist.rbi
331
333
  - lib/no_response/models/shared/assessmentoutcome.rb