atlas_rb 1.3.9 → 1.4.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.
@@ -32,9 +32,9 @@ module AtlasRb
32
32
  # non-grantee raises {AtlasRb::ForbiddenError}.
33
33
  #
34
34
  # @param id [String] the Compilation ID (NOID).
35
- # @param nuid [String, nil] optional acting user's NUID, forwarded as the
36
- # `User:` header. Required for cerberus-token requests; legacy bearer
37
- # tokens still resolve without it.
35
+ # @param nuid [String, nil] optional acting user's NUID. On the relay-signing
36
+ # path it is signed into the assertion `sub`; on the BYO-JWT (`ATLAS_JWT`)
37
+ # path it is ignored (identity lives in the token).
38
38
  # @param on_behalf_of [String, nil] optional NUID for the `On-Behalf-Of`
39
39
  # header. Falls through to {AtlasRb.config}.default_on_behalf_of when
40
40
  # omitted.
@@ -66,9 +66,9 @@ module AtlasRb
66
66
  # @param q [String, nil] case-insensitive title substring filter.
67
67
  # @param page [Integer, nil] 1-indexed page number.
68
68
  # @param per_page [Integer, nil] page size override.
69
- # @param nuid [String, nil] optional acting user's NUID, forwarded as the
70
- # `User:` header. Required for cerberus-token requests; legacy bearer
71
- # tokens still resolve without it.
69
+ # @param nuid [String, nil] optional acting user's NUID. On the relay-signing
70
+ # path it is signed into the assertion `sub`; on the BYO-JWT (`ATLAS_JWT`)
71
+ # path it is ignored (identity lives in the token).
72
72
  # @param on_behalf_of [String, nil] optional NUID for the `On-Behalf-Of`
73
73
  # header. Falls through to {AtlasRb.config}.default_on_behalf_of when
74
74
  # omitted.
@@ -103,9 +103,8 @@ module AtlasRb
103
103
  #
104
104
  # @param title [String] the Set's title (required; blank is a 422).
105
105
  # @param description [String, nil] optional free-text description.
106
- # @param nuid [String, nil] the acting user's NUID, forwarded as the
107
- # `User:` header the created Set's owner. Required for
108
- # cerberus-token requests.
106
+ # @param nuid [String, nil] the acting user's NUID signed into the
107
+ # assertion `sub` on the relay-signing path, and the created Set's owner.
109
108
  # @param on_behalf_of [String, nil] optional NUID for the `On-Behalf-Of`
110
109
  # header. Falls through to {AtlasRb.config}.default_on_behalf_of when
111
110
  # omitted.
@@ -140,9 +139,9 @@ module AtlasRb
140
139
  # @param description [String, nil] new description.
141
140
  # @param permissions [Hash, nil] ACL replacement, e.g.
142
141
  # `{ read: ["public"], edit: [], edit_users: ["000000003"] }`.
143
- # @param nuid [String, nil] optional acting user's NUID, forwarded as the
144
- # `User:` header. Required for cerberus-token requests; legacy bearer
145
- # tokens still resolve without it.
142
+ # @param nuid [String, nil] optional acting user's NUID. On the relay-signing
143
+ # path it is signed into the assertion `sub`; on the BYO-JWT (`ATLAS_JWT`)
144
+ # path it is ignored (identity lives in the token).
146
145
  # @param on_behalf_of [String, nil] optional NUID for the `On-Behalf-Of`
147
146
  # header. Falls through to {AtlasRb.config}.default_on_behalf_of when
148
147
  # omitted.
@@ -175,9 +174,9 @@ module AtlasRb
175
174
  # not a container.
176
175
  #
177
176
  # @param id [String] the Compilation ID.
178
- # @param nuid [String, nil] optional acting user's NUID, forwarded as the
179
- # `User:` header. Required for cerberus-token requests; legacy bearer
180
- # tokens still resolve without it.
177
+ # @param nuid [String, nil] optional acting user's NUID. On the relay-signing
178
+ # path it is signed into the assertion `sub`; on the BYO-JWT (`ATLAS_JWT`)
179
+ # path it is ignored (identity lives in the token).
181
180
  # @param on_behalf_of [String, nil] optional NUID for the `On-Behalf-Of`
182
181
  # header. Falls through to {AtlasRb.config}.default_on_behalf_of when
183
182
  # omitted.
@@ -199,9 +198,9 @@ module AtlasRb
199
198
  #
200
199
  # @param id [String] the Compilation ID.
201
200
  # @param collection_id [String] the Collection NOID to include.
202
- # @param nuid [String, nil] optional acting user's NUID, forwarded as the
203
- # `User:` header. Required for cerberus-token requests; legacy bearer
204
- # tokens still resolve without it.
201
+ # @param nuid [String, nil] optional acting user's NUID. On the relay-signing
202
+ # path it is signed into the assertion `sub`; on the BYO-JWT (`ATLAS_JWT`)
203
+ # path it is ignored (identity lives in the token).
205
204
  # @param on_behalf_of [String, nil] optional NUID for the `On-Behalf-Of`
