@game-infra/api-schemas-core 0.0.0 → 0.3.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.
package/dist/index.js CHANGED
@@ -3,7 +3,9 @@ export { ApiResponseSchema, createSuccessResponseSchema, TimestampFieldsSchema,
3
3
  // AI provider enum
4
4
  export { AI_PROVIDERS, AIProviderSchema } from "./aiProvider.js";
5
5
  // Auth
6
- export { AuthValidation, RegisterRequestSchema, AuthResponseFieldsSchema, RegisterResponseSchema, LoginRequestSchema, LoginResponseSchema, ValidateTokenRequestSchema, ValidateTokenResponseSchema, ValidateServiceTokenResponseSchema, } from "./auth.js";
6
+ export { AuthValidation, RegisterRequestSchema, AuthResponseFieldsSchema, RegisterResponseSchema, LoginRequestSchema, LoginResponseSchema, ValidateTokenRequestSchema, ValidateTokenResponseSchema, ValidateServiceTokenResponseSchema, IdentityReadinessResponseSchema, } from "./auth.js";
7
+ // Service tokens
8
+ export { ServiceTokenValidation, ServiceTokenIdSchema, ServiceTokenSchema, CreateServiceTokenRequestSchema, CreateServiceTokenResponseSchema, ListServiceTokensResponseSchema, RevokeServiceTokenResponseSchema, ServiceTokenValidateRequestSchema, ServiceTokenRejectionSchema, ServiceTokenValidateResponseSchema, PurgeServiceTokensResponseSchema, } from "./serviceToken.js";
7
9
  // Backup
8
10
  export { BackupInfoSchema, TriggerBackupResponseSchema, ListBackupsResponseSchema, RestoreBackupRequestSchema, RestoreBackupResponseSchema, DownloadBackupResponseSchema, } from "./backup.js";
9
11
  // Feedback
@@ -16,5 +18,5 @@ export { GameEntitySaveRequestSchema, GameEntitySaveResponseSchema, GameEntityLo
16
18
  export { DEFAULT_DEVELOPMENT_API_URL, createApiUrlResolver } from "./apiConfig.js";
17
19
  // Typed endpoint contracts (toad-contracts). Each contract carries its own
18
20
  // `pathResolver`; wire them into a client via @toad-contracts/frontend-http-client.
19
- export { authRegisterContract, authLoginContract, authValidateContract, authValidateServiceTokenContract, savegameSaveContract, savegameLoadContract, savegameListSlotsContract, gameEntitySaveContract, gameEntityUpdateContract, gameEntityLoadContract, gameEntityListContract, gameEntityListAllContract, gameEntityDeleteContract, gameEntityBulkSaveContract, backupTriggerContract, backupListContract, backupRestoreContract, backupDownloadContract, feedbackSubmitContract, heartbeatContract, } from "./contracts.js";
21
+ export { authRegisterContract, authLoginContract, authValidateContract, authValidateServiceTokenContract, identityReadinessContract, serviceTokenCreateContract, serviceTokenListContract, serviceTokenRevokeContract, serviceTokenValidateContract, serviceTokenPurgeContract, savegameSaveContract, savegameLoadContract, savegameListSlotsContract, gameEntitySaveContract, gameEntityUpdateContract, gameEntityLoadContract, gameEntityListContract, gameEntityListAllContract, gameEntityDeleteContract, gameEntityBulkSaveContract, backupTriggerContract, backupListContract, backupRestoreContract, backupDownloadContract, feedbackSubmitContract, heartbeatContract, } from "./contracts.js";
20
22
  //# sourceMappingURL=index.js.map
package/dist/index.js.map CHANGED
@@ -1 +1 @@
1
- {"version":3,"file":"index.js","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAAA,kDAAkD;AAClD,OAAO,EACL,iBAAiB,EACjB,2BAA2B,EAC3B,qBAAqB,EACrB,oBAAoB,GACrB,MAAM,aAAa,CAAC;AAGrB,mBAAmB;AACnB,OAAO,EAAE,YAAY,EAAE,gBAAgB,EAAE,MAAM,iBAAiB,CAAC;AAGjE,OAAO;AACP,OAAO,EACL,cAAc,EACd,qBAAqB,EACrB,wBAAwB,EACxB,sBAAsB,EACtB,kBAAkB,EAClB,mBAAmB,EACnB,0BAA0B,EAC1B,2BAA2B,EAC3B,kCAAkC,GACnC,MAAM,WAAW,CAAC;AAWnB,SAAS;AACT,OAAO,EACL,gBAAgB,EAChB,2BAA2B,EAC3B,yBAAyB,EACzB,0BAA0B,EAC1B,2BAA2B,EAC3B,4BAA4B,GAC7B,MAAM,aAAa,CAAC;AAUrB,WAAW;AACX,OAAO,EACL,YAAY,EACZ,2BAA2B,EAC3B,4BAA4B,GAC7B,MAAM,eAAe,CAAC;AAGvB,WAAW;AACX,OAAO,EACL,yBAAyB,EACzB,0BAA0B,EAC1B,0BAA0B,EAC1B,cAAc,EACd,+BAA+B,GAChC,MAAM,eAAe,CAAC;AASvB,gBAAgB;AAChB,OAAO,EACL,2BAA2B,EAC3B,4BAA4B,EAC5B,4BAA4B,EAC5B,oBAAoB,EACpB,4BAA4B,EAC5B,8BAA8B,EAC9B,+BAA+B,EAC/B,gCAAgC,GACjC,MAAM,iBAAiB,CAAC;AAYzB,2BAA2B;AAC3B,OAAO,EAAE,2BAA2B,EAAE,oBAAoB,EAAE,MAAM,gBAAgB,CAAC;AAGnF,2EAA2E;AAC3E,oFAAoF;AAEpF,OAAO,EACL,oBAAoB,EACpB,iBAAiB,EACjB,oBAAoB,EACpB,gCAAgC,EAChC,oBAAoB,EACpB,oBAAoB,EACpB,yBAAyB,EACzB,sBAAsB,EACtB,wBAAwB,EACxB,sBAAsB,EACtB,sBAAsB,EACtB,yBAAyB,EACzB,wBAAwB,EACxB,0BAA0B,EAC1B,qBAAqB,EACrB,kBAAkB,EAClB,qBAAqB,EACrB,sBAAsB,EACtB,sBAAsB,EACtB,iBAAiB,GAClB,MAAM,gBAAgB,CAAC"}
1
+ {"version":3,"file":"index.js","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAAA,kDAAkD;AAClD,OAAO,EACL,iBAAiB,EACjB,2BAA2B,EAC3B,qBAAqB,EACrB,oBAAoB,GACrB,MAAM,aAAa,CAAC;AAGrB,mBAAmB;AACnB,OAAO,EAAE,YAAY,EAAE,gBAAgB,EAAE,MAAM,iBAAiB,CAAC;AAGjE,OAAO;AACP,OAAO,EACL,cAAc,EACd,qBAAqB,EACrB,wBAAwB,EACxB,sBAAsB,EACtB,kBAAkB,EAClB,mBAAmB,EACnB,0BAA0B,EAC1B,2BAA2B,EAC3B,kCAAkC,EAClC,+BAA+B,GAChC,MAAM,WAAW,CAAC;AAYnB,iBAAiB;AACjB,OAAO,EACL,sBAAsB,EACtB,oBAAoB,EACpB,kBAAkB,EAClB,+BAA+B,EAC/B,gCAAgC,EAChC,+BAA+B,EAC/B,gCAAgC,EAChC,iCAAiC,EACjC,2BAA2B,EAC3B,kCAAkC,EAClC,gCAAgC,GACjC,MAAM,mBAAmB,CAAC;AAa3B,SAAS;AACT,OAAO,EACL,gBAAgB,EAChB,2BAA2B,EAC3B,yBAAyB,EACzB,0BAA0B,EAC1B,2BAA2B,EAC3B,4BAA4B,GAC7B,MAAM,aAAa,CAAC;AAUrB,WAAW;AACX,OAAO,EACL,YAAY,EACZ,2BAA2B,EAC3B,4BAA4B,GAC7B,MAAM,eAAe,CAAC;AAGvB,WAAW;AACX,OAAO,EACL,yBAAyB,EACzB,0BAA0B,EAC1B,0BAA0B,EAC1B,cAAc,EACd,+BAA+B,GAChC,MAAM,eAAe,CAAC;AASvB,gBAAgB;AAChB,OAAO,EACL,2BAA2B,EAC3B,4BAA4B,EAC5B,4BAA4B,EAC5B,oBAAoB,EACpB,4BAA4B,EAC5B,8BAA8B,EAC9B,+BAA+B,EAC/B,gCAAgC,GACjC,MAAM,iBAAiB,CAAC;AAYzB,2BAA2B;AAC3B,OAAO,EAAE,2BAA2B,EAAE,oBAAoB,EAAE,MAAM,gBAAgB,CAAC;AAGnF,2EAA2E;AAC3E,oFAAoF;AAEpF,OAAO,EACL,oBAAoB,EACpB,iBAAiB,EACjB,oBAAoB,EACpB,gCAAgC,EAChC,yBAAyB,EACzB,0BAA0B,EAC1B,wBAAwB,EACxB,0BAA0B,EAC1B,4BAA4B,EAC5B,yBAAyB,EACzB,oBAAoB,EACpB,oBAAoB,EACpB,yBAAyB,EACzB,sBAAsB,EACtB,wBAAwB,EACxB,sBAAsB,EACtB,sBAAsB,EACtB,yBAAyB,EACzB,wBAAwB,EACxB,0BAA0B,EAC1B,qBAAqB,EACrB,kBAAkB,EAClB,qBAAqB,EACrB,sBAAsB,EACtB,sBAAsB,EACtB,iBAAiB,GAClB,MAAM,gBAAgB,CAAC"}
@@ -0,0 +1,393 @@
1
+ import { type InferOutput } from "valibot";
2
+ /**
3
+ * Service tokens are long-lived credentials a script or backend service
4
+ * presents to game-infra APIs on behalf of the account that created them.
5
+ *
6
+ * The issuer never stores the token. It stores only the reference needed to
7
+ * withdraw one — the token id, its owner, and its expiry — and the token itself
8
+ * carries that id, so revocation is a write against the id rather than a lookup
9
+ * of the secret. A token is therefore shown exactly once, at creation.
10
+ */
11
+ /**
12
+ * Bounds shared by the UI and the service, so both reject the same input.
13
+ *
14
+ * The TTL ceiling is a year: past that the token stops being a credential
15
+ * anyone rotates and becomes one nobody remembers issuing, and the expiry is
16
+ * the only thing that retires a token no one revokes.
17
+ *
18
+ * @example
19
+ * ```ts
20
+ * import { ServiceTokenValidation } from '@game-infra/api-schemas-core'
21
+ *
22
+ * const ttl = Math.min(requested, ServiceTokenValidation.MAX_TTL_SECONDS)
23
+ * ```
24
+ */
25
+ export declare const ServiceTokenValidation: {
26
+ readonly MIN_NAME_LENGTH: 1;
27
+ readonly MAX_NAME_LENGTH: 100;
28
+ /** One hour. Shorter than this and the token cannot outlive a login. */
29
+ readonly MIN_TTL_SECONDS: number;
30
+ /** 365 days. */
31
+ readonly MAX_TTL_SECONDS: number;
32
+ /** 30 days — the default a caller gets when it names no TTL. */
33
+ readonly DEFAULT_TTL_SECONDS: number;
34
+ /** Token ids are `st_` plus 32 lowercase hex characters. */
35
+ readonly TOKEN_ID_PATTERN: RegExp;
36
+ };
37
+ /**
38
+ * A stored service-token id.
39
+ *
40
+ * @example
41
+ * ```ts
42
+ * import { ServiceTokenIdSchema } from '@game-infra/api-schemas-core'
43
+ * import { parse } from 'valibot'
44
+ *
45
+ * parse(ServiceTokenIdSchema, 'st_0123456789abcdef0123456789abcdef')
46
+ * ```
47
+ */
48
+ export declare const ServiceTokenIdSchema: import("valibot").SchemaWithPipe<readonly [import("valibot").StringSchema<undefined>, import("valibot").RegexAction<string, "Not a service-token id">]>;
49
+ /**
50
+ * Everything the issuer keeps about a service token — which is everything
51
+ * except the token.
52
+ *
53
+ * @example
54
+ * ```ts
55
+ * import type { ServiceToken } from '@game-infra/api-schemas-core'
56
+ *
57
+ * const isLive = (token: ServiceToken) => !token.revokedAt && Date.parse(token.expiresAt) > Date.now()
58
+ * ```
59
+ */
60
+ export declare const ServiceTokenSchema: import("valibot").ObjectSchema<{
61
+ /** Token id, carried by the token as its `jti` claim. */
62
+ readonly id: import("valibot").SchemaWithPipe<readonly [import("valibot").StringSchema<undefined>, import("valibot").RegexAction<string, "Not a service-token id">]>;
63
+ /** Caller-supplied label, the only way a human tells two tokens apart. */
64
+ readonly name: import("valibot").StringSchema<undefined>;
65
+ /** Account the token acts as. */
66
+ readonly userId: import("valibot").NumberSchema<undefined>;
67
+ /** Username of that account, as of issue time. */
68
+ readonly username: import("valibot").StringSchema<undefined>;
69
+ /** Authorization claims the token carries; never wider than the creator's. */
70
+ readonly claims: import("valibot").ArraySchema<import("valibot").StringSchema<undefined>, undefined>;
71
+ /** ISO-8601 issue time. */
72
+ readonly createdAt: import("valibot").StringSchema<undefined>;
73
+ /** ISO-8601 expiry, stamped into the token and not extendable. */
74
+ readonly expiresAt: import("valibot").StringSchema<undefined>;
75
+ /** ISO-8601 revocation time, or `null` while the token is still honoured. */
76
+ readonly revokedAt: import("valibot").NullableSchema<import("valibot").StringSchema<undefined>, undefined>;
77
+ /** ISO-8601 time the token last validated successfully, or `null`. */
78
+ readonly lastUsedAt: import("valibot").NullableSchema<import("valibot").StringSchema<undefined>, undefined>;
79
+ }, undefined>;
80
+ /**
81
+ * Inferred stored service-token record.
82
+ *
83
+ * @example
84
+ * ```ts
85
+ * import type { ServiceToken } from '@game-infra/api-schemas-core'
86
+ *
87
+ * const id: ServiceToken['id'] = 'st_0123456789abcdef0123456789abcdef'
88
+ * ```
89
+ */
90
+ export type ServiceToken = InferOutput<typeof ServiceTokenSchema>;
91
+ /**
92
+ * Request to mint a service token.
93
+ *
94
+ * `claims` is a request, not a grant: the service intersects it with the
95
+ * creator's own claims, so a token can never reach further than the account
96
+ * that created it.
97
+ *
98
+ * @example
99
+ * ```ts
100
+ * import { CreateServiceTokenRequestSchema } from '@game-infra/api-schemas-core'
101
+ * import { parse } from 'valibot'
102
+ *
103
+ * parse(CreateServiceTokenRequestSchema, { name: 'nightly-import', ttlSeconds: 604800 })
104
+ * ```
105
+ */
106
+ export declare const CreateServiceTokenRequestSchema: import("valibot").ObjectSchema<{
107
+ readonly name: import("valibot").SchemaWithPipe<readonly [import("valibot").StringSchema<undefined>, import("valibot").MinLengthAction<string, 1, "Name is required">, import("valibot").MaxLengthAction<string, 100, undefined>]>;
108
+ readonly ttlSeconds: import("valibot").OptionalSchema<import("valibot").SchemaWithPipe<readonly [import("valibot").NumberSchema<undefined>, import("valibot").IntegerAction<number, "TTL must be a whole number of seconds">, import("valibot").MinValueAction<number, number, undefined>, import("valibot").MaxValueAction<number, number, undefined>]>, undefined>;
109
+ readonly claims: import("valibot").OptionalSchema<import("valibot").ArraySchema<import("valibot").StringSchema<undefined>, undefined>, undefined>;
110
+ }, undefined>;
111
+ /**
112
+ * Inferred create-service-token request.
113
+ *
114
+ * @example
115
+ * ```ts
116
+ * import type { CreateServiceTokenRequest } from '@game-infra/api-schemas-core'
117
+ *
118
+ * const request: CreateServiceTokenRequest = { name: 'nightly-import' }
119
+ * ```
120
+ */
121
+ export type CreateServiceTokenRequest = InferOutput<typeof CreateServiceTokenRequestSchema>;
122
+ /**
123
+ * The one and only response that carries the token itself.
124
+ *
125
+ * @example
126
+ * ```ts
127
+ * import type { CreateServiceTokenResponse } from '@game-infra/api-schemas-core'
128
+ *
129
+ * const show = (response: CreateServiceTokenResponse) => response.token
130
+ * ```
131
+ */
132
+ export declare const CreateServiceTokenResponseSchema: import("valibot").ObjectSchema<{
133
+ readonly success: import("valibot").BooleanSchema<undefined>;
134
+ readonly error: import("valibot").OptionalSchema<import("valibot").StringSchema<undefined>, undefined>;
135
+ } & {
136
+ /** The signed token. Not stored, and not retrievable again. */
137
+ token: import("valibot").OptionalSchema<import("valibot").StringSchema<undefined>, undefined>;
138
+ serviceToken: import("valibot").OptionalSchema<import("valibot").ObjectSchema<{
139
+ /** Token id, carried by the token as its `jti` claim. */
140
+ readonly id: import("valibot").SchemaWithPipe<readonly [import("valibot").StringSchema<undefined>, import("valibot").RegexAction<string, "Not a service-token id">]>;
141
+ /** Caller-supplied label, the only way a human tells two tokens apart. */
142
+ readonly name: import("valibot").StringSchema<undefined>;
143
+ /** Account the token acts as. */
144
+ readonly userId: import("valibot").NumberSchema<undefined>;
145
+ /** Username of that account, as of issue time. */
146
+ readonly username: import("valibot").StringSchema<undefined>;
147
+ /** Authorization claims the token carries; never wider than the creator's. */
148
+ readonly claims: import("valibot").ArraySchema<import("valibot").StringSchema<undefined>, undefined>;
149
+ /** ISO-8601 issue time. */
150
+ readonly createdAt: import("valibot").StringSchema<undefined>;
151
+ /** ISO-8601 expiry, stamped into the token and not extendable. */
152
+ readonly expiresAt: import("valibot").StringSchema<undefined>;
153
+ /** ISO-8601 revocation time, or `null` while the token is still honoured. */
154
+ readonly revokedAt: import("valibot").NullableSchema<import("valibot").StringSchema<undefined>, undefined>;
155
+ /** ISO-8601 time the token last validated successfully, or `null`. */
156
+ readonly lastUsedAt: import("valibot").NullableSchema<import("valibot").StringSchema<undefined>, undefined>;
157
+ }, undefined>, undefined>;
158
+ }, undefined>;
159
+ /**
160
+ * Inferred create-service-token response.
161
+ *
162
+ * @example
163
+ * ```ts
164
+ * import type { CreateServiceTokenResponse } from '@game-infra/api-schemas-core'
165
+ *
166
+ * const ok: CreateServiceTokenResponse['success'] = true
167
+ * ```
168
+ */
169
+ export type CreateServiceTokenResponse = InferOutput<typeof CreateServiceTokenResponseSchema>;
170
+ /**
171
+ * The caller's own service tokens, newest first.
172
+ *
173
+ * @example
174
+ * ```ts
175
+ * import type { ListServiceTokensResponse } from '@game-infra/api-schemas-core'
176
+ *
177
+ * const count = (response: ListServiceTokensResponse) => response.serviceTokens?.length ?? 0
178
+ * ```
179
+ */
180
+ export declare const ListServiceTokensResponseSchema: import("valibot").ObjectSchema<{
181
+ readonly success: import("valibot").BooleanSchema<undefined>;
182
+ readonly error: import("valibot").OptionalSchema<import("valibot").StringSchema<undefined>, undefined>;
183
+ } & {
184
+ serviceTokens: import("valibot").OptionalSchema<import("valibot").ArraySchema<import("valibot").ObjectSchema<{
185
+ /** Token id, carried by the token as its `jti` claim. */
186
+ readonly id: import("valibot").SchemaWithPipe<readonly [import("valibot").StringSchema<undefined>, import("valibot").RegexAction<string, "Not a service-token id">]>;
187
+ /** Caller-supplied label, the only way a human tells two tokens apart. */
188
+ readonly name: import("valibot").StringSchema<undefined>;
189
+ /** Account the token acts as. */
190
+ readonly userId: import("valibot").NumberSchema<undefined>;
191
+ /** Username of that account, as of issue time. */
192
+ readonly username: import("valibot").StringSchema<undefined>;
193
+ /** Authorization claims the token carries; never wider than the creator's. */
194
+ readonly claims: import("valibot").ArraySchema<import("valibot").StringSchema<undefined>, undefined>;
195
+ /** ISO-8601 issue time. */
196
+ readonly createdAt: import("valibot").StringSchema<undefined>;
197
+ /** ISO-8601 expiry, stamped into the token and not extendable. */
198
+ readonly expiresAt: import("valibot").StringSchema<undefined>;
199
+ /** ISO-8601 revocation time, or `null` while the token is still honoured. */
200
+ readonly revokedAt: import("valibot").NullableSchema<import("valibot").StringSchema<undefined>, undefined>;
201
+ /** ISO-8601 time the token last validated successfully, or `null`. */
202
+ readonly lastUsedAt: import("valibot").NullableSchema<import("valibot").StringSchema<undefined>, undefined>;
203
+ }, undefined>, undefined>, undefined>;
204
+ /**
205
+ * The retention window the issuer applies before deleting an expired
206
+ * record, in seconds.
207
+ *
208
+ * A client cannot work out which records a purge would actually remove
209
+ * without it: an expired token's row survives until the window has passed
210
+ * too, so "expired" and "purgeable" are different sets, and a UI counting the
211
+ * first offers to delete rows the service will keep. Optional because a
212
+ * deployment predating this field does not send it.
213
+ */
214
+ retentionSeconds: import("valibot").OptionalSchema<import("valibot").NumberSchema<undefined>, undefined>;
215
+ }, undefined>;
216
+ /**
217
+ * Inferred list-service-tokens response.
218
+ *
219
+ * @example
220
+ * ```ts
221
+ * import type { ListServiceTokensResponse } from '@game-infra/api-schemas-core'
222
+ *
223
+ * const ok: ListServiceTokensResponse['success'] = true
224
+ * ```
225
+ */
226
+ export type ListServiceTokensResponse = InferOutput<typeof ListServiceTokensResponseSchema>;
227
+ /**
228
+ * Result of revoking a service token.
229
+ *
230
+ * @example
231
+ * ```ts
232
+ * import type { RevokeServiceTokenResponse } from '@game-infra/api-schemas-core'
233
+ *
234
+ * const when = (response: RevokeServiceTokenResponse) => response.serviceToken?.revokedAt
235
+ * ```
236
+ */
237
+ export declare const RevokeServiceTokenResponseSchema: import("valibot").ObjectSchema<{
238
+ readonly success: import("valibot").BooleanSchema<undefined>;
239
+ readonly error: import("valibot").OptionalSchema<import("valibot").StringSchema<undefined>, undefined>;
240
+ } & {
241
+ serviceToken: import("valibot").OptionalSchema<import("valibot").ObjectSchema<{
242
+ /** Token id, carried by the token as its `jti` claim. */
243
+ readonly id: import("valibot").SchemaWithPipe<readonly [import("valibot").StringSchema<undefined>, import("valibot").RegexAction<string, "Not a service-token id">]>;
244
+ /** Caller-supplied label, the only way a human tells two tokens apart. */
245
+ readonly name: import("valibot").StringSchema<undefined>;
246
+ /** Account the token acts as. */
247
+ readonly userId: import("valibot").NumberSchema<undefined>;
248
+ /** Username of that account, as of issue time. */
249
+ readonly username: import("valibot").StringSchema<undefined>;
250
+ /** Authorization claims the token carries; never wider than the creator's. */
251
+ readonly claims: import("valibot").ArraySchema<import("valibot").StringSchema<undefined>, undefined>;
252
+ /** ISO-8601 issue time. */
253
+ readonly createdAt: import("valibot").StringSchema<undefined>;
254
+ /** ISO-8601 expiry, stamped into the token and not extendable. */
255
+ readonly expiresAt: import("valibot").StringSchema<undefined>;
256
+ /** ISO-8601 revocation time, or `null` while the token is still honoured. */
257
+ readonly revokedAt: import("valibot").NullableSchema<import("valibot").StringSchema<undefined>, undefined>;
258
+ /** ISO-8601 time the token last validated successfully, or `null`. */
259
+ readonly lastUsedAt: import("valibot").NullableSchema<import("valibot").StringSchema<undefined>, undefined>;
260
+ }, undefined>, undefined>;
261
+ }, undefined>;
262
+ /**
263
+ * Inferred revoke-service-token response.
264
+ *
265
+ * @example
266
+ * ```ts
267
+ * import type { RevokeServiceTokenResponse } from '@game-infra/api-schemas-core'
268
+ *
269
+ * const ok: RevokeServiceTokenResponse['success'] = true
270
+ * ```
271
+ */
272
+ export type RevokeServiceTokenResponse = InferOutput<typeof RevokeServiceTokenResponseSchema>;
273
+ /**
274
+ * Token a service or script asks the issuer to check.
275
+ *
276
+ * @example
277
+ * ```ts
278
+ * import { ServiceTokenValidateRequestSchema } from '@game-infra/api-schemas-core'
279
+ * import { parse } from 'valibot'
280
+ *
281
+ * parse(ServiceTokenValidateRequestSchema, { token: 'eyJhbGciOi...' })
282
+ * ```
283
+ */
284
+ export declare const ServiceTokenValidateRequestSchema: import("valibot").ObjectSchema<{
285
+ readonly token: import("valibot").StringSchema<undefined>;
286
+ }, undefined>;
287
+ /**
288
+ * Inferred service-token validation request.
289
+ *
290
+ * @example
291
+ * ```ts
292
+ * import type { ServiceTokenValidateRequest } from '@game-infra/api-schemas-core'
293
+ *
294
+ * const request: ServiceTokenValidateRequest = { token: 'eyJhbGciOi...' }
295
+ * ```
296
+ */
297
+ export type ServiceTokenValidateRequest = InferOutput<typeof ServiceTokenValidateRequestSchema>;
298
+ /**
299
+ * Why a service token was not accepted.
300
+ *
301
+ * `revoked` and `unknown` are the two answers a signature check alone cannot
302
+ * give, and they are the reason this endpoint exists next to `/auth/validate`:
303
+ * `unknown` covers a correctly signed token whose record has been purged, which
304
+ * a caller must treat exactly like a revoked one.
305
+ *
306
+ * @example
307
+ * ```ts
308
+ * import { ServiceTokenRejectionSchema } from '@game-infra/api-schemas-core'
309
+ * import { parse } from 'valibot'
310
+ *
311
+ * parse(ServiceTokenRejectionSchema, 'revoked')
312
+ * ```
313
+ */
314
+ export declare const ServiceTokenRejectionSchema: import("valibot").UnionSchema<[import("valibot").LiteralSchema<"invalid", undefined>, import("valibot").LiteralSchema<"expired", undefined>, import("valibot").LiteralSchema<"revoked", undefined>, import("valibot").LiteralSchema<"unknown", undefined>, import("valibot").LiteralSchema<"wrongTokenType", undefined>], undefined>;
315
+ /**
316
+ * Inferred service-token rejection reason.
317
+ *
318
+ * @example
319
+ * ```ts
320
+ * import type { ServiceTokenRejection } from '@game-infra/api-schemas-core'
321
+ *
322
+ * const reason: ServiceTokenRejection = 'expired'
323
+ * ```
324
+ */
325
+ export type ServiceTokenRejection = InferOutput<typeof ServiceTokenRejectionSchema>;
326
+ /**
327
+ * Verdict on a service token: signature, expiry, and the revocation list.
328
+ *
329
+ * @example
330
+ * ```ts
331
+ * import type { ServiceTokenValidateResponse } from '@game-infra/api-schemas-core'
332
+ *
333
+ * const accept = (response: ServiceTokenValidateResponse) => response.valid === true
334
+ * ```
335
+ */
336
+ export declare const ServiceTokenValidateResponseSchema: import("valibot").ObjectSchema<{
337
+ readonly success: import("valibot").BooleanSchema<undefined>;
338
+ readonly error: import("valibot").OptionalSchema<import("valibot").StringSchema<undefined>, undefined>;
339
+ } & {
340
+ valid: import("valibot").OptionalSchema<import("valibot").BooleanSchema<undefined>, undefined>;
341
+ /** Set only when `valid` is false. */
342
+ reason: import("valibot").OptionalSchema<import("valibot").UnionSchema<[import("valibot").LiteralSchema<"invalid", undefined>, import("valibot").LiteralSchema<"expired", undefined>, import("valibot").LiteralSchema<"revoked", undefined>, import("valibot").LiteralSchema<"unknown", undefined>, import("valibot").LiteralSchema<"wrongTokenType", undefined>], undefined>, undefined>;
343
+ tokenId: import("valibot").OptionalSchema<import("valibot").StringSchema<undefined>, undefined>;
344
+ userId: import("valibot").OptionalSchema<import("valibot").NumberSchema<undefined>, undefined>;
345
+ username: import("valibot").OptionalSchema<import("valibot").StringSchema<undefined>, undefined>;
346
+ claims: import("valibot").OptionalSchema<import("valibot").ArraySchema<import("valibot").StringSchema<undefined>, undefined>, undefined>;
347
+ expiresAt: import("valibot").OptionalSchema<import("valibot").StringSchema<undefined>, undefined>;
348
+ }, undefined>;
349
+ /**
350
+ * Inferred service-token validation response.
351
+ *
352
+ * @example
353
+ * ```ts
354
+ * import type { ServiceTokenValidateResponse } from '@game-infra/api-schemas-core'
355
+ *
356
+ * const ok: ServiceTokenValidateResponse['success'] = true
357
+ * ```
358
+ */
359
+ export type ServiceTokenValidateResponse = InferOutput<typeof ServiceTokenValidateResponseSchema>;
360
+ /**
361
+ * How many obsolete token records a purge deleted.
362
+ *
363
+ * A record is obsolete once the token it describes has expired past the
364
+ * retention window: an expired token fails signature-and-expiry verification
365
+ * everywhere, so keeping its record buys neither revocation nor an answer.
366
+ *
367
+ * @example
368
+ * ```ts
369
+ * import type { PurgeServiceTokensResponse } from '@game-infra/api-schemas-core'
370
+ *
371
+ * const freed = (response: PurgeServiceTokensResponse) => response.purged ?? 0
372
+ * ```
373
+ */
374
+ export declare const PurgeServiceTokensResponseSchema: import("valibot").ObjectSchema<{
375
+ readonly success: import("valibot").BooleanSchema<undefined>;
376
+ readonly error: import("valibot").OptionalSchema<import("valibot").StringSchema<undefined>, undefined>;
377
+ } & {
378
+ purged: import("valibot").OptionalSchema<import("valibot").NumberSchema<undefined>, undefined>;
379
+ /** Retention window applied, in seconds, so a caller can explain the count. */
380
+ retentionSeconds: import("valibot").OptionalSchema<import("valibot").NumberSchema<undefined>, undefined>;
381
+ }, undefined>;
382
+ /**
383
+ * Inferred purge-service-tokens response.
384
+ *
385
+ * @example
386
+ * ```ts
387
+ * import type { PurgeServiceTokensResponse } from '@game-infra/api-schemas-core'
388
+ *
389
+ * const ok: PurgeServiceTokensResponse['success'] = true
390
+ * ```
391
+ */
392
+ export type PurgeServiceTokensResponse = InferOutput<typeof PurgeServiceTokensResponseSchema>;
393
+ //# sourceMappingURL=serviceToken.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"serviceToken.d.ts","sourceRoot":"","sources":["../src/serviceToken.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,227 @@
1
+ import { array, boolean, integer, literal, maxLength, maxValue, minLength, minValue, nullable, number, object, optional, pipe, regex, string, union, } from "valibot";
2
+ import { createSuccessResponseSchema } from "./common.js";
3
+ /**
4
+ * Service tokens are long-lived credentials a script or backend service
5
+ * presents to game-infra APIs on behalf of the account that created them.
6
+ *
7
+ * The issuer never stores the token. It stores only the reference needed to
8
+ * withdraw one — the token id, its owner, and its expiry — and the token itself
9
+ * carries that id, so revocation is a write against the id rather than a lookup
10
+ * of the secret. A token is therefore shown exactly once, at creation.
11
+ */
12
+ /**
13
+ * Bounds shared by the UI and the service, so both reject the same input.
14
+ *
15
+ * The TTL ceiling is a year: past that the token stops being a credential
16
+ * anyone rotates and becomes one nobody remembers issuing, and the expiry is
17
+ * the only thing that retires a token no one revokes.
18
+ *
19
+ * @example
20
+ * ```ts
21
+ * import { ServiceTokenValidation } from '@game-infra/api-schemas-core'
22
+ *
23
+ * const ttl = Math.min(requested, ServiceTokenValidation.MAX_TTL_SECONDS)
24
+ * ```
25
+ */
26
+ export const ServiceTokenValidation = {
27
+ MIN_NAME_LENGTH: 1,
28
+ MAX_NAME_LENGTH: 100,
29
+ /** One hour. Shorter than this and the token cannot outlive a login. */
30
+ MIN_TTL_SECONDS: 60 * 60,
31
+ /** 365 days. */
32
+ MAX_TTL_SECONDS: 365 * 24 * 60 * 60,
33
+ /** 30 days — the default a caller gets when it names no TTL. */
34
+ DEFAULT_TTL_SECONDS: 30 * 24 * 60 * 60,
35
+ /** Token ids are `st_` plus 32 lowercase hex characters. */
36
+ TOKEN_ID_PATTERN: /^st_[0-9a-f]{32}$/,
37
+ };
38
+ /**
39
+ * A stored service-token id.
40
+ *
41
+ * @example
42
+ * ```ts
43
+ * import { ServiceTokenIdSchema } from '@game-infra/api-schemas-core'
44
+ * import { parse } from 'valibot'
45
+ *
46
+ * parse(ServiceTokenIdSchema, 'st_0123456789abcdef0123456789abcdef')
47
+ * ```
48
+ */
49
+ export const ServiceTokenIdSchema = pipe(string(), regex(ServiceTokenValidation.TOKEN_ID_PATTERN, "Not a service-token id"));
50
+ /**
51
+ * Everything the issuer keeps about a service token — which is everything
52
+ * except the token.
53
+ *
54
+ * @example
55
+ * ```ts
56
+ * import type { ServiceToken } from '@game-infra/api-schemas-core'
57
+ *
58
+ * const isLive = (token: ServiceToken) => !token.revokedAt && Date.parse(token.expiresAt) > Date.now()
59
+ * ```
60
+ */
61
+ export const ServiceTokenSchema = object({
62
+ /** Token id, carried by the token as its `jti` claim. */
63
+ id: ServiceTokenIdSchema,
64
+ /** Caller-supplied label, the only way a human tells two tokens apart. */
65
+ name: string(),
66
+ /** Account the token acts as. */
67
+ userId: number(),
68
+ /** Username of that account, as of issue time. */
69
+ username: string(),
70
+ /** Authorization claims the token carries; never wider than the creator's. */
71
+ claims: array(string()),
72
+ /** ISO-8601 issue time. */
73
+ createdAt: string(),
74
+ /** ISO-8601 expiry, stamped into the token and not extendable. */
75
+ expiresAt: string(),
76
+ /** ISO-8601 revocation time, or `null` while the token is still honoured. */
77
+ revokedAt: nullable(string()),
78
+ /** ISO-8601 time the token last validated successfully, or `null`. */
79
+ lastUsedAt: nullable(string()),
80
+ });
81
+ /**
82
+ * Request to mint a service token.
83
+ *
84
+ * `claims` is a request, not a grant: the service intersects it with the
85
+ * creator's own claims, so a token can never reach further than the account
86
+ * that created it.
87
+ *
88
+ * @example
89
+ * ```ts
90
+ * import { CreateServiceTokenRequestSchema } from '@game-infra/api-schemas-core'
91
+ * import { parse } from 'valibot'
92
+ *
93
+ * parse(CreateServiceTokenRequestSchema, { name: 'nightly-import', ttlSeconds: 604800 })
94
+ * ```
95
+ */
96
+ export const CreateServiceTokenRequestSchema = object({
97
+ name: pipe(string(), minLength(ServiceTokenValidation.MIN_NAME_LENGTH, "Name is required"), maxLength(ServiceTokenValidation.MAX_NAME_LENGTH)),
98
+ ttlSeconds: optional(pipe(number(), integer("TTL must be a whole number of seconds"), minValue(ServiceTokenValidation.MIN_TTL_SECONDS), maxValue(ServiceTokenValidation.MAX_TTL_SECONDS))),
99
+ claims: optional(array(string())),
100
+ });
101
+ /**
102
+ * The one and only response that carries the token itself.
103
+ *
104
+ * @example
105
+ * ```ts
106
+ * import type { CreateServiceTokenResponse } from '@game-infra/api-schemas-core'
107
+ *
108
+ * const show = (response: CreateServiceTokenResponse) => response.token
109
+ * ```
110
+ */
111
+ export const CreateServiceTokenResponseSchema = createSuccessResponseSchema({
112
+ /** The signed token. Not stored, and not retrievable again. */
113
+ token: optional(string()),
114
+ serviceToken: optional(ServiceTokenSchema),
115
+ });
116
+ /**
117
+ * The caller's own service tokens, newest first.
118
+ *
119
+ * @example
120
+ * ```ts
121
+ * import type { ListServiceTokensResponse } from '@game-infra/api-schemas-core'
122
+ *
123
+ * const count = (response: ListServiceTokensResponse) => response.serviceTokens?.length ?? 0
124
+ * ```
125
+ */
126
+ export const ListServiceTokensResponseSchema = createSuccessResponseSchema({
127
+ serviceTokens: optional(array(ServiceTokenSchema)),
128
+ /**
129
+ * The retention window the issuer applies before deleting an expired
130
+ * record, in seconds.
131
+ *
132
+ * A client cannot work out which records a purge would actually remove
133
+ * without it: an expired token's row survives until the window has passed
134
+ * too, so "expired" and "purgeable" are different sets, and a UI counting the
135
+ * first offers to delete rows the service will keep. Optional because a
136
+ * deployment predating this field does not send it.
137
+ */
138
+ retentionSeconds: optional(number()),
139
+ });
140
+ /**
141
+ * Result of revoking a service token.
142
+ *
143
+ * @example
144
+ * ```ts
145
+ * import type { RevokeServiceTokenResponse } from '@game-infra/api-schemas-core'
146
+ *
147
+ * const when = (response: RevokeServiceTokenResponse) => response.serviceToken?.revokedAt
148
+ * ```
149
+ */
150
+ export const RevokeServiceTokenResponseSchema = createSuccessResponseSchema({
151
+ serviceToken: optional(ServiceTokenSchema),
152
+ });
153
+ /**
154
+ * Token a service or script asks the issuer to check.
155
+ *
156
+ * @example
157
+ * ```ts
158
+ * import { ServiceTokenValidateRequestSchema } from '@game-infra/api-schemas-core'
159
+ * import { parse } from 'valibot'
160
+ *
161
+ * parse(ServiceTokenValidateRequestSchema, { token: 'eyJhbGciOi...' })
162
+ * ```
163
+ */
164
+ export const ServiceTokenValidateRequestSchema = object({ token: string() });
165
+ /**
166
+ * Why a service token was not accepted.
167
+ *
168
+ * `revoked` and `unknown` are the two answers a signature check alone cannot
169
+ * give, and they are the reason this endpoint exists next to `/auth/validate`:
170
+ * `unknown` covers a correctly signed token whose record has been purged, which
171
+ * a caller must treat exactly like a revoked one.
172
+ *
173
+ * @example
174
+ * ```ts
175
+ * import { ServiceTokenRejectionSchema } from '@game-infra/api-schemas-core'
176
+ * import { parse } from 'valibot'
177
+ *
178
+ * parse(ServiceTokenRejectionSchema, 'revoked')
179
+ * ```
180
+ */
181
+ export const ServiceTokenRejectionSchema = union([
182
+ literal("invalid"),
183
+ literal("expired"),
184
+ literal("revoked"),
185
+ literal("unknown"),
186
+ literal("wrongTokenType"),
187
+ ]);
188
+ /**
189
+ * Verdict on a service token: signature, expiry, and the revocation list.
190
+ *
191
+ * @example
192
+ * ```ts
193
+ * import type { ServiceTokenValidateResponse } from '@game-infra/api-schemas-core'
194
+ *
195
+ * const accept = (response: ServiceTokenValidateResponse) => response.valid === true
196
+ * ```
197
+ */
198
+ export const ServiceTokenValidateResponseSchema = createSuccessResponseSchema({
199
+ valid: optional(boolean()),
200
+ /** Set only when `valid` is false. */
201
+ reason: optional(ServiceTokenRejectionSchema),
202
+ tokenId: optional(string()),
203
+ userId: optional(number()),
204
+ username: optional(string()),
205
+ claims: optional(array(string())),
206
+ expiresAt: optional(string()),
207
+ });
208
+ /**
209
+ * How many obsolete token records a purge deleted.
210
+ *
211
+ * A record is obsolete once the token it describes has expired past the
212
+ * retention window: an expired token fails signature-and-expiry verification
213
+ * everywhere, so keeping its record buys neither revocation nor an answer.
214
+ *
215
+ * @example
216
+ * ```ts
217
+ * import type { PurgeServiceTokensResponse } from '@game-infra/api-schemas-core'
218
+ *
219
+ * const freed = (response: PurgeServiceTokensResponse) => response.purged ?? 0
220
+ * ```
221
+ */
222
+ export const PurgeServiceTokensResponseSchema = createSuccessResponseSchema({
223
+ purged: optional(number()),
224
+ /** Retention window applied, in seconds, so a caller can explain the count. */
225
+ retentionSeconds: optional(number()),
226
+ });
227
+ //# sourceMappingURL=serviceToken.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"serviceToken.js","sourceRoot":"","sources":["../src/serviceToken.ts"],"names":[],"mappings":"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"}