@orpc/contract 0.0.0-next.b0f324e → 0.0.0-next.b11d127
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/README.md +26 -17
- package/dist/index.d.mts +342 -64
- package/dist/index.d.ts +342 -64
- package/dist/index.mjs +101 -31
- package/package.json +6 -7
package/dist/index.mjs
CHANGED
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import { mapEventIterator, ORPCError } from '@orpc/client';
|
|
1
|
+
import { isORPCErrorStatus, mapEventIterator, ORPCError } from '@orpc/client';
|
|
2
2
|
export { ORPCError } from '@orpc/client';
|
|
3
3
|
import { isAsyncIteratorObject } from '@orpc/shared';
|
|
4
4
|
|
|
@@ -18,13 +18,16 @@ function mergeMeta(meta1, meta2) {
|
|
|
18
18
|
}
|
|
19
19
|
|
|
20
20
|
class ContractProcedure {
|
|
21
|
+
/**
|
|
22
|
+
* This property holds the defined options for the contract procedure.
|
|
23
|
+
*/
|
|
21
24
|
"~orpc";
|
|
22
25
|
constructor(def) {
|
|
23
|
-
if (def.route?.successStatus && (def.route.successStatus
|
|
24
|
-
throw new Error("[ContractProcedure]
|
|
26
|
+
if (def.route?.successStatus && isORPCErrorStatus(def.route.successStatus)) {
|
|
27
|
+
throw new Error("[ContractProcedure] Invalid successStatus.");
|
|
25
28
|
}
|
|
26
|
-
if (Object.values(def.errorMap).some((val) => val && val.status && (val.status
|
|
27
|
-
throw new Error("[ContractProcedure]
|
|
29
|
+
if (Object.values(def.errorMap).some((val) => val && val.status && !isORPCErrorStatus(val.status))) {
|
|
30
|
+
throw new Error("[ContractProcedure] Invalid error status code.");
|
|
28
31
|
}
|
|
29
32
|
this["~orpc"] = def;
|
|
30
33
|
}
|
|
@@ -33,7 +36,7 @@ function isContractProcedure(item) {
|
|
|
33
36
|
if (item instanceof ContractProcedure) {
|
|
34
37
|
return true;
|
|
35
38
|
}
|
|
36
|
-
return (typeof item === "object" || typeof item === "function") && item !== null && "~orpc" in item && typeof item["~orpc"] === "object" && item["~orpc"] !== null && "
|
|
39
|
+
return (typeof item === "object" || typeof item === "function") && item !== null && "~orpc" in item && typeof item["~orpc"] === "object" && item["~orpc"] !== null && "errorMap" in item["~orpc"] && "route" in item["~orpc"] && "meta" in item["~orpc"];
|
|
37
40
|
}
|
|
38
41
|
|
|
39
42
|
function mergeRoute(a, b) {
|
|
@@ -60,31 +63,45 @@ function mergePrefix(a, b) {
|
|
|
60
63
|
function mergeTags(a, b) {
|
|
61
64
|
return a ? [...a, ...b] : b;
|
|
62
65
|
}
|
|
63
|
-
function
|
|
66
|
+
function enhanceRoute(route, options) {
|
|
64
67
|
let router = route;
|
|
65
68
|
if (options.prefix) {
|
|
66
69
|
router = prefixRoute(router, options.prefix);
|
|
67
70
|
}
|
|
68
|
-
if (options.tags) {
|
|
71
|
+
if (options.tags?.length) {
|
|
69
72
|
router = unshiftTagRoute(router, options.tags);
|
|
70
73
|
}
|
|
71
74
|
return router;
|
|
72
75
|
}
|
|
73
76
|
|
|
74
|
-
function
|
|
75
|
-
|
|
76
|
-
|
|
77
|
-
|
|
78
|
-
|
|
79
|
-
|
|
77
|
+
function getContractRouter(router, path) {
|
|
78
|
+
let current = router;
|
|
79
|
+
for (let i = 0; i < path.length; i++) {
|
|
80
|
+
const segment = path[i];
|
|
81
|
+
if (!current) {
|
|
82
|
+
return void 0;
|
|
83
|
+
}
|
|
84
|
+
if (isContractProcedure(current)) {
|
|
85
|
+
return void 0;
|
|
86
|
+
}
|
|
87
|
+
current = current[segment];
|
|
88
|
+
}
|
|
89
|
+
return current;
|
|
90
|
+
}
|
|
91
|
+
function enhanceContractRouter(router, options) {
|
|
92
|
+
if (isContractProcedure(router)) {
|
|
93
|
+
const enhanced2 = new ContractProcedure({
|
|
94
|
+
...router["~orpc"],
|
|
95
|
+
errorMap: mergeErrorMap(options.errorMap, router["~orpc"].errorMap),
|
|
96
|
+
route: enhanceRoute(router["~orpc"].route, options)
|
|
80
97
|
});
|
|
81
|
-
return
|
|
98
|
+
return enhanced2;
|
|
82
99
|
}
|
|
83
|
-
const
|
|
84
|
-
for (const key in
|
|
85
|
-
|
|
100
|
+
const enhanced = {};
|
|
101
|
+
for (const key in router) {
|
|
102
|
+
enhanced[key] = enhanceContractRouter(router[key], options);
|
|
86
103
|
}
|
|
87
|
-
return
|
|
104
|
+
return enhanced;
|
|
88
105
|
}
|
|
89
106
|
|
|
90
107
|
class ContractBuilder extends ContractProcedure {
|
|
@@ -94,7 +111,9 @@ class ContractBuilder extends ContractProcedure {
|
|
|
94
111
|
this["~orpc"].tags = def.tags;
|
|
95
112
|
}
|
|
96
113
|
/**
|
|
97
|
-
*
|
|
114
|
+
* Sets or overrides the initial meta.
|
|
115
|
+
*
|
|
116
|
+
* @see {@link https://orpc.unnoq.com/docs/metadata Metadata Docs}
|
|
98
117
|
*/
|
|
99
118
|
$meta(initialMeta) {
|
|
100
119
|
return new ContractBuilder({
|
|
@@ -103,7 +122,11 @@ class ContractBuilder extends ContractProcedure {
|
|
|
103
122
|
});
|
|
104
123
|
}
|
|
105
124
|
/**
|
|
106
|
-
*
|
|
125
|
+
* Sets or overrides the initial route.
|
|
126
|
+
* This option is typically relevant when integrating with OpenAPI.
|
|
127
|
+
*
|
|
128
|
+
* @see {@link https://orpc.unnoq.com/docs/openapi/routing OpenAPI Routing Docs}
|
|
129
|
+
* @see {@link https://orpc.unnoq.com/docs/openapi/input-output-structure OpenAPI Input/Output Structure Docs}
|
|
107
130
|
*/
|
|
108
131
|
$route(initialRoute) {
|
|
109
132
|
return new ContractBuilder({
|
|
@@ -111,56 +134,103 @@ class ContractBuilder extends ContractProcedure {
|
|
|
111
134
|
route: initialRoute
|
|
112
135
|
});
|
|
113
136
|
}
|
|
137
|
+
/**
|
|
138
|
+
* Adds type-safe custom errors to the contract.
|
|
139
|
+
* The provided errors are spared-merged with any existing errors in the contract.
|
|
140
|
+
*
|
|
141
|
+
* @see {@link https://orpc.unnoq.com/docs/error-handling#type%E2%80%90safe-error-handling Type-Safe Error Handling Docs}
|
|
142
|
+
*/
|
|
114
143
|
errors(errors) {
|
|
115
144
|
return new ContractBuilder({
|
|
116
145
|
...this["~orpc"],
|
|
117
146
|
errorMap: mergeErrorMap(this["~orpc"].errorMap, errors)
|
|
118
147
|
});
|
|
119
148
|
}
|
|
149
|
+
/**
|
|
150
|
+
* Sets or updates the metadata for the contract.
|
|
151
|
+
* The provided metadata is spared-merged with any existing metadata in the contract.
|
|
152
|
+
*
|
|
153
|
+
* @see {@link https://orpc.unnoq.com/docs/metadata Metadata Docs}
|
|
154
|
+
*/
|
|
120
155
|
meta(meta) {
|
|
121
156
|
return new ContractBuilder({
|
|
122
157
|
...this["~orpc"],
|
|
123
158
|
meta: mergeMeta(this["~orpc"].meta, meta)
|
|
124
159
|
});
|
|
125
160
|
}
|
|
161
|
+
/**
|
|
162
|
+
* Sets or updates the route definition for the contract.
|
|
163
|
+
* The provided route is spared-merged with any existing route in the contract.
|
|
164
|
+
* This option is typically relevant when integrating with OpenAPI.
|
|
165
|
+
*
|
|
166
|
+
* @see {@link https://orpc.unnoq.com/docs/openapi/routing OpenAPI Routing Docs}
|
|
167
|
+
* @see {@link https://orpc.unnoq.com/docs/openapi/input-output-structure OpenAPI Input/Output Structure Docs}
|
|
168
|
+
*/
|
|
126
169
|
route(route) {
|
|
127
170
|
return new ContractBuilder({
|
|
128
171
|
...this["~orpc"],
|
|
129
172
|
route: mergeRoute(this["~orpc"].route, route)
|
|
130
173
|
});
|
|
131
174
|
}
|
|
175
|
+
/**
|
|
176
|
+
* Defines the input validation schema for the contract.
|
|
177
|
+
*
|
|
178
|
+
* @see {@link https://orpc.unnoq.com/docs/procedure#input-output-validation Input Validation Docs}
|
|
179
|
+
*/
|
|
132
180
|
input(schema) {
|
|
133
181
|
return new ContractBuilder({
|
|
134
182
|
...this["~orpc"],
|
|
135
183
|
inputSchema: schema
|
|
136
184
|
});
|
|
137
185
|
}
|
|
186
|
+
/**
|
|
187
|
+
* Defines the output validation schema for the contract.
|
|
188
|
+
*
|
|
189
|
+
* @see {@link https://orpc.unnoq.com/docs/procedure#input-output-validation Output Validation Docs}
|
|
190
|
+
*/
|
|
138
191
|
output(schema) {
|
|
139
192
|
return new ContractBuilder({
|
|
140
193
|
...this["~orpc"],
|
|
141
194
|
outputSchema: schema
|
|
142
195
|
});
|
|
143
196
|
}
|
|
197
|
+
/**
|
|
198
|
+
* Prefixes all procedures in the contract router.
|
|
199
|
+
* The provided prefix is post-appended to any existing router prefix.
|
|
200
|
+
*
|
|
201
|
+
* @note This option does not affect procedures that do not define a path in their route definition.
|
|
202
|
+
*
|
|
203
|
+
* @see {@link https://orpc.unnoq.com/docs/openapi/routing#route-prefixes OpenAPI Route Prefixes Docs}
|
|
204
|
+
*/
|
|
144
205
|
prefix(prefix) {
|
|
145
206
|
return new ContractBuilder({
|
|
146
207
|
...this["~orpc"],
|
|
147
208
|
prefix: mergePrefix(this["~orpc"].prefix, prefix)
|
|
148
209
|
});
|
|
149
210
|
}
|
|
211
|
+
/**
|
|
212
|
+
* Adds tags to all procedures in the contract router.
|
|
213
|
+
* This helpful when you want to group procedures together in the OpenAPI specification.
|
|
214
|
+
*
|
|
215
|
+
* @see {@link https://orpc.unnoq.com/docs/openapi/openapi-specification#operation-metadata OpenAPI Operation Metadata Docs}
|
|
216
|
+
*/
|
|
150
217
|
tag(...tags) {
|
|
151
218
|
return new ContractBuilder({
|
|
152
219
|
...this["~orpc"],
|
|
153
220
|
tags: mergeTags(this["~orpc"].tags, tags)
|
|
154
221
|
});
|
|
155
222
|
}
|
|
223
|
+
/**
|
|
224
|
+
* Applies all of the previously defined options to the specified contract router.
|
|
225
|
+
*
|
|
226
|
+
* @see {@link https://orpc.unnoq.com/docs/router#extending-router Extending Router Docs}
|
|
227
|
+
*/
|
|
156
228
|
router(router) {
|
|
157
|
-
return
|
|
229
|
+
return enhanceContractRouter(router, this["~orpc"]);
|
|
158
230
|
}
|
|
159
231
|
}
|
|
160
232
|
const oc = new ContractBuilder({
|
|
161
233
|
errorMap: {},
|
|
162
|
-
inputSchema: void 0,
|
|
163
|
-
outputSchema: void 0,
|
|
164
234
|
route: {},
|
|
165
235
|
meta: {}
|
|
166
236
|
});
|
|
@@ -179,16 +249,16 @@ function fallbackContractConfig(key, value) {
|
|
|
179
249
|
return value;
|
|
180
250
|
}
|
|
181
251
|
|
|
182
|
-
const
|
|
252
|
+
const EVENT_ITERATOR_DETAILS_SYMBOL = Symbol("ORPC_EVENT_ITERATOR_DETAILS");
|
|
183
253
|
function eventIterator(yields, returns) {
|
|
184
254
|
return {
|
|
185
255
|
"~standard": {
|
|
186
|
-
[
|
|
256
|
+
[EVENT_ITERATOR_DETAILS_SYMBOL]: { yields, returns },
|
|
187
257
|
vendor: "orpc",
|
|
188
258
|
version: 1,
|
|
189
259
|
validate(iterator) {
|
|
190
260
|
if (!isAsyncIteratorObject(iterator)) {
|
|
191
|
-
return { issues: [{ message: "Expect event
|
|
261
|
+
return { issues: [{ message: "Expect event iterator", path: [] }] };
|
|
192
262
|
}
|
|
193
263
|
const mapped = mapEventIterator(iterator, {
|
|
194
264
|
async value(value, done) {
|
|
@@ -199,10 +269,10 @@ function eventIterator(yields, returns) {
|
|
|
199
269
|
const result = await schema["~standard"].validate(value);
|
|
200
270
|
if (result.issues) {
|
|
201
271
|
throw new ORPCError("EVENT_ITERATOR_VALIDATION_FAILED", {
|
|
202
|
-
message: "Event
|
|
272
|
+
message: "Event iterator validation failed",
|
|
203
273
|
cause: new ValidationError({
|
|
204
274
|
issues: result.issues,
|
|
205
|
-
message: "Event
|
|
275
|
+
message: "Event iterator validation failed"
|
|
206
276
|
})
|
|
207
277
|
});
|
|
208
278
|
}
|
|
@@ -219,7 +289,7 @@ function getEventIteratorSchemaDetails(schema) {
|
|
|
219
289
|
if (schema === void 0) {
|
|
220
290
|
return void 0;
|
|
221
291
|
}
|
|
222
|
-
return schema["~standard"][
|
|
292
|
+
return schema["~standard"][EVENT_ITERATOR_DETAILS_SYMBOL];
|
|
223
293
|
}
|
|
224
294
|
|
|
225
295
|
function type(...[map]) {
|
|
@@ -237,4 +307,4 @@ function type(...[map]) {
|
|
|
237
307
|
};
|
|
238
308
|
}
|
|
239
309
|
|
|
240
|
-
export { ContractBuilder, ContractProcedure, ValidationError,
|
|
310
|
+
export { ContractBuilder, ContractProcedure, ValidationError, enhanceContractRouter, enhanceRoute, eventIterator, fallbackContractConfig, getContractRouter, getEventIteratorSchemaDetails, isContractProcedure, mergeErrorMap, mergeMeta, mergePrefix, mergeRoute, mergeTags, oc, prefixRoute, type, unshiftTagRoute };
|
package/package.json
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@orpc/contract",
|
|
3
3
|
"type": "module",
|
|
4
|
-
"version": "0.0.0-next.
|
|
4
|
+
"version": "0.0.0-next.b11d127",
|
|
5
5
|
"license": "MIT",
|
|
6
6
|
"homepage": "https://orpc.unnoq.com",
|
|
7
7
|
"repository": {
|
|
@@ -25,14 +25,13 @@
|
|
|
25
25
|
],
|
|
26
26
|
"dependencies": {
|
|
27
27
|
"@standard-schema/spec": "^1.0.0",
|
|
28
|
-
"@orpc/shared": "0.0.0-next.
|
|
29
|
-
"@orpc/
|
|
30
|
-
"@orpc/client": "0.0.0-next.b0f324e"
|
|
28
|
+
"@orpc/shared": "0.0.0-next.b11d127",
|
|
29
|
+
"@orpc/client": "0.0.0-next.b11d127"
|
|
31
30
|
},
|
|
32
31
|
"devDependencies": {
|
|
33
|
-
"arktype": "2.
|
|
34
|
-
"valibot": "1.0.0
|
|
35
|
-
"zod": "^3.24.
|
|
32
|
+
"arktype": "2.1.20",
|
|
33
|
+
"valibot": "1.0.0",
|
|
34
|
+
"zod": "^3.24.2"
|
|
36
35
|
},
|
|
37
36
|
"scripts": {
|
|
38
37
|
"build": "unbuild",
|