206
205
  # header. Falls through to {AtlasRb.config}.default_on_behalf_of when
207
206
  # omitted.
@@ -226,9 +225,9 @@ module AtlasRb
226
225
  #
227
226
  # @param id [String] the Compilation ID.
228
227
  # @param collection_id [String] the Collection NOID to remove.
229
- # @param nuid [String, nil] optional acting user's NUID, forwarded as the
230
- # `User:` header. Required for cerberus-token requests; legacy bearer
231
- # tokens still resolve without it.
228
+ # @param nuid [String, nil] optional acting user's NUID. On the relay-signing
229
+ # path it is signed into the assertion `sub`; on the BYO-JWT (`ATLAS_JWT`)
230
+ # path it is ignored (identity lives in the token).
232
231
  # @param on_behalf_of [String, nil] optional NUID for the `On-Behalf-Of`
233
232
  # header. Falls through to {AtlasRb.config}.default_on_behalf_of when
234
233
  # omitted.
@@ -250,9 +249,9 @@ module AtlasRb
250
249
  #
251
250
  # @param id [String] the Compilation ID.
252
251
  # @param work_id [String] the Work NOID to include.
253
- # @param nuid [String, nil] optional acting user's NUID, forwarded as the
254
- # `User:` header. Required for cerberus-token requests; legacy bearer
255
- # tokens still resolve without it.
252
+ # @param nuid [String, nil] optional acting user's NUID. On the relay-signing
253
+ # path it is signed into the assertion `sub`; on the BYO-JWT (`ATLAS_JWT`)
254
+ # path it is ignored (identity lives in the token).
256
255
  # @param on_behalf_of [String, nil] optional NUID for the `On-Behalf-Of`
257
256
  # header. Falls through to {AtlasRb.config}.default_on_behalf_of when
258
257
  # omitted.
@@ -273,9 +272,9 @@ module AtlasRb
273
272
  #
274
273
  # @param id [String] the Compilation ID.
275
274
  # @param work_id [String] the Work NOID to remove.
276
- # @param nuid [String, nil] optional acting user's NUID, forwarded as the
277
- # `User:` header. Required for cerberus-token requests; legacy bearer
278
- # tokens still resolve without it.
275
+ # @param nuid [String, nil] optional acting user's NUID. On the relay-signing
276
+ # path it is signed into the assertion `sub`; on the BYO-JWT (`ATLAS_JWT`)
277
+ # path it is ignored (identity lives in the token).
279
278
  # @param on_behalf_of [String, nil] optional NUID for the `On-Behalf-Of`
280
279
  # header. Falls through to {AtlasRb.config}.default_on_behalf_of when
281
280
  # omitted.
@@ -300,9 +299,9 @@ module AtlasRb
300
299
  #
301
300
  # @param id [String] the Compilation ID.
302
301
  # @param work_id [String] the Work NOID to set aside.
303
- # @param nuid [String, nil] optional acting user's NUID, forwarded as the
304
- # `User:` header. Required for cerberus-token requests; legacy bearer
305
- # tokens still resolve without it.
302
+ # @param nuid [String, nil] optional acting user's NUID. On the relay-signing
303
+ # path it is signed into the assertion `sub`; on the BYO-JWT (`ATLAS_JWT`)
304
+ # path it is ignored (identity lives in the token).
306
305
  # @param on_behalf_of [String, nil] optional NUID for the `On-Behalf-Of`
307
306
  # header. Falls through to {AtlasRb.config}.default_on_behalf_of when
308
307
  # omitted.
@@ -323,9 +322,9 @@ module AtlasRb
323
322
  #
324
323
  # @param id [String] the Compilation ID.
325
324
  # @param work_id [String] the Work NOID to restore to the resolved set.
326
- # @param nuid [String, nil] optional acting user's NUID, forwarded as the
327
- # `User:` header. Required for cerberus-token requests; legacy bearer
328
- # tokens still resolve without it.
325
+ # @param nuid [String, nil] optional acting user's NUID. On the relay-signing
326
+ # path it is signed into the assertion `sub`; on the BYO-JWT (`ATLAS_JWT`)
327
+ # path it is ignored (identity lives in the token).
329
328
  # @param on_behalf_of [String, nil] optional NUID for the `On-Behalf-Of`
330
329
  # header. Falls through to {AtlasRb.config}.default_on_behalf_of when
331
330
  # omitted.
@@ -353,9 +352,9 @@ module AtlasRb
353
352
  # @param id [String] the Compilation ID.
354
353
  # @param page [Integer, nil] 1-indexed page number (default 1).
