@apollo-deploy/tesseract 1.8.0 → 2.0.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/README.md +218 -110
- package/dist/adapters/csharp/index.d.ts +5 -8
- package/dist/adapters/csharp/index.d.ts.map +1 -1
- package/dist/adapters/csharp/index.js +314 -74
- package/dist/adapters/csharp/index.js.map +1 -1
- package/dist/adapters/documentation.d.ts +17 -0
- package/dist/adapters/documentation.d.ts.map +1 -0
- package/dist/adapters/documentation.js +268 -0
- package/dist/adapters/documentation.js.map +1 -0
- package/dist/adapters/go/index.d.ts +5 -8
- package/dist/adapters/go/index.d.ts.map +1 -1
- package/dist/adapters/go/index.js +197 -101
- package/dist/adapters/go/index.js.map +1 -1
- package/dist/adapters/kotlin/index.d.ts +5 -9
- package/dist/adapters/kotlin/index.d.ts.map +1 -1
- package/dist/adapters/kotlin/index.js +280 -212
- package/dist/adapters/kotlin/index.js.map +1 -1
- package/dist/adapters/php/index.d.ts +5 -15
- package/dist/adapters/php/index.d.ts.map +1 -1
- package/dist/adapters/php/index.js +362 -90
- package/dist/adapters/php/index.js.map +1 -1
- package/dist/adapters/python/index.d.ts +5 -8
- package/dist/adapters/python/index.d.ts.map +1 -1
- package/dist/adapters/python/index.js +240 -109
- package/dist/adapters/python/index.js.map +1 -1
- package/dist/adapters/ruby/index.d.ts +3 -3
- package/dist/adapters/ruby/index.d.ts.map +1 -1
- package/dist/adapters/ruby/index.js +235 -46
- package/dist/adapters/ruby/index.js.map +1 -1
- package/dist/adapters/rust/index.d.ts +5 -9
- package/dist/adapters/rust/index.d.ts.map +1 -1
- package/dist/adapters/rust/index.js +237 -169
- package/dist/adapters/rust/index.js.map +1 -1
- package/dist/adapters/shared.d.ts +7 -0
- package/dist/adapters/shared.d.ts.map +1 -0
- package/dist/adapters/shared.js +68 -0
- package/dist/adapters/shared.js.map +1 -0
- package/dist/adapters/type-utils.d.ts +13 -0
- package/dist/adapters/type-utils.d.ts.map +1 -0
- package/dist/adapters/type-utils.js +105 -0
- package/dist/adapters/type-utils.js.map +1 -0
- package/dist/adapters/types.d.ts.map +1 -1
- package/dist/adapters/typescript/emitter/emitSchema.d.ts +2 -2
- package/dist/adapters/typescript/emitter/emitSchema.js +39 -27
- package/dist/adapters/typescript/emitter/emitSchema.js.map +1 -1
- package/dist/adapters/typescript/emitter/emitTypeScriptModels.d.ts +2 -2
- package/dist/adapters/typescript/emitter/emitTypeScriptModels.js +15 -15
- package/dist/adapters/typescript/emitter/importCollector.d.ts +2 -4
- package/dist/adapters/typescript/emitter/importCollector.d.ts.map +1 -1
- package/dist/adapters/typescript/emitter/importCollector.js +40 -50
- package/dist/adapters/typescript/emitter/importCollector.js.map +1 -1
- package/dist/adapters/typescript/emitter/parsers.d.ts +1 -1
- package/dist/adapters/typescript/emitter/parsers.js +13 -13
- package/dist/adapters/typescript/emitter/typeHoister.d.ts +1 -1
- package/dist/adapters/typescript/emitter/typeHoister.d.ts.map +1 -1
- package/dist/adapters/typescript/emitter/typeHoister.js +12 -20
- package/dist/adapters/typescript/emitter/typeHoister.js.map +1 -1
- package/dist/adapters/typescript/index.d.ts +3 -3
- package/dist/adapters/typescript/index.d.ts.map +1 -1
- package/dist/adapters/typescript/index.js +148 -166
- package/dist/adapters/typescript/index.js.map +1 -1
- package/dist/adapters/typescript/shared.d.ts +2 -2
- package/dist/adapters/typescript/shared.js +12 -12
- package/dist/cli.js +50 -37
- package/dist/cli.js.map +1 -1
- package/dist/collector.d.ts +77 -3
- package/dist/collector.d.ts.map +1 -1
- package/dist/collector.js +198 -20
- package/dist/collector.js.map +1 -1
- package/dist/elysia.js +2 -2
- package/dist/elysia.js.map +1 -1
- package/dist/express.d.ts.map +1 -1
- package/dist/express.js.map +1 -1
- package/dist/fastify.d.ts +8 -9
- package/dist/fastify.d.ts.map +1 -1
- package/dist/fastify.js +105 -164
- package/dist/fastify.js.map +1 -1
- package/dist/helpers/handlebars.d.ts +7 -16
- package/dist/helpers/handlebars.d.ts.map +1 -1
- package/dist/helpers/handlebars.js +127 -177
- package/dist/helpers/handlebars.js.map +1 -1
- package/dist/hono.d.ts.map +1 -1
- package/dist/hono.js.map +1 -1
- package/dist/index.d.ts +14 -12
- package/dist/index.d.ts.map +1 -1
- package/dist/index.js +32 -30
- package/dist/index.js.map +1 -1
- package/dist/koa.d.ts.map +1 -1
- package/dist/koa.js.map +1 -1
- package/dist/nestjs.d.ts.map +1 -1
- package/dist/nestjs.js +41 -14
- package/dist/nestjs.js.map +1 -1
- package/dist/pipeline/enrich.d.ts +2 -13
- package/dist/pipeline/enrich.d.ts.map +1 -1
- package/dist/pipeline/enrich.js +157 -212
- package/dist/pipeline/enrich.js.map +1 -1
- package/dist/pipeline/intake.d.ts +3 -3
- package/dist/pipeline/intake.d.ts.map +1 -1
- package/dist/pipeline/intake.js +342 -238
- package/dist/pipeline/intake.js.map +1 -1
- package/dist/pipeline/write.d.ts +1 -14
- package/dist/pipeline/write.d.ts.map +1 -1
- package/dist/pipeline/write.js +73 -113
- package/dist/pipeline/write.js.map +1 -1
- package/dist/types/config.d.ts +14 -26
- package/dist/types/config.d.ts.map +1 -1
- package/dist/types/config.js +16 -12
- package/dist/types/config.js.map +1 -1
- package/dist/types/ir.d.ts +12 -8
- package/dist/types/ir.d.ts.map +1 -1
- package/dist/types/manifest.d.ts +10 -11
- package/dist/types/manifest.d.ts.map +1 -1
- package/dist/types/manifest.js +54 -14
- package/dist/types/manifest.js.map +1 -1
- package/dist/types/sdk-module.d.ts +2 -2
- package/dist/types/sdk-module.js +1 -1
- package/dist/utils/format.d.ts +1 -3
- package/dist/utils/format.d.ts.map +1 -1
- package/dist/utils/format.js +3 -10
- package/dist/utils/format.js.map +1 -1
- package/dist/utils/naming.d.ts.map +1 -1
- package/dist/utils/naming.js +174 -184
- package/dist/utils/naming.js.map +1 -1
- package/dist/utils/npm-token.d.ts +1 -17
- package/dist/utils/npm-token.d.ts.map +1 -1
- package/dist/utils/npm-token.js +27 -76
- package/dist/utils/npm-token.js.map +1 -1
- package/dist/utils/version.d.ts +14 -0
- package/dist/utils/version.d.ts.map +1 -0
- package/dist/utils/version.js +60 -0
- package/dist/utils/version.js.map +1 -0
- package/package.json +4 -3
- package/templates/csharp/client.hbs +26 -49
- package/templates/csharp/csproj.hbs +7 -0
- package/templates/csharp/domain.hbs +48 -130
- package/templates/csharp/errors.hbs +17 -25
- package/templates/csharp/readme.hbs +31 -44
- package/templates/csharp/transport.hbs +238 -136
- package/templates/csharp/types.hbs +30 -76
- package/templates/go/client.hbs +44 -109
- package/templates/go/domain.hbs +83 -25
- package/templates/go/go-mod.hbs +1 -4
- package/templates/go/readme.hbs +32 -29
- package/templates/go/transport.hbs +174 -173
- package/templates/go/types.hbs +17 -53
- package/templates/go/utils.hbs +3 -2
- package/templates/kotlin/build-gradle.hbs +1 -1
- package/templates/kotlin/client.hbs +18 -15
- package/templates/kotlin/domain.hbs +54 -51
- package/templates/kotlin/errors.hbs +1 -1
- package/templates/kotlin/readme.hbs +35 -137
- package/templates/kotlin/transport.hbs +140 -123
- package/templates/kotlin/types.hbs +30 -81
- package/templates/php/client.hbs +8 -46
- package/templates/php/composer.hbs +2 -1
- package/templates/php/domain.hbs +86 -117
- package/templates/php/errors.hbs +1 -1
- package/templates/php/readme.hbs +42 -49
- package/templates/php/transport.hbs +192 -145
- package/templates/php/types.hbs +63 -60
- package/templates/python/client.hbs +15 -2
- package/templates/python/domain.hbs +50 -108
- package/templates/python/pyproject.hbs +5 -0
- package/templates/python/readme.hbs +47 -30
- package/templates/python/resources-init.hbs +1 -1
- package/templates/python/transport.hbs +167 -53
- package/templates/python/types.hbs +22 -58
- package/templates/ruby/client.hbs +10 -6
- package/templates/ruby/domain.hbs +48 -67
- package/templates/ruby/errors.hbs +3 -3
- package/templates/ruby/gemspec.hbs +3 -10
- package/templates/ruby/index.hbs +3 -3
- package/templates/ruby/readme.hbs +33 -70
- package/templates/ruby/transport.hbs +129 -103
- package/templates/ruby/types.hbs +11 -16
- package/templates/ruby/version.hbs +1 -1
- package/templates/rust/cargo.hbs +2 -0
- package/templates/rust/client.hbs +10 -1
- package/templates/rust/domain.hbs +69 -52
- package/templates/rust/error.hbs +3 -1
- package/templates/rust/lib.hbs +4 -5
- package/templates/rust/readme.hbs +33 -46
- package/templates/rust/transport.hbs +170 -159
- package/templates/rust/types.hbs +34 -111
- package/templates/typescript/domain-class.hbs +14 -6
- package/templates/typescript/domain.hbs +13 -5
- package/templates/typescript/package-json.hbs +3 -1
- package/templates/typescript/readme.hbs +42 -42
- package/templates/typescript/transport.hbs +46 -8
- package/templates/typescript/types-errors.hbs +1 -1
- package/dist/adapters/typescript/model-emitter.d.ts +0 -13
- package/dist/adapters/typescript/model-emitter.d.ts.map +0 -1
- package/dist/adapters/typescript/model-emitter.js +0 -415
- package/dist/adapters/typescript/model-emitter.js.map +0 -1
package/templates/rust/types.hbs
CHANGED
|
@@ -1,142 +1,65 @@
|
|
|
1
1
|
use serde::{Deserialize, Serialize};
|
|
2
2
|
|
|
3
3
|
{{#each schemas}}
|
|
4
|
-
{{#if
|
|
5
|
-
|
|
6
|
-
|
|
7
|
-
{{else}}
|
|
8
|
-
{{#if description}}
|
|
9
|
-
/// {{description}}
|
|
10
|
-
{{/if}}
|
|
11
|
-
#[derive(Debug, Clone, Serialize, Deserialize)]
|
|
12
|
-
{{#if additionalPropertiesType}}
|
|
13
|
-
{{! Additional properties means we need to use a flattened map }}
|
|
14
|
-
#[serde(rename_all = "camelCase")]
|
|
15
|
-
pub struct {{name}} {
|
|
16
|
-
{{#each properties}}
|
|
17
|
-
{{#if description}}
|
|
18
|
-
/// {{description}}
|
|
19
|
-
{{/if}}
|
|
20
|
-
{{#if deprecated}}
|
|
21
|
-
#[deprecated]
|
|
22
|
-
{{/if}}
|
|
23
|
-
{{#if (and nullable (not required))}}
|
|
24
|
-
#[serde(skip_serializing_if = "Option::is_none")]
|
|
25
|
-
pub {{snakeCase name}}: Option<{{{rustType type}}}>,
|
|
26
|
-
{{else if nullable}}
|
|
27
|
-
#[serde(skip_serializing_if = "Option::is_none")]
|
|
28
|
-
pub {{snakeCase name}}: Option<{{{rustType type}}}>,
|
|
29
|
-
{{else if required}}
|
|
30
|
-
pub {{snakeCase name}}: {{{rustType type}}},
|
|
31
|
-
{{else}}
|
|
32
|
-
#[serde(skip_serializing_if = "Option::is_none")]
|
|
33
|
-
pub {{snakeCase name}}: Option<{{{rustType type}}}>,
|
|
34
|
-
{{/if}}
|
|
35
|
-
{{/each}}
|
|
36
|
-
}
|
|
37
|
-
{{else}}
|
|
38
|
-
#[serde(rename_all = "camelCase")]
|
|
39
|
-
pub struct {{name}} {
|
|
40
|
-
{{#each properties}}
|
|
41
|
-
{{#if description}}
|
|
42
|
-
/// {{description}}
|
|
43
|
-
{{/if}}
|
|
44
|
-
{{#if deprecated}}
|
|
45
|
-
#[deprecated]
|
|
46
|
-
{{/if}}
|
|
47
|
-
{{#if (and nullable (not required))}}
|
|
48
|
-
#[serde(skip_serializing_if = "Option::is_none")]
|
|
49
|
-
pub {{snakeCase name}}: Option<{{{rustType type}}}>,
|
|
50
|
-
{{else if nullable}}
|
|
51
|
-
#[serde(skip_serializing_if = "Option::is_none")]
|
|
52
|
-
pub {{snakeCase name}}: Option<{{{rustType type}}}>,
|
|
53
|
-
{{else if required}}
|
|
54
|
-
pub {{snakeCase name}}: {{{rustType type}}},
|
|
55
|
-
{{else}}
|
|
56
|
-
#[serde(skip_serializing_if = "Option::is_none")]
|
|
57
|
-
pub {{snakeCase name}}: Option<{{{rustType type}}}>,
|
|
58
|
-
{{/if}}
|
|
59
|
-
{{/each}}
|
|
60
|
-
}
|
|
61
|
-
{{/if}}
|
|
62
|
-
{{/if}}
|
|
63
|
-
{{/if}}
|
|
4
|
+
{{#if external}}
|
|
5
|
+
/// External schema placeholder. Configure a language-specific package mapping to replace it.
|
|
6
|
+
pub type {{name}} = serde_json::Value;
|
|
64
7
|
|
|
65
|
-
{{
|
|
8
|
+
{{else if isEnum}}
|
|
9
|
+
{{#if stringEnum}}
|
|
66
10
|
{{#if description}}
|
|
67
11
|
/// {{description}}
|
|
68
12
|
{{/if}}
|
|
69
13
|
#[derive(Debug, Clone, Serialize, Deserialize, PartialEq, Eq)]
|
|
70
|
-
{{#if enumValues}}
|
|
71
|
-
#[serde(rename_all = "camelCase")]
|
|
72
|
-
{{/if}}
|
|
73
14
|
pub enum {{name}} {
|
|
74
|
-
|
|
75
|
-
#[serde(rename = "{{
|
|
76
|
-
|
|
77
|
-
{{/each}}
|
|
15
|
+
{{#each enumValues}}
|
|
16
|
+
#[serde(rename = "{{value}}")] {{name}},
|
|
17
|
+
{{/each}}
|
|
78
18
|
}
|
|
19
|
+
{{else}}
|
|
20
|
+
pub type {{name}} = f64;
|
|
79
21
|
{{/if}}
|
|
80
22
|
|
|
81
|
-
{{
|
|
23
|
+
{{else if isUnionType}}
|
|
82
24
|
{{#if description}}
|
|
83
25
|
/// {{description}}
|
|
84
26
|
{{/if}}
|
|
85
|
-
{{#if properties.length}}
|
|
86
|
-
{{! Type alias with shape — emit as struct }}
|
|
87
27
|
#[derive(Debug, Clone, Serialize, Deserialize)]
|
|
88
|
-
#[serde(
|
|
89
|
-
pub struct {{name}}
|
|
90
|
-
{{#each properties}}
|
|
91
|
-
{{#if description}}
|
|
92
|
-
/// {{description}}
|
|
93
|
-
{{/if}}
|
|
94
|
-
{{#if required}}
|
|
95
|
-
pub {{snakeCase name}}: {{{rustType type}}},
|
|
96
|
-
{{else}}
|
|
97
|
-
#[serde(skip_serializing_if = "Option::is_none")]
|
|
98
|
-
pub {{snakeCase name}}: Option<{{{rustType type}}}>,
|
|
99
|
-
{{/if}}
|
|
100
|
-
{{/each}}
|
|
101
|
-
}
|
|
102
|
-
{{else}}
|
|
103
|
-
{{! Simple type alias — skip, referenced by name }}
|
|
104
|
-
// {{name}} is a type alias — referenced inline.
|
|
105
|
-
{{/if}}
|
|
106
|
-
{{/if}}
|
|
28
|
+
#[serde(transparent)]
|
|
29
|
+
pub struct {{name}}(pub serde_json::Value);
|
|
107
30
|
|
|
108
|
-
{{
|
|
31
|
+
{{else if isIntersectionType}}
|
|
109
32
|
{{#if description}}
|
|
110
33
|
/// {{description}}
|
|
111
34
|
{{/if}}
|
|
112
|
-
|
|
113
|
-
|
|
114
|
-
|
|
115
|
-
|
|
116
|
-
|
|
117
|
-
|
|
118
|
-
|
|
119
|
-
{{/each}}
|
|
120
|
-
}
|
|
121
|
-
{{/if}}
|
|
35
|
+
#[derive(Debug, Clone, Serialize, Deserialize, Default)]
|
|
36
|
+
#[serde(transparent)]
|
|
37
|
+
pub struct {{name}}(pub std::collections::HashMap<String, serde_json::Value>);
|
|
38
|
+
|
|
39
|
+
{{else if isTypeAlias}}
|
|
40
|
+
{{#if description}}
|
|
41
|
+
/// {{description}}
|
|
122
42
|
{{/if}}
|
|
43
|
+
pub type {{name}} = {{{aliasType}}};
|
|
123
44
|
|
|
124
|
-
{{
|
|
45
|
+
{{else}}
|
|
125
46
|
{{#if description}}
|
|
126
47
|
/// {{description}}
|
|
127
48
|
{{/if}}
|
|
128
|
-
{{#if intersectionMembers.length}}
|
|
129
|
-
{{! Intersection type — flatten into a struct combining all members }}
|
|
130
49
|
#[derive(Debug, Clone, Serialize, Deserialize)]
|
|
131
|
-
#[serde(rename_all = "camelCase")]
|
|
132
50
|
pub struct {{name}} {
|
|
133
|
-
|
|
134
|
-
|
|
135
|
-
{{
|
|
136
|
-
|
|
137
|
-
|
|
138
|
-
}
|
|
51
|
+
{{#each properties}}
|
|
52
|
+
{{#if description}}
|
|
53
|
+
/// {{description}}
|
|
54
|
+
{{/if}}
|
|
55
|
+
#[serde(rename = "{{name}}"{{#if optional}}, skip_serializing_if = "Option::is_none"{{/if}})]
|
|
56
|
+
pub {{fieldName}}: {{targetType}},
|
|
57
|
+
{{/each}}
|
|
58
|
+
{{#if additionalType}}
|
|
59
|
+
#[serde(flatten)]
|
|
60
|
+
pub additional_properties: std::collections::HashMap<String, {{additionalType}}>,
|
|
139
61
|
{{/if}}
|
|
62
|
+
}
|
|
140
63
|
{{/if}}
|
|
141
64
|
|
|
142
65
|
{{/each}}
|
|
@@ -70,10 +70,12 @@ export class {{interfaceName}} {
|
|
|
70
70
|
}
|
|
71
71
|
}
|
|
72
72
|
{{/if}}
|
|
73
|
-
{{#if (or (hasRequestBody this) (needsRequestHeaders this))}}
|
|
73
|
+
{{#if (or (hasRequestBody this) (needsRequestHeaders this) (sendsEmptyBody this))}}
|
|
74
74
|
const sseHeaders: Record<string, string> = {};
|
|
75
75
|
{{#if (hasRequestBody this)}}
|
|
76
76
|
sseHeaders['Content-Type'] = '{{requestBody.contentType}}';
|
|
77
|
+
{{else if (sendsEmptyBody this)}}
|
|
78
|
+
sseHeaders['Content-Type'] = 'application/json';
|
|
77
79
|
{{/if}}
|
|
78
80
|
{{#if (and headerParams.length headerType)}}
|
|
79
81
|
if (headerOptions) {
|
|
@@ -98,14 +100,16 @@ export class {{interfaceName}} {
|
|
|
98
100
|
}
|
|
99
101
|
{{/if}}
|
|
100
102
|
{{/if}}
|
|
101
|
-
return createSSEStream<{{#if sseReturnType}}{{sseReturnType}}{{else}}{{{sseEventType this}}}{{/if}}>(
|
|
103
|
+
return createSSEStream<{{#if sseReturnType}}{{sseReturnType}}{{else}}SSEEvent<{{{sseEventType this}}}>{{/if}}>(
|
|
102
104
|
sseUrl.toString(),
|
|
103
105
|
{
|
|
104
106
|
method: '{{httpMethod}}',
|
|
105
107
|
{{#if (hasRequestBody this)}}
|
|
106
108
|
body: JSON.stringify(input),
|
|
109
|
+
{{else if (sendsEmptyBody this)}}
|
|
110
|
+
body: '{}',
|
|
107
111
|
{{/if}}
|
|
108
|
-
{{#if (or (hasRequestBody this) (needsRequestHeaders this))}}
|
|
112
|
+
{{#if (or (hasRequestBody this) (needsRequestHeaders this) (sendsEmptyBody this))}}
|
|
109
113
|
headers: Object.keys(sseHeaders).length > 0 ? sseHeaders : undefined,
|
|
110
114
|
{{/if}}
|
|
111
115
|
},
|
|
@@ -133,9 +137,11 @@ export class {{interfaceName}} {
|
|
|
133
137
|
{{else if queryType}}
|
|
134
138
|
const params = query;
|
|
135
139
|
{{/if}}
|
|
136
|
-
{{#if (needsRequestHeaders this)}}
|
|
140
|
+
{{#if (or (needsRequestHeaders this) (sendsEmptyBody this))}}
|
|
137
141
|
const requestHeaders: Record<string, string> = {};
|
|
138
|
-
{{#if (
|
|
142
|
+
{{#if (sendsEmptyBody this)}}
|
|
143
|
+
requestHeaders['Content-Type'] = 'application/json';
|
|
144
|
+
{{else if (and (hasRequestBody this) (and (neq requestBody.contentType "application/json") (neq requestBody.contentType "multipart/form-data")))}}
|
|
139
145
|
requestHeaders['Content-Type'] = '{{requestBody.contentType}}';
|
|
140
146
|
{{/if}}
|
|
141
147
|
{{#if (and headerParams.length headerType)}}
|
|
@@ -167,11 +173,13 @@ export class {{interfaceName}} {
|
|
|
167
173
|
url: `{{path}}`,
|
|
168
174
|
{{#if (hasRequestBody this)}}
|
|
169
175
|
data: input,
|
|
176
|
+
{{else if (sendsEmptyBody this)}}
|
|
177
|
+
data: {},
|
|
170
178
|
{{/if}}
|
|
171
179
|
{{#if (or (hasQueryParams this) queryType)}}
|
|
172
180
|
params,
|
|
173
181
|
{{/if}}
|
|
174
|
-
{{#if (needsRequestHeaders this)}}
|
|
182
|
+
{{#if (or (needsRequestHeaders this) (sendsEmptyBody this))}}
|
|
175
183
|
headers: Object.keys(requestHeaders).length > 0 ? requestHeaders : undefined,
|
|
176
184
|
{{/if}}
|
|
177
185
|
},
|
|
@@ -84,10 +84,12 @@ export function {{factoryName}}(transport: SDKTransport): {{interfaceName}} {
|
|
|
84
84
|
}
|
|
85
85
|
}
|
|
86
86
|
{{/if}}
|
|
87
|
-
{{#if (or (hasRequestBody this) (needsRequestHeaders this))}}
|
|
87
|
+
{{#if (or (hasRequestBody this) (needsRequestHeaders this) (sendsEmptyBody this))}}
|
|
88
88
|
const sseHeaders: Record<string, string> = {};
|
|
89
89
|
{{#if (hasRequestBody this)}}
|
|
90
90
|
sseHeaders['Content-Type'] = '{{requestBody.contentType}}';
|
|
91
|
+
{{else if (sendsEmptyBody this)}}
|
|
92
|
+
sseHeaders['Content-Type'] = 'application/json';
|
|
91
93
|
{{/if}}
|
|
92
94
|
{{#if (and headerParams.length headerType)}}
|
|
93
95
|
if (headerOptions) {
|
|
@@ -118,8 +120,10 @@ export function {{factoryName}}(transport: SDKTransport): {{interfaceName}} {
|
|
|
118
120
|
method: '{{httpMethod}}',
|
|
119
121
|
{{#if (hasRequestBody this)}}
|
|
120
122
|
body: JSON.stringify(input),
|
|
123
|
+
{{else if (sendsEmptyBody this)}}
|
|
124
|
+
body: '{}',
|
|
121
125
|
{{/if}}
|
|
122
|
-
{{#if (or (hasRequestBody this) (needsRequestHeaders this))}}
|
|
126
|
+
{{#if (or (hasRequestBody this) (needsRequestHeaders this) (sendsEmptyBody this))}}
|
|
123
127
|
headers: Object.keys(sseHeaders).length > 0 ? sseHeaders : undefined,
|
|
124
128
|
{{/if}}
|
|
125
129
|
},
|
|
@@ -142,9 +146,11 @@ export function {{factoryName}}(transport: SDKTransport): {{interfaceName}} {
|
|
|
142
146
|
{{else if queryType}}
|
|
143
147
|
const params = query;
|
|
144
148
|
{{/if}}
|
|
145
|
-
{{#if (needsRequestHeaders this)}}
|
|
149
|
+
{{#if (or (needsRequestHeaders this) (sendsEmptyBody this))}}
|
|
146
150
|
const requestHeaders: Record<string, string> = {};
|
|
147
|
-
{{#if (
|
|
151
|
+
{{#if (sendsEmptyBody this)}}
|
|
152
|
+
requestHeaders['Content-Type'] = 'application/json';
|
|
153
|
+
{{else if (and (hasRequestBody this) (and (neq requestBody.contentType "application/json") (neq requestBody.contentType "multipart/form-data")))}}
|
|
148
154
|
requestHeaders['Content-Type'] = '{{requestBody.contentType}}';
|
|
149
155
|
{{/if}}
|
|
150
156
|
{{#if (and headerParams.length headerType)}}
|
|
@@ -176,11 +182,13 @@ export function {{factoryName}}(transport: SDKTransport): {{interfaceName}} {
|
|
|
176
182
|
url: `{{path}}`,
|
|
177
183
|
{{#if (hasRequestBody this)}}
|
|
178
184
|
data: input,
|
|
185
|
+
{{else if (sendsEmptyBody this)}}
|
|
186
|
+
data: {},
|
|
179
187
|
{{/if}}
|
|
180
188
|
{{#if (or (hasQueryParams this) queryType)}}
|
|
181
189
|
params,
|
|
182
190
|
{{/if}}
|
|
183
|
-
{{#if (needsRequestHeaders this)}}
|
|
191
|
+
{{#if (or (needsRequestHeaders this) (sendsEmptyBody this))}}
|
|
184
192
|
headers: Object.keys(requestHeaders).length > 0 ? requestHeaders : undefined,
|
|
185
193
|
{{/if}}
|
|
186
194
|
},
|
|
@@ -1,10 +1,8 @@
|
|
|
1
1
|
# {{title}} SDK
|
|
2
2
|
|
|
3
|
-
{{#if description}}
|
|
4
|
-
{{description}}
|
|
3
|
+
{{#if description}}{{description}}{{else}}TypeScript client for the {{title}} API.{{/if}}
|
|
5
4
|
|
|
6
|
-
|
|
7
|
-
> This SDK was automatically generated by [Tesseract](https://www.npmjs.com/package/@apollo-deploy/tesseract).
|
|
5
|
+
> Generated by [Tesseract](https://www.npmjs.com/package/@apollo-deploy/tesseract). Generated source files should not be edited manually.
|
|
8
6
|
|
|
9
7
|
## Installation
|
|
10
8
|
|
|
@@ -12,7 +10,7 @@
|
|
|
12
10
|
npm install {{packageName}}
|
|
13
11
|
```
|
|
14
12
|
|
|
15
|
-
## Quick
|
|
13
|
+
## Quick start
|
|
16
14
|
|
|
17
15
|
```typescript
|
|
18
16
|
import { create{{clientName}}Client } from '{{packageName}}';
|
|
@@ -20,66 +18,68 @@ import { create{{clientName}}Client } from '{{packageName}}';
|
|
|
20
18
|
const client = create{{clientName}}Client({
|
|
21
19
|
baseUrl: '{{baseUrl}}',
|
|
22
20
|
{{#each securitySchemes}}
|
|
23
|
-
{{configKey}}:
|
|
21
|
+
{{configKey}}: process.env.{{upperCase (snakeCase configKey)}},
|
|
24
22
|
{{/each}}
|
|
23
|
+
timeoutMs: 15_000,
|
|
25
24
|
});
|
|
25
|
+
|
|
26
|
+
{{#if groups.length}}
|
|
27
|
+
// Domain clients are available directly on the client.
|
|
26
28
|
const api = client.{{groups.[0].name}};
|
|
29
|
+
{{/if}}
|
|
27
30
|
```
|
|
28
31
|
|
|
29
|
-
##
|
|
32
|
+
## Configuration and reliability
|
|
30
33
|
|
|
31
|
-
|
|
32
|
-
import { create{{clientName}}Client } from '{{packageName}}';
|
|
34
|
+
The generated transport supports:
|
|
33
35
|
|
|
34
|
-
|
|
36
|
+
- Bounded request timeouts and `AbortSignal` cancellation
|
|
37
|
+
- Exponential-backoff retries for transient failures
|
|
38
|
+
- `Retry-After` handling for rate limits
|
|
39
|
+
- Per-request headers, timeout, and retry overrides
|
|
40
|
+
- Structured `SDKError` values with HTTP status, error code, and request ID
|
|
41
|
+
- Request/response hooks and transport plugins for logging or telemetry
|
|
35
42
|
|
|
36
|
-
|
|
37
|
-
|
|
38
|
-
|
|
39
|
-
|
|
40
|
-
|
|
41
|
-
|
|
42
|
-
|
|
43
|
+
```typescript
|
|
44
|
+
const client = create{{clientName}}Client({
|
|
45
|
+
timeoutMs: 30_000,
|
|
46
|
+
defaultHeaders: { 'X-Application': 'my-service' },
|
|
47
|
+
retries: {
|
|
48
|
+
attempts: 3,
|
|
49
|
+
backoffMs: 400,
|
|
50
|
+
jitter: true,
|
|
43
51
|
},
|
|
44
|
-
);
|
|
52
|
+
});
|
|
45
53
|
```
|
|
46
54
|
|
|
47
|
-
|
|
48
|
-
|
|
49
|
-
{{#each groups}}
|
|
50
|
-
### {{interfaceName}}
|
|
55
|
+
Mutating requests are retried only when the request is considered idempotent, carries an idempotency key, or the retry policy explicitly allows it.
|
|
51
56
|
|
|
52
|
-
|
|
53
|
-
{{description}}
|
|
57
|
+
## Documentation
|
|
54
58
|
|
|
55
|
-
|
|
56
|
-
|
|
57
|
-
|--------|------|------|-------------|
|
|
58
|
-
{{#each operations}}
|
|
59
|
-
| `{{name}}` | {{httpMethod}} | `{{path}}` | {{#if description}}{{description}}{{else}}-{{/if}} |
|
|
60
|
-
{{/each}}
|
|
61
|
-
|
|
62
|
-
{{/each}}
|
|
63
|
-
## Types
|
|
59
|
+
- [Documentation index](./docs/README.md)
|
|
60
|
+
- [Generated types](./docs/types.md)
|
|
64
61
|
|
|
65
|
-
|
|
66
|
-
|
|
67
|
-
|
|
68
|
-
{{else}}
|
|
69
|
-
- `{{name}}`{{#if description}} — {{description}}{{/if}}
|
|
70
|
-
{{/if}}
|
|
62
|
+
| Domain | Description |
|
|
63
|
+
|---|---|
|
|
64
|
+
{{#each groups}}
|
|
65
|
+
| [{{interfaceName}}](./docs/domains/{{fileName}}.md) | {{#if description}}{{description}}{{else}}{{name}} operations{{/if}} |
|
|
71
66
|
{{/each}}
|
|
72
67
|
|
|
73
|
-
## Error
|
|
68
|
+
## Error handling
|
|
74
69
|
|
|
75
70
|
```typescript
|
|
76
71
|
import { SDKError } from '{{packageName}}';
|
|
77
72
|
|
|
78
73
|
try {
|
|
79
|
-
|
|
74
|
+
// await client.someDomain.someOperation();
|
|
80
75
|
} catch (error) {
|
|
81
76
|
if (error instanceof SDKError) {
|
|
82
|
-
console.error(
|
|
77
|
+
console.error(error.status, error.code, error.requestId);
|
|
83
78
|
}
|
|
79
|
+
throw error;
|
|
84
80
|
}
|
|
85
81
|
```
|
|
82
|
+
|
|
83
|
+
## License
|
|
84
|
+
|
|
85
|
+
MIT
|
|
@@ -59,8 +59,12 @@ function calculateBackoff(attempt: number, baseMs: number, useJitter: boolean, m
|
|
|
59
59
|
function parseRetryAfterMs(error: unknown): number | undefined {
|
|
60
60
|
if (!isAxiosError(error)) return undefined;
|
|
61
61
|
|
|
62
|
-
const
|
|
63
|
-
|
|
62
|
+
const header = error.response?.headers?.['retry-after'];
|
|
63
|
+
const rawRetryAfter = Array.isArray(header) ? header[0] : header;
|
|
64
|
+
if (
|
|
65
|
+
(typeof rawRetryAfter !== 'string' && typeof rawRetryAfter !== 'number') ||
|
|
66
|
+
String(rawRetryAfter).length === 0
|
|
67
|
+
) {
|
|
64
68
|
return undefined;
|
|
65
69
|
}
|
|
66
70
|
|
|
@@ -71,7 +75,7 @@ function parseRetryAfterMs(error: unknown): number | undefined {
|
|
|
71
75
|
}
|
|
72
76
|
|
|
73
77
|
// Try HTTP-date format
|
|
74
|
-
const absoluteTime = Date.parse(rawRetryAfter);
|
|
78
|
+
const absoluteTime = Date.parse(String(rawRetryAfter));
|
|
75
79
|
if (!Number.isNaN(absoluteTime)) {
|
|
76
80
|
return Math.max(absoluteTime - Date.now(), 0);
|
|
77
81
|
}
|
|
@@ -213,6 +217,11 @@ export interface TransportConfig {
|
|
|
213
217
|
* Default: ['POST', 'PUT', 'PATCH', 'DELETE']
|
|
214
218
|
*/
|
|
215
219
|
idempotentMethods?: string[];
|
|
220
|
+
/**
|
|
221
|
+
* HTTP methods eligible for automatic retries without an idempotency key.
|
|
222
|
+
* Default: ['GET', 'HEAD', 'OPTIONS', 'PUT', 'DELETE']
|
|
223
|
+
*/
|
|
224
|
+
retryMethods?: string[];
|
|
216
225
|
}
|
|
217
226
|
|
|
218
227
|
// ── Telemetry Meta Types ────────────────────────────
|
|
@@ -244,6 +253,7 @@ export interface ResolvedTransportConfig extends TransportConfig {
|
|
|
244
253
|
retries: RetryConfig;
|
|
245
254
|
plugins: SDKPlugin[];
|
|
246
255
|
idempotentMethods: string[];
|
|
256
|
+
retryMethods: string[];
|
|
247
257
|
}
|
|
248
258
|
|
|
249
259
|
/**
|
|
@@ -365,14 +375,16 @@ export function createTransport(config: TransportConfig): SDKTransport {
|
|
|
365
375
|
},
|
|
366
376
|
plugins: config.plugins ?? [],
|
|
367
377
|
idempotentMethods: config.idempotentMethods ?? ['POST', 'PUT', 'PATCH', 'DELETE'],
|
|
378
|
+
retryMethods: config.retryMethods ?? ['GET', 'HEAD', 'OPTIONS', 'PUT', 'DELETE'],
|
|
368
379
|
};
|
|
369
380
|
|
|
370
381
|
const instance = axios.create({
|
|
371
382
|
baseURL: resolvedConfig.baseUrl,
|
|
372
383
|
timeout: resolvedConfig.timeoutMs,
|
|
373
384
|
withCredentials: resolvedConfig.withCredentials ?? false,
|
|
385
|
+
// Content-Type is set per-request when a body is present (see domain methods).
|
|
386
|
+
// Avoid advertising application/json on GET/HEAD with no body.
|
|
374
387
|
headers: {
|
|
375
|
-
'Content-Type': 'application/json',
|
|
376
388
|
...(resolvedConfig.defaultHeaders ?? {}),
|
|
377
389
|
},
|
|
378
390
|
...resolvedConfig.axiosConfig,
|
|
@@ -483,6 +495,17 @@ export function createTransport(config: TransportConfig): SDKTransport {
|
|
|
483
495
|
|
|
484
496
|
// ── Request Execution ───────────────────────────────
|
|
485
497
|
|
|
498
|
+
function hasIdempotencyKey(headers: AxiosRequestConfig['headers']): boolean {
|
|
499
|
+
if (!headers) return false;
|
|
500
|
+
return Object.entries(headers as Record<string, unknown>).some(
|
|
501
|
+
([name, value]) =>
|
|
502
|
+
name.toLowerCase() === 'x-idempotency-key' &&
|
|
503
|
+
value !== undefined &&
|
|
504
|
+
value !== null &&
|
|
505
|
+
String(value).length > 0,
|
|
506
|
+
);
|
|
507
|
+
}
|
|
508
|
+
|
|
486
509
|
/**
|
|
487
510
|
* Execute an HTTP request with automatic retries and error mapping.
|
|
488
511
|
*/
|
|
@@ -545,9 +568,13 @@ export async function executeRequest<T>(
|
|
|
545
568
|
const duration = startTime === undefined ? 0 : Date.now() - startTime;
|
|
546
569
|
|
|
547
570
|
// Determine if we should retry
|
|
571
|
+
const method = (effectiveConfig.method ?? 'GET').toUpperCase();
|
|
572
|
+
const methodCanRetry =
|
|
573
|
+
transport.config.retryMethods.includes(method) ||
|
|
574
|
+
hasIdempotencyKey(effectiveConfig.headers);
|
|
548
575
|
const shouldRetry = retries.shouldRetry
|
|
549
576
|
? retries.shouldRetry(sdkError, attempt)
|
|
550
|
-
: sdkError.isRetryable();
|
|
577
|
+
: methodCanRetry && sdkError.isRetryable();
|
|
551
578
|
|
|
552
579
|
const willRetry = attempt < maxAttempts && shouldRetry;
|
|
553
580
|
|
|
@@ -578,7 +605,7 @@ export async function executeRequest<T>(
|
|
|
578
605
|
let delayMs: number;
|
|
579
606
|
|
|
580
607
|
if (sdkError.status === 429 && retryAfterMs !== undefined) {
|
|
581
|
-
delayMs = retryAfterMs;
|
|
608
|
+
delayMs = Math.min(retryAfterMs, maxBackoff);
|
|
582
609
|
} else {
|
|
583
610
|
delayMs = calculateBackoff(attempt, retries.backoffMs, retries.jitter, maxBackoff);
|
|
584
611
|
}
|
|
@@ -648,15 +675,26 @@ function mapAxiosError(error: unknown): SDKError {
|
|
|
648
675
|
|
|
649
676
|
const status = error.response.status;
|
|
650
677
|
const data = error.response.data as any;
|
|
678
|
+
const headerRequestId =
|
|
679
|
+
error.response.headers?.['x-request-id'] ??
|
|
680
|
+
error.response.headers?.['request-id'];
|
|
681
|
+
const requestId = Array.isArray(headerRequestId)
|
|
682
|
+
? headerRequestId[0]
|
|
683
|
+
: typeof headerRequestId === 'string'
|
|
684
|
+
? headerRequestId
|
|
685
|
+
: undefined;
|
|
651
686
|
|
|
652
687
|
if (data && typeof data === 'object' && typeof data.error === 'string' && typeof data.message === 'string') {
|
|
653
|
-
return new SDKError(
|
|
688
|
+
return new SDKError(
|
|
689
|
+
{ ...data, request_id: data.request_id ?? requestId } as ApiErrorEnvelope,
|
|
690
|
+
status,
|
|
691
|
+
);
|
|
654
692
|
}
|
|
655
693
|
|
|
656
694
|
return new SDKError(
|
|
657
695
|
data?.message || error.message || resolveMessage(status),
|
|
658
696
|
status,
|
|
659
697
|
data?.error || resolveErrorCode(status),
|
|
660
|
-
data?.request_id,
|
|
698
|
+
data?.request_id ?? requestId,
|
|
661
699
|
);
|
|
662
700
|
}
|
|
@@ -167,7 +167,7 @@ export class SDKError extends Error {
|
|
|
167
167
|
|
|
168
168
|
/** Check if this error is retryable */
|
|
169
169
|
isRetryable(): boolean {
|
|
170
|
-
return this.code === 'network_error' || this.code === 'gateway_timeout' || this.status === 429 || this.status >= 500;
|
|
170
|
+
return this.code === 'network_error' || this.code === 'gateway_timeout' || this.status === 408 || this.status === 425 || this.status === 429 || this.status >= 500;
|
|
171
171
|
}
|
|
172
172
|
|
|
173
173
|
/** Convert to a plain object for logging/serialization */
|
|
@@ -1,13 +0,0 @@
|
|
|
1
|
-
/**
|
|
2
|
-
* TypeScript model emitter (ts-morph based).
|
|
3
|
-
*
|
|
4
|
-
* Emits schema definitions as TypeScript interfaces, type aliases,
|
|
5
|
-
* and enums using ts-morph AST construction.
|
|
6
|
-
*/
|
|
7
|
-
import type { EnrichedSDKIR } from '../../types/ir.js';
|
|
8
|
-
import type { EmittedFile } from '../../pipeline/write.js';
|
|
9
|
-
export declare function emitTypeScriptModels(enriched: EnrichedSDKIR, outputDir: string): {
|
|
10
|
-
files: EmittedFile[];
|
|
11
|
-
domainTypeFiles: string[];
|
|
12
|
-
};
|
|
13
|
-
//# sourceMappingURL=model-emitter.d.ts.map
|
|
@@ -1 +0,0 @@
|
|
|
1
|
-
{"version":3,"file":"model-emitter.d.ts","sourceRoot":"","sources":["../../../src/adapters/typescript/model-emitter.ts"],"names":[],"mappings":"AAAA;;;;;GAKG;AASH,OAAO,KAAK,EAAE,aAAa,EAAoC,MAAM,mBAAmB,CAAC;AACzF,OAAO,KAAK,EAAE,WAAW,EAAE,MAAM,yBAAyB,CAAC;AAE3D,wBAAgB,oBAAoB,CAClC,QAAQ,EAAE,aAAa,EACvB,SAAS,EAAE,MAAM,GAChB;IAAE,KAAK,EAAE,WAAW,EAAE,CAAC;IAAC,eAAe,EAAE,MAAM,EAAE,CAAA;CAAE,CAmErD"}
|