@stacksjs/types 0.72.57 → 0.72.60
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 +1 -1
- package/dist/request.d.ts +61 -6
- package/package.json +3 -3
package/dist/index.js
CHANGED
|
@@ -1,2 +1,2 @@
|
|
|
1
1
|
// @bun
|
|
2
|
-
function
|
|
2
|
+
function a(e){return typeof e==="object"&&e!==null&&"id"in e&&"userId"in e&&"clientId"in e&&"scopes"in e}function c(e){return a(e)&&"abilities"in e}function d(e){return typeof e==="object"&&e!==null&&"id"in e&&"name"in e&&"secret"in e&&"redirect"in e}var i;((t)=>{t.Second="* * * * * *";t.FiveSeconds="*/5 * * * * *";t.TenSeconds="*/10 * * * * *";t.ThirtySeconds="*/30 * * * * *";t.Minute="* * * * *";t.TwoMinutes="*/2 * * * *";t.FiveMinutes="*/5 * * * *";t.TenMinutes="*/10 * * * *";t.FifteenMinutes="*/15 * * * *";t.ThirtyMinutes="*/30 * * * *";t.Hour="0 * * * *";t.HalfHour="0,30 * * * *";t.Day="0 0 * * *";t.Week="0 0 * * 0";t.Weekday="0 0 * * 1-5";t.Weekend="0 0 * * 0,6";t.Month="0 0 1 * *";t.Year="0 0 1 1 *"})(i||={});var s;((r)=>{r.Bluesky="bluesky";r.Discord="discord";r.Facebook="facebook";r.GitHub="github";r.Instagram="instagram";r.LinkedIn="linkedin";r.Mastodon="mastodon";r.Slack="slack";r.Twitter="twitter";r.YouTube="youtube"})(s||={});var l;((n)=>{n[n.Success=0]="Success";n[n.FatalError=1]="FatalError";n[n.InvalidArgument=9]="InvalidArgument"})(l||={});import{toString as p}from"@stacksjs/strings";function y(e){if(e===null)return"null";let o=p(e).slice(8,-1).toLowerCase();return typeof e==="object"||typeof e==="function"?o:typeof e}function h(e){return e}function T(e){return e}var C={development:{default:"sync",connections:{sync:{driver:"sync"}},failed:{driver:"database",table:"failed_jobs"}},production:{default:"redis",connections:{redis:{driver:"redis",prefix:"stacks:queue",concurrency:5,distributedLock:!0,metrics:{enabled:!0},defaultDeadLetterOptions:{enabled:!0,maxRetries:3}}},failed:{driver:"redis",prefix:"stacks:failed"},worker:{concurrency:5,shutdownTimeout:30000}},highPerformance:{default:"redis",connections:{redis:{driver:"redis",prefix:"stacks:queue",concurrency:20,distributedLock:!0,metrics:{enabled:!0,collectInterval:5000},horizontalScaling:{enabled:!0,maxWorkersPerInstance:20,jobsPerWorker:50},defaultDeadLetterOptions:{enabled:!0,maxRetries:5}}},failed:{driver:"redis",prefix:"stacks:failed"},worker:{concurrency:20,shutdownTimeout:60000}},database:{default:"database",connections:{database:{driver:"database",table:"jobs",queue:"default",retryAfter:90}},failed:{driver:"database",table:"failed_jobs"}}};var M={server:{development:{enabled:!0,mode:"server",debug:!0,server:{host:"localhost",port:6001,scheme:"ws",driver:"bun",rateLimit:{enabled:!1},healthCheck:{enabled:!0,path:"/health"}},channels:{public:!0,private:!0,presence:!0}},production:{enabled:!0,mode:"server",debug:!1,server:{host:"0.0.0.0",port:6001,scheme:"wss",driver:"bun",redis:{enabled:!0,prefix:"stacks:realtime:"},rateLimit:{enabled:!0,maxConnectionsPerIp:100,maxMessagesPerSecond:50,maxPayloadSize:65536},loadManagement:{maxConnections:1e4,backpressureThreshold:1000,messageQueueSize:1e4,gracefulShutdownTimeout:30000},autoScaling:{min:2,max:10,targetCPU:70},healthCheck:{enabled:!0,path:"/health",interval:30},metrics:{enabled:!0,port:9090,path:"/metrics"}},channels:{public:!0,private:!0,presence:!0}},highPerformance:{enabled:!0,mode:"server",server:{driver:"bun",redis:{enabled:!0,cluster:!0},rateLimit:{enabled:!0,maxConnectionsPerIp:500,maxMessagesPerSecond:200,maxPayloadSize:131072},loadManagement:{maxConnections:1e5,backpressureThreshold:5000,messageQueueSize:50000,gracefulShutdownTimeout:60000},autoScaling:{min:4,max:50,targetCPU:60}}},chat:{enabled:!0,mode:"server",server:{driver:"bun",redis:{enabled:!0},rateLimit:{enabled:!0,maxConnectionsPerIp:10,maxMessagesPerSecond:20},loadManagement:{maxConnections:50000}},channels:{public:!0,private:!0,presence:{enabled:!0,maxMembersPerChannel:500,memberInfoTtl:60}}},gaming:{enabled:!0,mode:"server",server:{driver:"bun",redis:{enabled:!0,cluster:!0},rateLimit:{enabled:!0,maxConnectionsPerIp:50,maxMessagesPerSecond:100},loadManagement:{maxConnections:50000,backpressureThreshold:2000,messageQueueSize:20000},autoScaling:{min:2,max:20,targetCPU:50}},channels:{public:!0,private:!0,presence:!0}}},serverless:{development:{enabled:!0,mode:"serverless",debug:!0,serverless:{connectionTimeout:3600,idleTimeout:600,stageName:"dev",memorySize:256,timeout:30},channels:{public:!0,private:!0,presence:!0}},production:{enabled:!0,mode:"serverless",debug:!1,serverless:{connectionTimeout:3600,idleTimeout:600,stageName:"production",memorySize:512,timeout:30,provisionedConcurrency:2},channels:{public:!0,private:!0,presence:!0}},notifications:{enabled:!0,mode:"serverless",serverless:{connectionTimeout:7200,idleTimeout:1800,memorySize:256,timeout:15},channels:{public:!0,private:!0,presence:!1}}}};var S={calendar:{github:"stacksjs/calendar",package:"@stacksjs/calendar",description:"Calendar links, ICS generation, and an STX calendar component"},table:{github:"stacksjs/table",package:"@stacksjs/table",description:"Typed table drivers and an STX data table component"}};export{i as Every,l as ExitCode,C as QueuePresets,M as RealtimePresets,s as SocialLinkIcon,h as defineModel,T as defineModels,y as getTypeName,a as isAccessToken,d as isOAuthClient,c as isPersonalAccessToken,S as stackExtensionRegistry};
|
package/dist/request.d.ts
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
import { User } from '@stacksjs/orm';
|
|
2
2
|
import type { AuthToken } from '@stacksjs/types';
|
|
3
|
-
import type { Infer } from '@stacksjs/ts-validation';
|
|
3
|
+
import type { Infer, IsRequired } from '@stacksjs/ts-validation';
|
|
4
4
|
import type { UploadedFile } from '@stacksjs/storage';
|
|
5
5
|
declare interface RequestData {
|
|
6
6
|
[key: string]: any
|
|
@@ -89,9 +89,9 @@ export declare interface RequestInstance<TFields extends Record<string, any> = R
|
|
|
89
89
|
body?: ReadableStream<Uint8Array> | null
|
|
90
90
|
getUrl?: () => string
|
|
91
91
|
cookies?: RequestCookies
|
|
92
|
-
get<K extends keyof TFields & string>(key: K, defaultValue?: TFields[K]): TFields[K]
|
|
92
|
+
get<K extends keyof TInput<TFields, TParams> & string>(key: K, defaultValue?: TInput<TFields, TParams>[K]): TInput<TFields, TParams>[K]
|
|
93
93
|
get<T = any>(key: string, defaultValue?: T): T
|
|
94
|
-
input<K extends keyof TFields & string>(key: K, defaultValue?: TFields[K]): TFields[K]
|
|
94
|
+
input<K extends keyof TInput<TFields, TParams> & string>(key: K, defaultValue?: TInput<TFields, TParams>[K]): TInput<TFields, TParams>[K]
|
|
95
95
|
input<T = any>(key: string, defaultValue?: T): T
|
|
96
96
|
all: () => TFields
|
|
97
97
|
only<K extends keyof TFields & string>(keys: K[]): Pick<TFields, K>
|
|
@@ -245,9 +245,64 @@ export type ActionRequest<TFields extends Record<string, any> = Record<string, a
|
|
|
245
245
|
* type Body = InferValidations<typeof validations>
|
|
246
246
|
* // → { email: string, password: string, remember: boolean }
|
|
247
247
|
*/
|
|
248
|
-
|
|
249
|
-
|
|
250
|
-
|
|
248
|
+
/**
|
|
249
|
+
* Resolve a computed type to its final shape, for display.
|
|
250
|
+
*
|
|
251
|
+
* A named alias over a generic is shown by TypeScript as the alias: hovering
|
|
252
|
+
* `handle`'s parameter reported
|
|
253
|
+
*
|
|
254
|
+
* InferValidations<{ id: { rule: WithConditionals<NumberValidatorType> }; … }>
|
|
255
|
+
*
|
|
256
|
+
* which is the machinery, not the answer. It says nothing about what `id`
|
|
257
|
+
* actually is - the reader has to go and resolve it themselves, which is
|
|
258
|
+
* exactly the work the inference was supposed to save. Mapping the type through
|
|
259
|
+
* a fresh object literal forces it to be displayed evaluated, so the same hover
|
|
260
|
+
* reports `{ id: number, name: string }`.
|
|
261
|
+
*
|
|
262
|
+
* Display only: `Resolved<T>` and `T` are the same type.
|
|
263
|
+
*/
|
|
264
|
+
export type Resolved<T> = T extends infer U ? { [K in keyof U]: U[K] } : never;
|
|
265
|
+
/**
|
|
266
|
+
* The shape a set of validation rules describes.
|
|
267
|
+
*
|
|
268
|
+
* Optionality comes from the rules themselves: a field whose rule went through
|
|
269
|
+
* `.required()` is a required key, and everything else is optional. Before
|
|
270
|
+
* ts-validation 0.5.6 there was nothing to read - `required()` returned `this`
|
|
271
|
+
* and `isRequired` was a runtime boolean - so every field typed as present,
|
|
272
|
+
* including the ones a handler has to guard. `user.name` was `string` on a
|
|
273
|
+
* payload where it could be absent, which is the type saying something the
|
|
274
|
+
* runtime does not.
|
|
275
|
+
*
|
|
276
|
+
* Written as two mapped types rather than one with an optional modifier,
|
|
277
|
+
* because `?` cannot be applied conditionally per key.
|
|
278
|
+
*/
|
|
279
|
+
export type InferValidations<V extends Record<string, { rule: any }>> = Resolved<
|
|
280
|
+
& { [K in keyof V as IsRequired<V[K]['rule']> extends true ? K : never]: Infer<V[K]['rule']> }
|
|
281
|
+
& { [K in keyof V as IsRequired<V[K]['rule']> extends true ? never : K]?: Infer<V[K]['rule']> }
|
|
282
|
+
>;
|
|
283
|
+
/**
|
|
284
|
+
* What `get()` and `input()` can actually be asked for.
|
|
285
|
+
*
|
|
286
|
+
* They read one merged bag — `getAllInputFor` folds query, then body, then
|
|
287
|
+
* route params, in that order — so a path param is as reachable through
|
|
288
|
+
* `request.get('id')` as a validated body field is. The declarations were keyed
|
|
289
|
+
* on `TFields` alone, which meant `request.params.id` was `string` while
|
|
290
|
+
* `request.get('id')` right beside it was `any`: the same value, typed on one
|
|
291
|
+
* route and not the other.
|
|
292
|
+
*
|
|
293
|
+
* Params override fields where the names collide, because that is the order the
|
|
294
|
+
* runtime merges in.
|
|
295
|
+
*/
|
|
296
|
+
export type TInput<TFields extends Record<string, any>, TParams extends Record<string, string>,> = string extends keyof TParams
|
|
297
|
+
/*
|
|
298
|
+
* No path was declared, so `TParams` is the wide `Record<string, string>`
|
|
299
|
+
* default and its `keyof` is `string`. Merging that would `Omit` every key
|
|
300
|
+
* from `TFields` and leave the fields typed as strings - so an action with
|
|
301
|
+
* validations but no `path:` would have had its inferred body erased. When
|
|
302
|
+
* nothing is known about the params, the fields are the whole answer.
|
|
303
|
+
*/
|
|
304
|
+
? TFields
|
|
305
|
+
: Omit<TFields, keyof TParams> & TParams;
|
|
251
306
|
export type RequestValidationRules = Record<string, string | {
|
|
252
307
|
rule: { validate: (value: any) => any }
|
|
253
308
|
message?: string | Record<string, string>
|
package/package.json
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@stacksjs/types",
|
|
3
3
|
"type": "module",
|
|
4
|
-
"version": "0.72.
|
|
4
|
+
"version": "0.72.60",
|
|
5
5
|
"description": "The Stacks framework types.",
|
|
6
6
|
"author": "Chris Breuer",
|
|
7
7
|
"contributors": [
|
|
@@ -59,7 +59,7 @@
|
|
|
59
59
|
"@stacksjs/bunpress": "^0.2.8",
|
|
60
60
|
"@stacksjs/clapp": "^0.2.12",
|
|
61
61
|
"@stacksjs/stx": "^0.2.219",
|
|
62
|
-
"@stacksjs/ts-validation": "^0.5.
|
|
62
|
+
"@stacksjs/ts-validation": "^0.5.6",
|
|
63
63
|
"bun-query-builder": "^0.2.53"
|
|
64
64
|
},
|
|
65
65
|
"peerDependencies": {
|
|
@@ -71,7 +71,7 @@
|
|
|
71
71
|
}
|
|
72
72
|
},
|
|
73
73
|
"devDependencies": {
|
|
74
|
-
"@stacksjs/validation": "0.72.
|
|
74
|
+
"@stacksjs/validation": "0.72.60",
|
|
75
75
|
"better-dx": "^0.2.24",
|
|
76
76
|
"meilisearch": "^0.59.0"
|
|
77
77
|
},
|