355
354
  # @param per_page [Integer, nil] page size (default 25, capped at 100).
356
- # @param nuid [String, nil] optional acting user's NUID, forwarded as the
357
- # `User:` header. Required for cerberus-token requests; legacy bearer
358
- # tokens still resolve without it.
355
+ # @param nuid [String, nil] optional acting user's NUID. On the relay-signing
356
+ # path it is signed into the assertion `sub`; on the BYO-JWT (`ATLAS_JWT`)
357
+ # path it is ignored (identity lives in the token).
359
358
  # @param on_behalf_of [String, nil] optional NUID for the `On-Behalf-Of`
360
359
  # header. Falls through to {AtlasRb.config}.default_on_behalf_of when
361
360
  # omitted.
@@ -45,10 +45,10 @@ module AtlasRb
45
45
  # to send no `On-Behalf-Of:` header.
46
46
  attr_accessor :default_on_behalf_of
47
47
 
48
- # Relay signing (the cerberus_token replacement). When set, the regular
49
- # relay path *signs* a short-lived assertion (ES256, `sub` = acting nuid)
50
- # instead of sending `ATLAS_TOKEN` + a `User:` header identity becomes
51
- # proven, not asserted. Leave nil (the default) to keep the legacy relay.
48
+ # Relay signing. When set, the regular relay path *signs* a short-lived
49
+ # assertion (ES256, `sub` = acting nuid) — identity is proven, not asserted.
50
+ # This is the relay credential: with no signing key configured (and no
51
+ # `ATLAS_JWT`), the transport raises {AtlasRb::ConfigurationError}.
52
52
  #
53
53
  # Accepts either a value or a callable (resolved per request, so a Rails
54
54
  # host can read it from request-scoped state / credentials). The value may
@@ -23,9 +23,9 @@ module AtlasRb
23
23
  # Fetch a single Delegate by NOID or `valkyrie_id`.
24
24
  #
25
25
  # @param id [String] the Delegate's NOID or `valkyrie_id`.
26
- # @param nuid [String, nil] optional acting user's NUID, forwarded as the
27
- # `User:` header. Required for cerberus-token requests; legacy bearer
28
- # tokens still resolve without it.
26
+ # @param nuid [String, nil] optional acting user's NUID. On the relay-signing
27
+ # path it is signed into the assertion `sub`; on the BYO-JWT (`ATLAS_JWT`)
28
+ # path it is ignored (identity lives in the token).
29
29
  # @param on_behalf_of [String, nil] optional NUID for the `On-Behalf-Of`
30
30
  # header. Falls through to {AtlasRb.config}.default_on_behalf_of when
31
31
  # omitted.
@@ -164,4 +164,11 @@ module AtlasRb
164
164
  @subject = subject
165
165
  end
166
166
  end
167
+
168
+ # Raised when the transport has no way to authenticate a relay request:
169
+ # neither `ATLAS_JWT` (BYO-JWT mode) nor a signing key
170
+ # ({AtlasRb.config#assertion_signing_key}, relay-signing mode) is configured.
171
+ # This is a host-misconfiguration error surfaced at request-build time, not a
172
+ # wire response — fix the configuration rather than rescuing it.
173
+ class ConfigurationError < Error; end
167
174
  end
@@ -6,45 +6,35 @@ module AtlasRb
6
6
  # Every Atlas request reads these environment variables:
7
7
  #
8
8
  # - `ATLAS_URL` — base URL of the Atlas API (e.g. `https://atlas.example.edu`).
9
- # - `ATLAS_TOKEN` — Cerberus-relay bearer token used in the `Authorization`
10
- # header on the default (relay) path.
11
9
  # - `ATLAS_JWT` — *optional* personal-access JWT (minted by Atlas's
12
10
  # `POST /nuid`, Cerberus-delegated post-SSO). When set, it switches the
13
11
  # transport into **bring-your-own-JWT mode** (see below).
14
12
  #
15
13
  # ## Two transport modes
16
14
  #
17
- # **Relay mode (default, `ATLAS_JWT` unset).** Authenticates with
18
- # `ATLAS_TOKEN` and identifies the acting user via a `User: NUID <nuid>`
19
- # header, optionally an `On-Behalf-Of: NUID <nuid>` header for acting-as /
20
- # view-as flows. When `nuid` / `on_behalf_of` are omitted (positional arg
21
- # `nil`, kwarg `nil`), the helper falls through to {AtlasRb.config}'s
22
- # `default_nuid` / `default_on_behalf_of` callables host applications wire
23
- # those up to their request-scoped `Current.*` source. Caller-passed values
24
- # always win over the configured defaults. This is the path Cerberus uses.
15
+ # **Relay-signing mode (default).** The regular relay path **signs** a
16
+ # short-lived assertion (ES256, `iss=cerberus`, `aud=atlas`, `sub` = the
17
+ # acting nuid) with Cerberus's private key Atlas verifies it against the
18
+ # matching public key. No `User:` header; identity is the proven `sub`.
19
+ # **Acting-as rides a signed `obo` claim** inside the assertion (the target
20
+ # can't be forged onto a stolen assertion; Atlas admin-gates the operator and
21
+ # ignores any header obo on this path). When `nuid` / `on_behalf_of` are
22
+ # omitted (positional arg `nil`, kwarg `nil`), the helper falls through to
23
+ # {AtlasRb.config}'s `default_nuid` / `default_on_behalf_of` callables — host
24
+ # applications wire those up to their request-scoped `Current.*` source;
25
+ # caller-passed values always win. The key is configured via
26
+ # {AtlasRb.config#assertion_signing_key} / `assertion_signing_kid`. This is
27
+ # the path Cerberus uses.
25
28
  #
26
29
  # **BYO-JWT mode (`ATLAS_JWT` set).** Authenticates with the JWT, which
27
30
  # already encodes the acting user — so **no `User:` header is sent**, and
28
31
  # `On-Behalf-Of` is **suppressed** (Atlas rejects acting-as on the JWT path
29
32
  # with a 403; acting-as is a relay-only concept). `ATLAS_JWT` takes
30
- # precedence over `ATLAS_TOKEN`. This is the standalone-script path: a
33
+ # precedence over relay-signing. This is the standalone-script path: a
31
34
  # librarian exports their minted token and runs headless against the API.
32
35
  #
33
- # **Relay-signing mode ({AtlasRb.config#assertion_signing_key} set).** The
34
- # cryptographic replacement for the `ATLAS_TOKEN` relay: instead of a shared
35
- # secret + an asserted `User:` header, the regular relay path **signs** a
36
- # short-lived assertion (ES256, `iss=cerberus`, `aud=atlas`, `sub` = the
37
- # acting nuid) with Cerberus's private key — Atlas verifies it with the
38
- # public key. No `User:` header; identity is the proven `sub`. **Acting-as
39
- # rides a signed `obo` claim** inside the assertion (the target can't be forged
40
- # onto a stolen assertion; Atlas admin-gates the operator and ignores any
41
- # header obo on this path) — it is no longer punted to the legacy relay. Off
42
- # unless a signing key is configured (so it coexists with `ATLAS_TOKEN`
43
- # during cutover). `ATLAS_JWT`, if set, still wins over signing.
44
- #
45
- # Requires an Atlas that verifies the signed `obo` claim (the signed-obo
46
- # release); against an older Atlas an `obo` would be silently ignored, so
47
- # don't enable signing for acting-as traffic until Atlas is on that version.
36
+ # If neither a signing key nor `ATLAS_JWT` is configured there is no relay
37
+ # credential, so the transport raises {AtlasRb::ConfigurationError}.
48
38
  #
49
39
  # The module is mixed in via `extend`, so its methods become class methods on
50
40
  # the host (e.g. `AtlasRb::Work.connection({})`).
@@ -60,14 +50,13 @@ module AtlasRb
60
50
  # @param params [Hash] query-string / body params to attach to the request.
61
51
  # Resource classes use this to pass things like `parent_id:`, `work_id:`,
62
52
  # or `metadata:` without manually serializing.
63
- # @param nuid [String, nil] optional Northeastern University ID to send in
64
- # the `User` header. When `nil`, falls through to
65
- # `AtlasRb.config.default_nuid&.call`; if that is also nil, no `User:`
66
- # header is sent (legacy bearer-only path).
67
- # @param on_behalf_of [String, nil] optional NUID for the `On-Behalf-Of`
68
- # header. When `nil`, falls through to
53
+ # @param nuid [String, nil] optional Northeastern University ID. On the
54
+ # relay-signing path it is signed into the assertion `sub`. When `nil`,
55
+ # falls through to `AtlasRb.config.default_nuid&.call`.
56
+ # @param on_behalf_of [String, nil] optional NUID carried as a signed `obo`
57
+ # claim (acting-as / view-as). When `nil`, falls through to
69
58
  # `AtlasRb.config.default_on_behalf_of&.call`; if that is also nil, no
70
- # `On-Behalf-Of:` header is sent. Used by acting-as / view-as flows.
59
+ # `obo` claim is added.
71
60
  # @param idempotency_key [String, nil] optional UUID to send in the
72
61
  # `Idempotency-Key` header. Used by retry-safe create flows (currently
73
62
  # `POST /works`, `POST /file_sets`, `POST /files`) to deduplicate replays
@@ -96,15 +85,16 @@ module AtlasRb
96
85
 
97
86
  # Build a multipart Faraday connection used for binary and XML uploads.
98
87
  #
99
- # The same `ATLAS_URL` / `ATLAS_TOKEN` env vars apply. Unlike {#connection},
88
+ # The same `ATLAS_URL` env var and auth modes apply. Unlike {#connection},
100
89
  # the `Content-Type` is set automatically by the multipart middleware, and
101
90
  # callers pass a payload hash whose values may include
102
91
  # `Faraday::Multipart::FilePart` instances. Fall-through semantics for
103
92
  # `nuid` / `on_behalf_of` match {#connection}.
104
93
  #
105
- # @param nuid [String, nil] optional NUID for the `User` header.
106
- # @param on_behalf_of [String, nil] optional NUID for the `On-Behalf-Of`
107
- # header.
94
+ # @param nuid [String, nil] optional acting NUID (signed into the assertion
95
+ # `sub` on the relay-signing path).
96
+ # @param on_behalf_of [String, nil] optional NUID carried as a signed `obo`
97
+ # claim (acting-as / view-as).
108
98
  # @param idempotency_key [String, nil] optional UUID to send in the
109
99
  # `Idempotency-Key` header. See {#connection} for semantics; the
110
100
  # `POST /files` (Blob) create flow uses this transport.
@@ -174,9 +164,10 @@ module AtlasRb
174
164
  private
175
165
 
176
166
  # Build the auth + identity headers shared by {#connection} and {#multipart}.
177
- # Precedence: ATLAS_JWT (BYO-JWT) > relay-signing > ATLAS_TOKEN relay. The
178
- # acting nuid / on_behalf_of fall through to the configured `default_nuid` /
167
+ # Precedence: ATLAS_JWT (BYO-JWT) > relay-signing. The acting nuid /
168
+ # on_behalf_of fall through to the configured `default_nuid` /
179
169
  # `default_on_behalf_of` callables here, once, for whichever mode applies.
170
+ # Raises {ConfigurationError} when neither credential is configured.
180
171
  def auth_headers(nuid, on_behalf_of)
181
172
  jwt = ENV.fetch("ATLAS_JWT", nil)
182
173
  return { "Authorization" => "Bearer #{jwt}" } if jwt
@@ -184,14 +175,16 @@ module AtlasRb
184
175
  nuid ||= AtlasRb.config.default_nuid&.call
185
176
  on_behalf_of ||= AtlasRb.config.default_on_behalf_of&.call
186
177
 
187
- signed_relay_headers(nuid, on_behalf_of) || relay_headers(nuid, on_behalf_of)
178
+ signed_relay_headers(nuid, on_behalf_of) ||
179
+ raise(ConfigurationError,
180
+ "atlas_rb: no auth configured — set ATLAS_JWT or " \
181
+ "AtlasRb.config.assertion_signing_key (with an acting nuid to sign)")
188
182
  end
189
183
 
190
- # A signed-assertion Authorization header (sub = acting nuid), or nil to
191
- # defer to the legacy relay. nil when signing isn't configured or there is no
192
- # acting nuid to put in `sub`. Acting-as is carried IN the assertion as a
193
- # signed `obo` claim (Atlas honours it on the assertion path as of the
194
- # signed-obo release), so it is no longer punted to the cerberus_token relay.
184
+ # A signed-assertion Authorization header (sub = acting nuid), or nil when
185
+ # signing isn't configured or there is no acting nuid to put in `sub`.
186
+ # Acting-as is carried IN the assertion as a signed `obo` claim (Atlas
187
+ # honours it on the assertion path; a header obo is ignored there).
195
188
  def signed_relay_headers(nuid, on_behalf_of)
196
189
  return nil unless nuid
197
190
 
@@ -201,15 +194,6 @@ module AtlasRb
201
194
  { "Authorization" => "Bearer #{signed_assertion(nuid.to_s, key, on_behalf_of)}" }
202
195
  end
203
196
 
204
- # Legacy relay headers: ATLAS_TOKEN bearer + acting-user identity headers.
205
- # `nuid` / `on_behalf_of` are already resolved by {#auth_headers}.
206
- def relay_headers(nuid, on_behalf_of)
207
- headers = { "Authorization" => "Bearer #{ENV.fetch("ATLAS_TOKEN", nil)}" }
208
- headers["User"] = "NUID #{nuid}" if nuid
209
- headers["On-Behalf-Of"] = "NUID #{on_behalf_of}" if on_behalf_of
210
- headers
211
- end
212
-
213
197
  # Mint a Cerberus relay assertion for `nuid`, signed ES256 with `key`. The
214
198
  # `kid` header tells Atlas which public key to verify against; iss/aud are
215
199
  # the fixed contract; the short TTL bounds replay; `jti` is forward-compat
@@ -17,9 +17,9 @@ module AtlasRb
17
17
  # Fetch a single FileSet by ID.
18
18
  #
19
19
  # @param id [String] the FileSet ID.
20
- # @param nuid [String, nil] optional acting user's NUID, forwarded as the
21
- # `User:` header. Required for cerberus-token requests; legacy bearer
22
- # tokens still resolve without it.
20
+ # @param nuid [String, nil] optional acting user's NUID. On the relay-signing
21
+ # path it is signed into the assertion `sub`; on the BYO-JWT (`ATLAS_JWT`)
22
+ # path it is ignored (identity lives in the token).
23
23
  # @param on_behalf_of [String, nil] optional NUID for the `On-Behalf-Of`
24
24
  # header. Falls through to {AtlasRb.config}.default_on_behalf_of when
25
25
  # omitted.
@@ -48,9 +48,9 @@ module AtlasRb
48
48
  # @param idempotency_key [String, nil] optional UUID. A repeat call with
49
49
  # the same key returns the originally-created FileSet instead of
50
50
  # creating a new one. See {AtlasRb::Work.create} for full semantics.
51
- # @param nuid [String, nil] optional acting user's NUID, forwarded as the
52
- # `User:` header. Required for cerberus-token requests; legacy bearer
53
- # tokens still resolve without it.
51
+ # @param nuid [String, nil] optional acting user's NUID. On the relay-signing
52
+ # path it is signed into the assertion `sub`; on the BYO-JWT (`ATLAS_JWT`)
53
+ # path it is ignored (identity lives in the token).
54
54
  # @param on_behalf_of [String, nil] optional NUID for the `On-Behalf-Of`
55
55
  # header. Falls through to {AtlasRb.config}.default_on_behalf_of when
56
56
  # omitted.
@@ -81,9 +81,9 @@ module AtlasRb
81
81
  # Delete a FileSet.
82
82
  #
83
83
  # @param id [String] the FileSet ID.
84
- # @param nuid [String, nil] optional acting user's NUID, forwarded as the
85
- # `User:` header. Required for cerberus-token requests; legacy bearer
86
- # tokens still resolve without it.
84
+ # @param nuid [String, nil] optional acting user's NUID. On the relay-signing
85
+ # path it is signed into the assertion `sub`; on the BYO-JWT (`ATLAS_JWT`)
86
+ # path it is ignored (identity lives in the token).
87
87
  # @param on_behalf_of [String, nil] optional NUID for the `On-Behalf-Of`
88
88
  # header. Falls through to {AtlasRb.config}.default_on_behalf_of when
89
89
  # omitted.
@@ -104,9 +104,9 @@ module AtlasRb
104
104
  #
105
105
  # @param id [String] the FileSet ID.
106
106
  # @param blob_path [String] path to the binary file on disk.
107
- # @param nuid [String, nil] optional acting user's NUID, forwarded as the
108
- # `User:` header. Required for cerberus-token requests; legacy bearer
109
- # tokens still resolve without it.
107
+ # @param nuid [String, nil] optional acting user's NUID. On the relay-signing
108
+ # path it is signed into the assertion `sub`; on the BYO-JWT (`ATLAS_JWT`)
109
+ # path it is ignored (identity lives in the token).
110
110
  # @param on_behalf_of [String, nil] optional NUID for the `On-Behalf-Of`
111
111
  # header. Falls through to {AtlasRb.config}.default_on_behalf_of when
112
112
  # omitted.
@@ -138,9 +138,9 @@ module AtlasRb
138
138
  #
139
139
  # @param id [String] the FileSet ID.
140
140
  # @param uri [String] the IIIF image-service base URI for the page.
141
- # @param nuid [String, nil] optional acting user's NUID, forwarded as the
142
- # `User:` header. Required for cerberus-token requests; legacy bearer
143
- # tokens still resolve without it.
141
+ # @param nuid [String, nil] optional acting user's NUID. On the relay-signing
142
+ # path it is signed into the assertion `sub`; on the BYO-JWT (`ATLAS_JWT`)
143
+ # path it is ignored (identity lives in the token).
144
144
  # @param on_behalf_of [String, nil] optional NUID for the `On-Behalf-Of`
145
145
  # header. Falls through to {AtlasRb.config}.default_on_behalf_of when
146
146
  # omitted.
@@ -26,9 +26,9 @@ module AtlasRb
26
26
  # pair so callers can dispatch on type.
27
27
  #
28
28
  # @param id [String] an Atlas resource ID of any type.
29
- # @param nuid [String, nil] optional acting user's NUID, forwarded as the
30
- # `User:` header. Required for cerberus-token requests; legacy bearer
31
- # tokens still resolve without it.
29
+ # @param nuid [String, nil] optional acting user's NUID. On the relay-signing
30
+ # path it is signed into the assertion `sub`; on the BYO-JWT (`ATLAS_JWT`)
31
+ # path it is ignored (identity lives in the token).
32
32
  # @param on_behalf_of [String, nil] optional NUID for the `On-Behalf-Of`
33
33
  # header. Falls through to {AtlasRb.config}.default_on_behalf_of when
34
34
  # omitted.
@@ -65,9 +65,9 @@ module AtlasRb
65
65
  #
66
66
  # @param ids [Array<String>] resource NOIDs to resolve. (Raw Valkyrie ids
67
67
  # are not a supported input — the endpoint resolves alternate ids only.)
68
- # @param nuid [String, nil] optional acting user's NUID, forwarded as the
69
- # `User:` header. Required for cerberus-token requests; legacy bearer
70
- # tokens still resolve without it.
68
+ # @param nuid [String, nil] optional acting user's NUID. On the relay-signing
69
+ # path it is signed into the assertion `sub`; on the BYO-JWT (`ATLAS_JWT`)
70
+ # path it is ignored (identity lives in the token).
71
71
  # @param on_behalf_of [String, nil] optional NUID for the `On-Behalf-Of`
72
72
  # header. Falls through to {AtlasRb.config}.default_on_behalf_of when
73
73
  # omitted.
@@ -90,9 +90,9 @@ module AtlasRb
90
90
  # Useful for surfacing validation errors in UIs before the user commits.
91
91
  #
92
92
  # @param xml_path [String] path to a MODS XML file on disk.
93
- # @param nuid [String, nil] optional acting user's NUID, forwarded as the
94
- # `User:` header. Required for cerberus-token requests; legacy bearer
95
- # tokens still resolve without it.
93
+ # @param nuid [String, nil] optional acting user's NUID. On the relay-signing
94
+ # path it is signed into the assertion `sub`; on the BYO-JWT (`ATLAS_JWT`)
95
+ # path it is ignored (identity lives in the token).
96
96
  # @param on_behalf_of [String, nil] optional NUID for the `On-Behalf-Of`
97
97
  # header. Falls through to {AtlasRb.config}.default_on_behalf_of when
98
98
  # omitted.
@@ -111,9 +111,9 @@ module AtlasRb
111
111
  # Fetch the access-control entries for a resource.
112
112
  #
113
113
  # @param id [String] an Atlas resource ID.
114
- # @param nuid [String, nil] optional acting user's NUID, forwarded as the
115
- # `User:` header. Required for cerberus-token requests; legacy bearer
116
- # tokens still resolve without it.
114
+ # @param nuid [String, nil] optional acting user's NUID. On the relay-signing
115
+ # path it is signed into the assertion `sub`; on the BYO-JWT (`ATLAS_JWT`)
116
+ # path it is ignored (identity lives in the token).
117
117
  # @param on_behalf_of [String, nil] optional NUID for the `On-Behalf-Of`
118
118
  # header. Falls through to {AtlasRb.config}.default_on_behalf_of when
119
119
  # omitted.
@@ -146,9 +146,9 @@ module AtlasRb
146
146
  # history in one shot.
147
147
  #
148
148
  # @param id [String] an Atlas resource ID.
149
- # @param nuid [String, nil] optional acting user's NUID, forwarded as the
150
- # `User:` header. Required for cerberus-token requests; legacy bearer
151
- # tokens still resolve without it.
149
+ # @param nuid [String, nil] optional acting user's NUID. On the relay-signing
150
+ # path it is signed into the assertion `sub`; on the BYO-JWT (`ATLAS_JWT`)
151
+ # path it is ignored (identity lives in the token).
152
152
  # @param on_behalf_of [String, nil] optional NUID for the `On-Behalf-Of`
153
153
  # header. Falls through to {AtlasRb.config}.default_on_behalf_of when
154
154
  # omitted.
@@ -187,9 +187,9 @@ module AtlasRb
187
187
  # responses, matching {history}.
188
188
  #
189
189
  # @param id [String] an Atlas resource ID.
190
- # @param nuid [String, nil] optional acting user's NUID, forwarded as the
191
- # `User:` header. Required for cerberus-token requests; legacy bearer
192
- # tokens still resolve without it.
190
+ # @param nuid [String, nil] optional acting user's NUID. On the relay-signing
191
+ # path it is signed into the assertion `sub`; on the BYO-JWT (`ATLAS_JWT`)
192
+ # path it is ignored (identity lives in the token).
193
193
  # @param on_behalf_of [String, nil] optional NUID for the `On-Behalf-Of`
194
194
  # header. Falls through to {AtlasRb.config}.default_on_behalf_of when
195
195
  # omitted.
@@ -225,9 +225,9 @@ module AtlasRb
225
225
  # e.g. `"v3"`.
226
226
  # @param kind [String, nil] response format extension. Omit (or pass
227
227
  # `"xml"`) for the historical XML — the only format the server retains.
228
- # @param nuid [String, nil] optional acting user's NUID, forwarded as the
229
- # `User:` header. Required for cerberus-token requests; legacy bearer
230
- # tokens still resolve without it.
228
+ # @param nuid [String, nil] optional acting user's NUID. On the relay-signing
229
+ # path it is signed into the assertion `sub`; on the BYO-JWT (`ATLAS_JWT`)
230
+ # path it is ignored (identity lives in the token).
231
231
  # @param on_behalf_of [String, nil] optional NUID for the `On-Behalf-Of`
232
232
  # header. Falls through to {AtlasRb.config}.default_on_behalf_of when
233
233
  # omitted.
@@ -10,10 +10,10 @@ module AtlasRb
10
10
  #
11
11
  # The `:system` principal needs a different bearer token (carried in
12
12
  # `Rails.application.credentials.atlas_system_token`, not the user-side
13
- # `ENV["ATLAS_TOKEN"]`) and pairs with a different `User:` header (always
14
- # {NUID}, never the acting user). Atlas's `require_auth` enforces the
15
- # pairing — a user token paired with the system NUID, or the system token
16
- # paired with a real user NUID, both 401.
13
+ # relay-signing / `ATLAS_JWT` credentials) and pairs with a hard-pinned
14
+ # `User:` header (always {NUID}, never the acting user). Atlas's
15
+ # `require_auth` enforces the pairing — the system token paired with a
16
+ # real-user NUID is a 401.
17
17
  #
18
18
  # Routing system calls through their own class makes the carve-out
19
19
  # structural: there is no kwarg that flips a regular call into a system
data/lib/atlas_rb/user.rb CHANGED
@@ -5,8 +5,9 @@ module AtlasRb
5
5
  # resolution.
6
6
  #
7
7
  # This is a **user-context** binding: calls authenticate as the acting
8
- # user via the standard `ATLAS_TOKEN` + `User:` header pairing, like every
9
- # other top-level class. It is deliberately *not* part of
8
+ # user via the standard relay-signing path (the acting NUID is signed into
9
+ # the assertion `sub`), like every other top-level class. It is
10
+ # deliberately *not* part of
10
11
  # {AtlasRb::System} — that namespace is structurally reserved for
11
12
  # system-token calls ({System::User.find_or_create}), and directory
12
13
  # lookups are an ordinary logged-in-user capability.
@@ -30,9 +31,9 @@ module AtlasRb
30
31
  # it by name; a blank query resolves to an empty list.
31
32
  #
32
33
  # @param query [String] name fragment or NUID prefix to match.
33
- # @param nuid [String, nil] optional acting user's NUID, forwarded as the
34
- # `User:` header. Required for cerberus-token requests; legacy bearer
35
- # tokens still resolve without it.
34
+ # @param nuid [String, nil] optional acting user's NUID. On the relay-signing
35
+ # path it is signed into the assertion `sub`; on the BYO-JWT (`ATLAS_JWT`)
36
+ # path it is ignored (identity lives in the token).
36
37
  # @return [Array<AtlasRb::Mash>] matching directory entries, each
37
38
  # carrying `nuid` and `name`.
38
39
  #
@@ -49,9 +50,9 @@ module AtlasRb
49
50
  #
50
51
  # @param target_nuid [String] the NUID being looked up — the *subject*
51
52
  # of the call, distinct from the acting `nuid:` kwarg.
52
- # @param nuid [String, nil] optional acting user's NUID, forwarded as the
53
- # `User:` header. Required for cerberus-token requests; legacy bearer
54
- # tokens still resolve without it.
53
+ # @param nuid [String, nil] optional acting user's NUID. On the relay-signing
54
+ # path it is signed into the assertion `sub`; on the BYO-JWT (`ATLAS_JWT`)
55
+ # path it is ignored (identity lives in the token).
55
56
  # @return [AtlasRb::Mash, nil] the `nuid` + `name` entry, or `nil` when
56
57
  # Atlas reports the NUID as absent (unknown, or held by an excluded
57
58
  # role — the two are indistinguishable on the wire by design).
@@ -73,9 +74,9 @@ module AtlasRb
73
74
  # input — callers index by `nuid`. Atlas caps the batch at 100.
74
75
  #
75
76
  # @param nuids [Array<String>, String] the NUIDs to resolve.
76
- # @param nuid [String, nil] optional acting user's NUID, forwarded as the
77
- # `User:` header. Required for cerberus-token requests; legacy bearer
78
- # tokens still resolve without it.
77
+ # @param nuid [String, nil] optional acting user's NUID. On the relay-signing
78
+ # path it is signed into the assertion `sub`; on the BYO-JWT (`ATLAS_JWT`)
79
+ # path it is ignored (identity lives in the token).
79
80
  # @return [Array<AtlasRb::Mash>] resolved entries, each carrying `nuid`
80
81
  # and `name`, ordered by name.
81
82
  #