@postman/sdk-config 0.0.4 → 0.1.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 +42 -17
- package/dist/index.cjs +2011 -181
- package/dist/index.cjs.map +1 -1
- package/dist/index.d.cts +3 -1
- package/dist/index.d.ts +3 -1
- package/dist/index.js +1974 -182
- package/dist/index.js.map +1 -1
- package/dist/sdk-config/index.cjs +2233 -0
- package/dist/sdk-config/index.cjs.map +1 -0
- package/dist/sdk-config/index.d.cts +3 -0
- package/dist/sdk-config/index.d.ts +3 -0
- package/dist/sdk-config/index.js +2192 -0
- package/dist/sdk-config/index.js.map +1 -0
- package/dist/sdk-config/v1/index.cjs +2233 -0
- package/dist/sdk-config/v1/index.cjs.map +1 -0
- package/dist/sdk-config/v1/index.d.cts +8644 -0
- package/dist/sdk-config/v1/index.d.ts +8644 -0
- package/dist/sdk-config/v1/index.js +2192 -0
- package/dist/sdk-config/v1/index.js.map +1 -0
- package/dist/sdk-config-ir/index.cjs +147 -18
- package/dist/sdk-config-ir/index.cjs.map +1 -1
- package/dist/sdk-config-ir/index.d.cts +2 -1
- package/dist/sdk-config-ir/index.d.ts +2 -1
- package/dist/sdk-config-ir/index.js +146 -19
- package/dist/sdk-config-ir/index.js.map +1 -1
- package/dist/sdk-config-ir/v1/index.cjs +147 -18
- package/dist/sdk-config-ir/v1/index.cjs.map +1 -1
- package/dist/sdk-config-ir/v1/index.d.cts +422 -400
- package/dist/sdk-config-ir/v1/index.d.ts +422 -400
- package/dist/sdk-config-ir/v1/index.js +146 -19
- package/dist/sdk-config-ir/v1/index.js.map +1 -1
- package/dist/typescript-ByDbin_v.d.cts +426 -0
- package/dist/typescript-ByDbin_v.d.ts +426 -0
- package/package.json +15 -2
- package/src/sdk-config/v1/README.md +135 -0
- package/src/sdk-config-ir/v1/README.md +44 -26
package/dist/index.js
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
import { z } from 'zod';
|
|
2
2
|
import semver from 'semver';
|
|
3
3
|
|
|
4
|
-
// src/sdk-config-
|
|
4
|
+
// src/sdk-config-domain/v1/api.ts
|
|
5
5
|
var nonEmptyStringSchema = z.string().min(1);
|
|
6
6
|
var exactSemverSchema = z.string().refine(
|
|
7
7
|
(value) => {
|
|
@@ -25,7 +25,7 @@ var jsonValueSchema = z.lazy(
|
|
|
25
25
|
);
|
|
26
26
|
var jsonObjectSchema = z.record(z.string(), jsonValueSchema);
|
|
27
27
|
|
|
28
|
-
// src/sdk-config-
|
|
28
|
+
// src/sdk-config-domain/v1/api.ts
|
|
29
29
|
var authVariableSchema = z.strictObject({
|
|
30
30
|
name: nonEmptyStringSchema.optional(),
|
|
31
31
|
environmentVariable: nonEmptyStringSchema.optional(),
|
|
@@ -175,8 +175,20 @@ var apiConfigSchema = z.strictObject({
|
|
|
175
175
|
environmentVariables: z.array(environmentVariableSchema).default([]),
|
|
176
176
|
defaultEnvironment: nonEmptyStringSchema.optional(),
|
|
177
177
|
auth: authConfigSchema.optional(),
|
|
178
|
-
headers: z.array(headerSchema).optional()
|
|
178
|
+
headers: z.array(headerSchema).optional(),
|
|
179
|
+
/**
|
|
180
|
+
* Selects the named `x-fern-audiences`.
|
|
181
|
+
*
|
|
182
|
+
* Absent means all audiences. A present empty array selects no tagged audience: untagged nodes
|
|
183
|
+
* remain included, while every audience-tagged node is excluded.
|
|
184
|
+
*/
|
|
185
|
+
audiences: z.array(nonEmptyStringSchema).optional()
|
|
179
186
|
});
|
|
187
|
+
|
|
188
|
+
// src/sdk-config/v1/api.ts
|
|
189
|
+
var sdkConfigV1AuthSchemeSchema = authSchemeSchema;
|
|
190
|
+
var sdkConfigV1AuthConfigSchema = authConfigSchema;
|
|
191
|
+
var sdkConfigV1ApiConfigSchema = apiConfigSchema;
|
|
180
192
|
var retryConfigSchema = z.strictObject({
|
|
181
193
|
enabled: z.boolean().default(true),
|
|
182
194
|
maxAttempts: z.number().int().min(1).default(3),
|
|
@@ -229,34 +241,89 @@ var clientConfigSchema = z.strictObject({
|
|
|
229
241
|
pathParameterStyle: parameterStyleSchema.optional(),
|
|
230
242
|
filePropertyStyle: parameterStyleSchema.optional(),
|
|
231
243
|
useDefaultRequestParameterValues: z.boolean().optional(),
|
|
244
|
+
respectOptionalRequestBody: z.boolean().optional(),
|
|
232
245
|
tokenRefresh: tokenRefreshConfigSchema.optional()
|
|
233
246
|
});
|
|
234
|
-
|
|
235
|
-
|
|
236
|
-
|
|
237
|
-
|
|
238
|
-
|
|
239
|
-
|
|
240
|
-
|
|
241
|
-
|
|
242
|
-
|
|
247
|
+
|
|
248
|
+
// src/sdk-config/v1/client.ts
|
|
249
|
+
var sdkConfigV1ClientConfigSchema = clientConfigSchema;
|
|
250
|
+
var goModulePathSchema = nonEmptyStringSchema.regex(
|
|
251
|
+
/^(?!.*(?:^|\/)\.{1,2}(?:\/|$))[A-Za-z0-9._~-]+(?:\/[A-Za-z0-9._~-]+)+$/,
|
|
252
|
+
"Go module path must be a slash-delimited path using letters, numbers, dots, dashes, underscores, or tildes"
|
|
253
|
+
);
|
|
254
|
+
var composerPackageNameSchema = nonEmptyStringSchema.regex(
|
|
255
|
+
/^[a-z0-9]([_.-]?[a-z0-9]+)*\/[a-z0-9](([_.]?|-{0,2})[a-z0-9]+)*$/,
|
|
256
|
+
'Composer package name must be a lowercase "vendor/package" name'
|
|
257
|
+
);
|
|
258
|
+
var authorSchema = z.strictObject({
|
|
259
|
+
name: nonEmptyStringSchema,
|
|
260
|
+
email: z.email().optional()
|
|
243
261
|
});
|
|
244
|
-
var
|
|
245
|
-
|
|
246
|
-
|
|
262
|
+
var developerSchema = z.strictObject({
|
|
263
|
+
name: nonEmptyStringSchema,
|
|
264
|
+
email: z.email().optional(),
|
|
265
|
+
organization: nonEmptyStringSchema.optional(),
|
|
266
|
+
organizationUrl: nonEmptyStringSchema.optional()
|
|
247
267
|
});
|
|
248
|
-
var
|
|
249
|
-
|
|
250
|
-
|
|
268
|
+
var licenseSchema = z.strictObject({
|
|
269
|
+
type: nonEmptyStringSchema,
|
|
270
|
+
name: nonEmptyStringSchema.optional(),
|
|
271
|
+
url: nonEmptyStringSchema.optional(),
|
|
272
|
+
path: nonEmptyStringSchema.optional()
|
|
251
273
|
});
|
|
252
|
-
var
|
|
253
|
-
|
|
254
|
-
|
|
274
|
+
var dependencySourceSchema = z.discriminatedUnion("type", [
|
|
275
|
+
z.strictObject({
|
|
276
|
+
type: z.literal("registry"),
|
|
277
|
+
registry: nonEmptyStringSchema.optional()
|
|
278
|
+
}),
|
|
279
|
+
z.strictObject({
|
|
280
|
+
type: z.literal("git"),
|
|
281
|
+
url: nonEmptyStringSchema,
|
|
282
|
+
ref: nonEmptyStringSchema.optional(),
|
|
283
|
+
subdirectory: nonEmptyStringSchema.optional()
|
|
284
|
+
}),
|
|
285
|
+
z.strictObject({
|
|
286
|
+
type: z.literal("path"),
|
|
287
|
+
path: nonEmptyStringSchema
|
|
288
|
+
})
|
|
255
289
|
]);
|
|
256
|
-
var
|
|
257
|
-
|
|
258
|
-
|
|
259
|
-
|
|
290
|
+
var dependencySchema = z.strictObject({
|
|
291
|
+
name: nonEmptyStringSchema,
|
|
292
|
+
version: nonEmptyStringSchema.optional(),
|
|
293
|
+
source: dependencySourceSchema.optional(),
|
|
294
|
+
packageName: nonEmptyStringSchema.optional(),
|
|
295
|
+
features: z.array(nonEmptyStringSchema).optional(),
|
|
296
|
+
extras: z.array(nonEmptyStringSchema).optional(),
|
|
297
|
+
optional: z.boolean().optional(),
|
|
298
|
+
defaultFeatures: z.boolean().optional(),
|
|
299
|
+
environmentMarker: nonEmptyStringSchema.optional()
|
|
300
|
+
}).refine(({ source, version }) => source !== void 0 || version !== void 0, {
|
|
301
|
+
message: "dependency must define a version or a source"
|
|
302
|
+
});
|
|
303
|
+
var projectUrlSchema = z.strictObject({
|
|
304
|
+
label: nonEmptyStringSchema,
|
|
305
|
+
url: nonEmptyStringSchema
|
|
306
|
+
});
|
|
307
|
+
var packageConfigSchema = z.strictObject({
|
|
308
|
+
packageName: nonEmptyStringSchema.optional(),
|
|
309
|
+
moduleName: nonEmptyStringSchema.optional(),
|
|
310
|
+
modulePath: goModulePathSchema.optional(),
|
|
311
|
+
namespace: nonEmptyStringSchema.optional(),
|
|
312
|
+
groupId: nonEmptyStringSchema.optional(),
|
|
313
|
+
artifactId: nonEmptyStringSchema.optional(),
|
|
314
|
+
description: z.string().optional(),
|
|
315
|
+
repository: nonEmptyStringSchema.optional(),
|
|
316
|
+
homepage: nonEmptyStringSchema.optional(),
|
|
317
|
+
documentationUrl: nonEmptyStringSchema.optional(),
|
|
318
|
+
authors: z.array(authorSchema).optional(),
|
|
319
|
+
developers: z.array(developerSchema).optional(),
|
|
320
|
+
license: licenseSchema.optional(),
|
|
321
|
+
keywords: z.array(nonEmptyStringSchema).optional(),
|
|
322
|
+
classifiers: z.array(nonEmptyStringSchema).optional(),
|
|
323
|
+
projectUrls: z.array(projectUrlSchema).optional(),
|
|
324
|
+
extraDependencies: z.array(dependencySchema).optional(),
|
|
325
|
+
extraDevDependencies: z.array(dependencySchema).optional(),
|
|
326
|
+
extraPeerDependencies: z.array(dependencySchema).optional()
|
|
260
327
|
});
|
|
261
328
|
var httpMethodSchema = z.enum([
|
|
262
329
|
"GET",
|
|
@@ -274,12 +341,17 @@ var readmeEndpointSchema = z.strictObject({
|
|
|
274
341
|
path: nonEmptyStringSchema,
|
|
275
342
|
stream: z.boolean().optional()
|
|
276
343
|
});
|
|
344
|
+
var readmeCustomSectionSchema = z.strictObject({
|
|
345
|
+
title: nonEmptyStringSchema,
|
|
346
|
+
content: z.string()
|
|
347
|
+
});
|
|
277
348
|
var readmeConfigSchema = z.strictObject({
|
|
278
349
|
apiName: nonEmptyStringSchema.optional(),
|
|
279
350
|
introduction: z.string().optional(),
|
|
280
351
|
apiReferenceLink: nonEmptyStringSchema.optional(),
|
|
281
352
|
bannerLink: nonEmptyStringSchema.optional(),
|
|
282
353
|
disabledSections: z.array(nonEmptyStringSchema).optional(),
|
|
354
|
+
customSections: z.array(readmeCustomSectionSchema).optional(),
|
|
283
355
|
defaultEndpoint: readmeEndpointSchema.optional(),
|
|
284
356
|
features: z.record(z.string(), z.array(readmeEndpointSchema)).optional()
|
|
285
357
|
});
|
|
@@ -294,6 +366,737 @@ var docsConfigSchema = z.strictObject({
|
|
|
294
366
|
referenceBaseUrl: nonEmptyStringSchema.optional(),
|
|
295
367
|
includeApiReference: z.boolean().optional()
|
|
296
368
|
});
|
|
369
|
+
|
|
370
|
+
// src/sdk-config/v1/docs.ts
|
|
371
|
+
var sdkConfigV1ReadmeEndpointSchema = readmeEndpointSchema;
|
|
372
|
+
var sdkConfigV1ReadmeCustomSectionSchema = readmeCustomSectionSchema;
|
|
373
|
+
var sdkConfigV1DocsConfigSchema = docsConfigSchema;
|
|
374
|
+
|
|
375
|
+
// src/sdk-config/v1/fern-config-mapper-types.ts
|
|
376
|
+
var FernConfigMappingError = class extends Error {
|
|
377
|
+
constructor(issues) {
|
|
378
|
+
super(issues.map(({ path, reason }) => `${path.join(".")}: ${reason}`).join("\n"));
|
|
379
|
+
this.issues = issues;
|
|
380
|
+
this.name = "FernConfigMappingError";
|
|
381
|
+
}
|
|
382
|
+
issues;
|
|
383
|
+
};
|
|
384
|
+
|
|
385
|
+
// src/sdk-config/v1/fern-config-mapper-helpers.ts
|
|
386
|
+
function fail(code, path, reason, suggestedAction, sdkConfigPath) {
|
|
387
|
+
throw new FernConfigMappingError([
|
|
388
|
+
{
|
|
389
|
+
code,
|
|
390
|
+
severity: "error",
|
|
391
|
+
path,
|
|
392
|
+
reason,
|
|
393
|
+
suggestedAction,
|
|
394
|
+
...optional("sdkConfigPath", sdkConfigPath)
|
|
395
|
+
}
|
|
396
|
+
]);
|
|
397
|
+
}
|
|
398
|
+
function takeTimeoutMs(value, state, basePath) {
|
|
399
|
+
const milliseconds = locate(value, ["defaultTimeout", "defaultTimeoutInMilliseconds"], basePath);
|
|
400
|
+
if (milliseconds && (milliseconds.value === "infinity" || isNonNegativeNumber(milliseconds.value))) {
|
|
401
|
+
consume(state, milliseconds.path);
|
|
402
|
+
return milliseconds.value;
|
|
403
|
+
}
|
|
404
|
+
const seconds = locate(
|
|
405
|
+
value,
|
|
406
|
+
["defaultTimeoutInSeconds", "timeoutInSeconds", "timeout"],
|
|
407
|
+
basePath
|
|
408
|
+
);
|
|
409
|
+
if (seconds && (seconds.value === "infinity" || isNonNegativeNumber(seconds.value))) {
|
|
410
|
+
consume(state, seconds.path);
|
|
411
|
+
return seconds.value === "infinity" ? "infinity" : seconds.value * 1e3;
|
|
412
|
+
}
|
|
413
|
+
return void 0;
|
|
414
|
+
}
|
|
415
|
+
function locate(value, aliases, basePath) {
|
|
416
|
+
for (const [key, child] of Object.entries(value)) {
|
|
417
|
+
if (aliases.some((alias) => normalizeKey(alias) === normalizeKey(key))) {
|
|
418
|
+
return { value: child, path: [...basePath, key] };
|
|
419
|
+
}
|
|
420
|
+
}
|
|
421
|
+
return void 0;
|
|
422
|
+
}
|
|
423
|
+
function takeObject(value, aliases, _state, basePath) {
|
|
424
|
+
const located = locate(value, aliases, basePath);
|
|
425
|
+
return located && isObject(located.value) ? { value: located.value, path: located.path } : void 0;
|
|
426
|
+
}
|
|
427
|
+
function takeString(value, aliases, state, basePath) {
|
|
428
|
+
const located = locate(value, aliases, basePath);
|
|
429
|
+
if (!located || typeof located.value !== "string" || located.value.length === 0) return void 0;
|
|
430
|
+
consume(state, located.path);
|
|
431
|
+
return located.value;
|
|
432
|
+
}
|
|
433
|
+
function takeGoModulePath(value, aliases, state, basePath) {
|
|
434
|
+
const located = locate(value, aliases, basePath);
|
|
435
|
+
if (!located || !goModulePathSchema.safeParse(located.value).success) return void 0;
|
|
436
|
+
consume(state, located.path);
|
|
437
|
+
return located.value;
|
|
438
|
+
}
|
|
439
|
+
function takeBoolean(value, aliases, state, basePath) {
|
|
440
|
+
const located = locate(value, aliases, basePath);
|
|
441
|
+
if (!located || typeof located.value !== "boolean") return void 0;
|
|
442
|
+
consume(state, located.path);
|
|
443
|
+
return located.value;
|
|
444
|
+
}
|
|
445
|
+
function takeNumber(value, aliases, state, basePath) {
|
|
446
|
+
const located = locate(value, aliases, basePath);
|
|
447
|
+
if (!located || !isNonNegativeNumber(located.value) || !Number.isInteger(located.value))
|
|
448
|
+
return void 0;
|
|
449
|
+
consume(state, located.path);
|
|
450
|
+
return located.value;
|
|
451
|
+
}
|
|
452
|
+
function takeEnum(value, aliases, values, state, basePath) {
|
|
453
|
+
const located = locate(value, aliases, basePath);
|
|
454
|
+
if (!located || typeof located.value !== "string" || !values.includes(located.value))
|
|
455
|
+
return void 0;
|
|
456
|
+
consume(state, located.path);
|
|
457
|
+
return located.value;
|
|
458
|
+
}
|
|
459
|
+
function takeEnumArray(value, aliases, values, state, basePath) {
|
|
460
|
+
const located = locate(value, aliases, basePath);
|
|
461
|
+
if (!located || !Array.isArray(located.value) || located.value.some((item) => typeof item !== "string" || !values.includes(item)))
|
|
462
|
+
return void 0;
|
|
463
|
+
consume(state, located.path);
|
|
464
|
+
return located.value;
|
|
465
|
+
}
|
|
466
|
+
function takeStringArray(value, aliases, state, basePath) {
|
|
467
|
+
const located = locate(value, aliases, basePath);
|
|
468
|
+
const strings = located ? stringArrayValue(located.value) : void 0;
|
|
469
|
+
if (!located || !strings) return void 0;
|
|
470
|
+
consume(state, located.path);
|
|
471
|
+
return strings;
|
|
472
|
+
}
|
|
473
|
+
function takeStringArrayRecord(value, aliases, state, basePath) {
|
|
474
|
+
const located = locate(value, aliases, basePath);
|
|
475
|
+
if (!located || !isObject(located.value)) return void 0;
|
|
476
|
+
const entries = Object.entries(located.value);
|
|
477
|
+
if (entries.some(([, item]) => !stringArrayValue(item))) return void 0;
|
|
478
|
+
consume(state, located.path);
|
|
479
|
+
return Object.fromEntries(entries);
|
|
480
|
+
}
|
|
481
|
+
function collectUnsupported(value, basePath, state) {
|
|
482
|
+
return collectLeafPaths(value, basePath).filter((path) => {
|
|
483
|
+
const key = pathKey(path);
|
|
484
|
+
return ![...state.consumedPaths].some(
|
|
485
|
+
(consumed) => key === consumed || key.startsWith(`${consumed}.`)
|
|
486
|
+
);
|
|
487
|
+
}).map((path) => ({
|
|
488
|
+
code: "FERN_CONFIG_FIELD_UNSUPPORTED",
|
|
489
|
+
severity: "warning",
|
|
490
|
+
path,
|
|
491
|
+
reason: "Fern configuration field is not represented by SDK Config v1",
|
|
492
|
+
suggestedAction: "Review this value and set the closest SDK Config field manually, or preserve the setting outside SDK Config if no equivalent exists."
|
|
493
|
+
}));
|
|
494
|
+
}
|
|
495
|
+
function collectLeafPaths(value, path) {
|
|
496
|
+
if (Array.isArray(value))
|
|
497
|
+
return value.flatMap((item, index) => collectLeafPaths(item, [...path, index]));
|
|
498
|
+
if (isObject(value))
|
|
499
|
+
return Object.entries(value).flatMap(([key, child]) => collectLeafPaths(child, [...path, key]));
|
|
500
|
+
return value === void 0 ? [] : [path];
|
|
501
|
+
}
|
|
502
|
+
function consume(state, path) {
|
|
503
|
+
state.consumedPaths.add(pathKey(path));
|
|
504
|
+
}
|
|
505
|
+
function pathKey(path) {
|
|
506
|
+
return path.join(".");
|
|
507
|
+
}
|
|
508
|
+
function normalizeKey(value) {
|
|
509
|
+
return value.replace(/[-_]/g, "").toLowerCase();
|
|
510
|
+
}
|
|
511
|
+
function compact(value) {
|
|
512
|
+
return Object.fromEntries(Object.entries(value).filter(([, child]) => child !== void 0));
|
|
513
|
+
}
|
|
514
|
+
function optional(key, value) {
|
|
515
|
+
return value === void 0 ? {} : { [key]: value };
|
|
516
|
+
}
|
|
517
|
+
function isObject(value) {
|
|
518
|
+
return value !== null && typeof value === "object" && !Array.isArray(value);
|
|
519
|
+
}
|
|
520
|
+
function isNonNegativeNumber(value) {
|
|
521
|
+
return typeof value === "number" && Number.isFinite(value) && value >= 0;
|
|
522
|
+
}
|
|
523
|
+
function stringValue(value) {
|
|
524
|
+
return typeof value === "string" && value.length > 0 ? value : void 0;
|
|
525
|
+
}
|
|
526
|
+
function stringArrayValue(value) {
|
|
527
|
+
return Array.isArray(value) && value.every((item) => typeof item === "string" && item.length > 0) ? value : void 0;
|
|
528
|
+
}
|
|
529
|
+
function stableJson(value) {
|
|
530
|
+
return JSON.stringify(sortKeys(value));
|
|
531
|
+
}
|
|
532
|
+
function sortKeys(value) {
|
|
533
|
+
if (Array.isArray(value)) return value.map(sortKeys);
|
|
534
|
+
if (!isObject(value)) return value;
|
|
535
|
+
return Object.fromEntries(
|
|
536
|
+
Object.entries(value).sort(([left], [right]) => left.localeCompare(right)).map(([key, child]) => [key, sortKeys(child)])
|
|
537
|
+
);
|
|
538
|
+
}
|
|
539
|
+
|
|
540
|
+
// src/sdk-config/v1/fern-config-mapper-output.ts
|
|
541
|
+
function mapOutput(generator, language, index) {
|
|
542
|
+
const raw = isObject(generator.raw) ? generator.raw : void 0;
|
|
543
|
+
const rawOutput = raw && isObject(raw.output) ? raw.output : void 0;
|
|
544
|
+
const outputPath = ["group", "generators", index, "outputMode"];
|
|
545
|
+
const state = { consumedPaths: /* @__PURE__ */ new Set() };
|
|
546
|
+
if (rawOutput?.location === "local-file-system") {
|
|
547
|
+
if (isObject(generator.outputMode)) consume(state, [...outputPath, "type"]);
|
|
548
|
+
return finishOutputMapping(
|
|
549
|
+
{
|
|
550
|
+
output: {
|
|
551
|
+
delivery: "files",
|
|
552
|
+
...typeof rawOutput.path === "string" && rawOutput.path ? { path: rawOutput.path } : {}
|
|
553
|
+
}
|
|
554
|
+
},
|
|
555
|
+
generator.outputMode,
|
|
556
|
+
outputPath,
|
|
557
|
+
state,
|
|
558
|
+
index
|
|
559
|
+
);
|
|
560
|
+
}
|
|
561
|
+
if (!isObject(generator.outputMode) || typeof generator.outputMode.type !== "string") {
|
|
562
|
+
fail(
|
|
563
|
+
"FERN_OUTPUT_REQUIRED",
|
|
564
|
+
["group", "generators", index, "outputMode"],
|
|
565
|
+
`Cannot map output for Fern generator ${generator.name}`,
|
|
566
|
+
"Set generator.output to a public SDK Config output, or provide the resolved Fern outputMode.",
|
|
567
|
+
["targets", index, "output"]
|
|
568
|
+
);
|
|
569
|
+
}
|
|
570
|
+
const output = generator.outputMode;
|
|
571
|
+
consume(state, [...outputPath, "type"]);
|
|
572
|
+
switch (output.type) {
|
|
573
|
+
case "downloadFiles":
|
|
574
|
+
return finishOutputMapping({ output: { delivery: "zip" } }, output, outputPath, state, index);
|
|
575
|
+
case "github":
|
|
576
|
+
return finishOutputMapping(
|
|
577
|
+
githubOutput(output, output.publishInfo, language, outputPath, state, index),
|
|
578
|
+
output,
|
|
579
|
+
outputPath,
|
|
580
|
+
state,
|
|
581
|
+
index
|
|
582
|
+
);
|
|
583
|
+
case "githubV2": {
|
|
584
|
+
if (!isObject(output.githubV2))
|
|
585
|
+
fail(
|
|
586
|
+
"FERN_GITHUB_OUTPUT_INVALID",
|
|
587
|
+
["group", "generators", index, "outputMode", "githubV2"],
|
|
588
|
+
"Fern githubV2 output is missing its configuration",
|
|
589
|
+
'Set target.output manually with delivery "github" and the intended repository.',
|
|
590
|
+
["targets", index, "output"]
|
|
591
|
+
);
|
|
592
|
+
const githubPath = [...outputPath, "githubV2"];
|
|
593
|
+
return finishOutputMapping(
|
|
594
|
+
githubOutput(
|
|
595
|
+
output.githubV2,
|
|
596
|
+
output.githubV2.publishInfo,
|
|
597
|
+
language,
|
|
598
|
+
githubPath,
|
|
599
|
+
state,
|
|
600
|
+
index
|
|
601
|
+
),
|
|
602
|
+
output,
|
|
603
|
+
outputPath,
|
|
604
|
+
state,
|
|
605
|
+
index
|
|
606
|
+
);
|
|
607
|
+
}
|
|
608
|
+
case "publishV2": {
|
|
609
|
+
const publication = mapPublication(
|
|
610
|
+
output.publishV2,
|
|
611
|
+
language,
|
|
612
|
+
[...outputPath, "publishV2"],
|
|
613
|
+
state,
|
|
614
|
+
index
|
|
615
|
+
);
|
|
616
|
+
return finishOutputMapping(
|
|
617
|
+
{
|
|
618
|
+
output: { delivery: "zip", publish: publication.publish },
|
|
619
|
+
...optional("package", publication.package)
|
|
620
|
+
},
|
|
621
|
+
output,
|
|
622
|
+
outputPath,
|
|
623
|
+
state,
|
|
624
|
+
index
|
|
625
|
+
);
|
|
626
|
+
}
|
|
627
|
+
case "publish": {
|
|
628
|
+
const publication = mapLegacyPublication(
|
|
629
|
+
output.registryOverrides,
|
|
630
|
+
language,
|
|
631
|
+
[...outputPath, "registryOverrides"],
|
|
632
|
+
state,
|
|
633
|
+
index
|
|
634
|
+
);
|
|
635
|
+
return finishOutputMapping(
|
|
636
|
+
{
|
|
637
|
+
output: { delivery: "zip", publish: publication.publish },
|
|
638
|
+
...optional("package", publication.package)
|
|
639
|
+
},
|
|
640
|
+
output,
|
|
641
|
+
outputPath,
|
|
642
|
+
state,
|
|
643
|
+
index
|
|
644
|
+
);
|
|
645
|
+
}
|
|
646
|
+
default:
|
|
647
|
+
fail(
|
|
648
|
+
"FERN_OUTPUT_UNSUPPORTED",
|
|
649
|
+
["group", "generators", index, "outputMode", "type"],
|
|
650
|
+
`Unsupported Fern output mode "${output.type}"`,
|
|
651
|
+
"Choose the equivalent files, zip, or github SDK Config output manually.",
|
|
652
|
+
["targets", index, "output"]
|
|
653
|
+
);
|
|
654
|
+
}
|
|
655
|
+
}
|
|
656
|
+
function githubOutput(value, publishInfo, language, sourcePath, state, index) {
|
|
657
|
+
const owner = stringValue(value.owner);
|
|
658
|
+
const repo = stringValue(value.repo);
|
|
659
|
+
if (!owner || !repo)
|
|
660
|
+
fail(
|
|
661
|
+
"FERN_GITHUB_REPOSITORY_REQUIRED",
|
|
662
|
+
sourcePath,
|
|
663
|
+
"Fern GitHub output requires owner and repo",
|
|
664
|
+
'Set target.output.github.repository manually as "owner/repository".',
|
|
665
|
+
["targets", index, "output", "github", "repository"]
|
|
666
|
+
);
|
|
667
|
+
consume(state, [...sourcePath, "owner"]);
|
|
668
|
+
consume(state, [...sourcePath, "repo"]);
|
|
669
|
+
const publication = publishInfo ? mapPublication(publishInfo, language, [...sourcePath, "publishInfo"], state, index) : void 0;
|
|
670
|
+
const type = stringValue(value.type);
|
|
671
|
+
const reviewers = mapReviewers(value.reviewers, [...sourcePath, "reviewers"], state);
|
|
672
|
+
if (type) consume(state, [...sourcePath, "type"]);
|
|
673
|
+
if (typeof value.makePr === "boolean") consume(state, [...sourcePath, "makePr"]);
|
|
674
|
+
if (stringValue(value.host)) consume(state, [...sourcePath, "host"]);
|
|
675
|
+
if (stringValue(value.branch)) consume(state, [...sourcePath, "branch"]);
|
|
676
|
+
return {
|
|
677
|
+
output: {
|
|
678
|
+
delivery: "github",
|
|
679
|
+
github: {
|
|
680
|
+
repository: `${owner}/${repo}`,
|
|
681
|
+
...optional("host", stringValue(value.host)),
|
|
682
|
+
...optional("branch", stringValue(value.branch)),
|
|
683
|
+
mode: value.makePr === true || type === "pullRequest" ? "pull-request" : type === "push" ? "push" : "release",
|
|
684
|
+
...optional("reviewers", reviewers)
|
|
685
|
+
},
|
|
686
|
+
...publication ? { publish: publication.publish } : {}
|
|
687
|
+
},
|
|
688
|
+
...optional("package", publication?.package)
|
|
689
|
+
};
|
|
690
|
+
}
|
|
691
|
+
function mapReviewers(value, sourcePath, state) {
|
|
692
|
+
if (Array.isArray(value)) {
|
|
693
|
+
const teams2 = reviewerNames(value, "team", sourcePath, state);
|
|
694
|
+
const users2 = reviewerNames(value, "user", sourcePath, state);
|
|
695
|
+
return teams2 || users2 ? { ...optional("teams", teams2), ...optional("users", users2) } : void 0;
|
|
696
|
+
}
|
|
697
|
+
if (!isObject(value)) return void 0;
|
|
698
|
+
const teams = reviewerNames(value.teams, "team", [...sourcePath, "teams"], state);
|
|
699
|
+
const users = reviewerNames(value.users, "user", [...sourcePath, "users"], state);
|
|
700
|
+
return teams || users ? { ...optional("teams", teams), ...optional("users", users) } : void 0;
|
|
701
|
+
}
|
|
702
|
+
function reviewerNames(value, expectedType, sourcePath, state) {
|
|
703
|
+
if (!Array.isArray(value)) return void 0;
|
|
704
|
+
const names = value.flatMap((reviewer, index) => {
|
|
705
|
+
if (typeof reviewer === "string") {
|
|
706
|
+
consume(state, [...sourcePath, index]);
|
|
707
|
+
return [reviewer];
|
|
708
|
+
}
|
|
709
|
+
if (!isObject(reviewer) || reviewer.type !== expectedType || typeof reviewer.name !== "string") {
|
|
710
|
+
return [];
|
|
711
|
+
}
|
|
712
|
+
consume(state, [...sourcePath, index, "type"]);
|
|
713
|
+
consume(state, [...sourcePath, index, "name"]);
|
|
714
|
+
return [reviewer.name];
|
|
715
|
+
});
|
|
716
|
+
return names.length ? names : void 0;
|
|
717
|
+
}
|
|
718
|
+
function mapPublication(value, language, sourcePath, state, index) {
|
|
719
|
+
if (!isObject(value))
|
|
720
|
+
fail(
|
|
721
|
+
"FERN_PUBLICATION_INVALID",
|
|
722
|
+
sourcePath,
|
|
723
|
+
"Fern publication output is invalid",
|
|
724
|
+
"Set target.output.publish and target.package manually.",
|
|
725
|
+
["targets", index, "output", "publish"]
|
|
726
|
+
);
|
|
727
|
+
const type = stringValue(value.type);
|
|
728
|
+
if (type) consume(state, [...sourcePath, "type"]);
|
|
729
|
+
const nested = type && isObject(value[type]) ? value[type] : value;
|
|
730
|
+
const nestedPath = nested === value ? sourcePath : [...sourcePath, type];
|
|
731
|
+
const registry = publicationRegistry(type, language, [...sourcePath, "type"], index);
|
|
732
|
+
const registryUrl = stringValue(nested.registryUrl);
|
|
733
|
+
if (registryUrl) consume(state, [...nestedPath, "registryUrl"]);
|
|
734
|
+
if (registry === "maven") {
|
|
735
|
+
const coordinate = stringValue(nested.coordinate);
|
|
736
|
+
if (coordinate) consume(state, [...nestedPath, "coordinate"]);
|
|
737
|
+
return {
|
|
738
|
+
publish: compact({ registry, url: registryUrl }),
|
|
739
|
+
...coordinate ? { package: mavenPackage(coordinate, [...nestedPath, "coordinate"], index) } : {}
|
|
740
|
+
};
|
|
741
|
+
}
|
|
742
|
+
const packageNameField = stringValue(nested.packageName) ? "packageName" : "coordinate";
|
|
743
|
+
const packageName = stringValue(nested[packageNameField]);
|
|
744
|
+
if (packageName) consume(state, [...nestedPath, packageNameField]);
|
|
745
|
+
const metadata = registry === "pypi" ? mapPypiMetadata(nested.pypiMetadata, nestedPath, state) : {};
|
|
746
|
+
return {
|
|
747
|
+
publish: compact({ registry, url: registryUrl }),
|
|
748
|
+
...packageName || Object.keys(metadata).length ? { package: { ...optional("packageName", packageName), ...metadata } } : {}
|
|
749
|
+
};
|
|
750
|
+
}
|
|
751
|
+
function mapLegacyPublication(value, language, sourcePath, state, index) {
|
|
752
|
+
const registry = defaultRegistry(language, sourcePath, index);
|
|
753
|
+
const overrides = isObject(value) ? value : {};
|
|
754
|
+
const override = isObject(overrides[registry]) ? overrides[registry] : {};
|
|
755
|
+
return mapPublication(override, language, [...sourcePath, registry], state, index);
|
|
756
|
+
}
|
|
757
|
+
function publicationRegistry(type, language, sourcePath, index) {
|
|
758
|
+
if (type === "postman") {
|
|
759
|
+
fail(
|
|
760
|
+
"FERN_POSTMAN_PUBLICATION_UNSUPPORTED",
|
|
761
|
+
sourcePath,
|
|
762
|
+
"Postman collection publication is not an SDK output",
|
|
763
|
+
"Remove this non-SDK target or convert it separately from the SDK Config document."
|
|
764
|
+
);
|
|
765
|
+
}
|
|
766
|
+
const normalized = type?.replace(/Override$/, "").toLowerCase();
|
|
767
|
+
if (normalized === "rubygems") return "rubygems";
|
|
768
|
+
if (normalized && ["npm", "pypi", "maven", "nuget", "crates"].includes(normalized)) {
|
|
769
|
+
return normalized;
|
|
770
|
+
}
|
|
771
|
+
if (normalized !== void 0) {
|
|
772
|
+
fail(
|
|
773
|
+
"FERN_PUBLICATION_UNSUPPORTED",
|
|
774
|
+
sourcePath,
|
|
775
|
+
`Unsupported Fern publication type "${type}"`,
|
|
776
|
+
"Set target.output.publish and target.package manually if SDK Config supports the registry.",
|
|
777
|
+
["targets", index, "output", "publish"]
|
|
778
|
+
);
|
|
779
|
+
}
|
|
780
|
+
return defaultRegistry(language, sourcePath, index);
|
|
781
|
+
}
|
|
782
|
+
function defaultRegistry(language, sourcePath, index) {
|
|
783
|
+
const registries = {
|
|
784
|
+
typescript: "npm",
|
|
785
|
+
mcp: "npm",
|
|
786
|
+
python: "pypi",
|
|
787
|
+
java: "maven",
|
|
788
|
+
kotlin: "maven",
|
|
789
|
+
csharp: "nuget",
|
|
790
|
+
ruby: "rubygems",
|
|
791
|
+
rust: "crates",
|
|
792
|
+
go: "go",
|
|
793
|
+
php: "composer"
|
|
794
|
+
};
|
|
795
|
+
const registry = registries[language];
|
|
796
|
+
if (!registry)
|
|
797
|
+
fail(
|
|
798
|
+
"FERN_PUBLICATION_REGISTRY_REQUIRED",
|
|
799
|
+
sourcePath,
|
|
800
|
+
`No publication registry can be inferred for ${language}`,
|
|
801
|
+
"Set target.output.publish.registry manually.",
|
|
802
|
+
["targets", index, "output", "publish", "registry"]
|
|
803
|
+
);
|
|
804
|
+
return registry;
|
|
805
|
+
}
|
|
806
|
+
function mavenPackage(coordinate, sourcePath, index) {
|
|
807
|
+
const parts = coordinate.split(":");
|
|
808
|
+
const [groupId, artifactId] = parts;
|
|
809
|
+
if (parts.length !== 2 || !groupId || !artifactId)
|
|
810
|
+
fail(
|
|
811
|
+
"FERN_MAVEN_COORDINATE_INVALID",
|
|
812
|
+
sourcePath,
|
|
813
|
+
`Invalid Maven coordinate ${coordinate}`,
|
|
814
|
+
"Set target.package.groupId and target.package.artifactId manually.",
|
|
815
|
+
["targets", index, "package"]
|
|
816
|
+
);
|
|
817
|
+
return { groupId, artifactId };
|
|
818
|
+
}
|
|
819
|
+
function mapPypiMetadata(value, sourcePath, state) {
|
|
820
|
+
if (!isObject(value)) return {};
|
|
821
|
+
const metadataPath = [...sourcePath, "pypiMetadata"];
|
|
822
|
+
const description = stringValue(value.description);
|
|
823
|
+
const keywords = stringArrayValue(value.keywords);
|
|
824
|
+
const documentationUrl = stringValue(value.documentationLink);
|
|
825
|
+
const homepage = stringValue(value.homepageLink);
|
|
826
|
+
const authors = mapAuthors(value.authors, [...metadataPath, "authors"], state);
|
|
827
|
+
if (description) consume(state, [...metadataPath, "description"]);
|
|
828
|
+
if (keywords) consume(state, [...metadataPath, "keywords"]);
|
|
829
|
+
if (documentationUrl) consume(state, [...metadataPath, "documentationLink"]);
|
|
830
|
+
if (homepage) consume(state, [...metadataPath, "homepageLink"]);
|
|
831
|
+
return compact({ description, authors, keywords, documentationUrl, homepage });
|
|
832
|
+
}
|
|
833
|
+
function mapAuthors(value, sourcePath, state) {
|
|
834
|
+
if (!Array.isArray(value)) return void 0;
|
|
835
|
+
const authors = value.flatMap((author) => {
|
|
836
|
+
if (!isObject(author)) return [];
|
|
837
|
+
const name = stringValue(author.name);
|
|
838
|
+
const email = stringValue(author.email);
|
|
839
|
+
return name ? [{ name, ...optional("email", email) }] : [];
|
|
840
|
+
});
|
|
841
|
+
if (authors.length !== value.length) return void 0;
|
|
842
|
+
value.forEach((author, index) => {
|
|
843
|
+
consume(state, [...sourcePath, index, "name"]);
|
|
844
|
+
if (isObject(author) && stringValue(author.email)) {
|
|
845
|
+
consume(state, [...sourcePath, index, "email"]);
|
|
846
|
+
}
|
|
847
|
+
});
|
|
848
|
+
return authors;
|
|
849
|
+
}
|
|
850
|
+
function finishOutputMapping(mapping, outputMode, sourcePath, state, index) {
|
|
851
|
+
for (const path of collectLeafPaths(outputMode, sourcePath)) {
|
|
852
|
+
if (path[path.length - 1] === "_visit") consume(state, path);
|
|
853
|
+
}
|
|
854
|
+
return {
|
|
855
|
+
...mapping,
|
|
856
|
+
unsupportedFields: collectUnsupported(outputMode, sourcePath, state).map(
|
|
857
|
+
(diagnostic) => outputDiagnostic(diagnostic.path, index)
|
|
858
|
+
)
|
|
859
|
+
};
|
|
860
|
+
}
|
|
861
|
+
function outputDiagnostic(path, index) {
|
|
862
|
+
const fields = path.filter((part) => typeof part === "string");
|
|
863
|
+
const field = fields[fields.length - 1];
|
|
864
|
+
const credential = fields.some((part) => part === "credentials" || part === "signature") || ["apiKey", "keyId", "password", "secretKey", "token", "username"].includes(field ?? "");
|
|
865
|
+
if (credential) {
|
|
866
|
+
return {
|
|
867
|
+
code: "FERN_OUTPUT_CREDENTIAL_UNSUPPORTED",
|
|
868
|
+
severity: "warning",
|
|
869
|
+
path,
|
|
870
|
+
reason: "Fern output credentials and signatures are not represented by SDK Config v1",
|
|
871
|
+
suggestedAction: "Configure publication credentials and signing secrets outside SDK Config."
|
|
872
|
+
};
|
|
873
|
+
}
|
|
874
|
+
const guidance = {
|
|
875
|
+
directory: {
|
|
876
|
+
suggestedAction: "Preserve the GitHub output subdirectory outside SDK Config; public v1 has no repository subdirectory field."
|
|
877
|
+
},
|
|
878
|
+
license: {
|
|
879
|
+
sdkConfigPath: ["targets", index, "package", "license"],
|
|
880
|
+
suggestedAction: "Set target.package.license manually using portable license metadata."
|
|
881
|
+
},
|
|
882
|
+
id: {
|
|
883
|
+
sdkConfigPath: ["targets", index, "package", "license"],
|
|
884
|
+
suggestedAction: "Set target.package.license manually using portable license metadata."
|
|
885
|
+
},
|
|
886
|
+
contents: {
|
|
887
|
+
sdkConfigPath: ["targets", index, "package", "license"],
|
|
888
|
+
suggestedAction: "Set target.package.license manually without embedding license contents."
|
|
889
|
+
},
|
|
890
|
+
downloadSnippets: {
|
|
891
|
+
sdkConfigPath: ["docs", "snippets", "enabled"],
|
|
892
|
+
suggestedAction: "Set docs.snippets.enabled manually and choose a portable output path if needed."
|
|
893
|
+
},
|
|
894
|
+
version: {
|
|
895
|
+
sdkConfigPath: ["targets", index, "sdkVersion"],
|
|
896
|
+
suggestedAction: "Set target.sdkVersion manually if this output version identifies the SDK artifact."
|
|
897
|
+
},
|
|
898
|
+
description: {
|
|
899
|
+
sdkConfigPath: ["targets", index, "package", "description"],
|
|
900
|
+
suggestedAction: "Set target.package.description manually to a valid value."
|
|
901
|
+
},
|
|
902
|
+
authors: {
|
|
903
|
+
sdkConfigPath: ["targets", index, "package", "authors"],
|
|
904
|
+
suggestedAction: "Set target.package.authors manually using valid author metadata."
|
|
905
|
+
},
|
|
906
|
+
keywords: {
|
|
907
|
+
sdkConfigPath: ["targets", index, "package", "keywords"],
|
|
908
|
+
suggestedAction: "Set target.package.keywords manually using non-empty strings."
|
|
909
|
+
},
|
|
910
|
+
documentationLink: {
|
|
911
|
+
sdkConfigPath: ["targets", index, "package", "documentationUrl"],
|
|
912
|
+
suggestedAction: "Set target.package.documentationUrl manually to a valid URL."
|
|
913
|
+
},
|
|
914
|
+
homepageLink: {
|
|
915
|
+
sdkConfigPath: ["targets", index, "package", "homepage"],
|
|
916
|
+
suggestedAction: "Set target.package.homepage manually to a valid URL."
|
|
917
|
+
}
|
|
918
|
+
};
|
|
919
|
+
const fieldGuidance = field ? guidance[field] : void 0;
|
|
920
|
+
const resolvedGuidance = fields.includes("license") ? guidance.license : fieldGuidance;
|
|
921
|
+
return {
|
|
922
|
+
code: "FERN_OUTPUT_FIELD_UNSUPPORTED",
|
|
923
|
+
severity: "warning",
|
|
924
|
+
path,
|
|
925
|
+
reason: "Fern output field is not represented by SDK Config v1",
|
|
926
|
+
...optional("sdkConfigPath", resolvedGuidance?.sdkConfigPath),
|
|
927
|
+
suggestedAction: resolvedGuidance?.suggestedAction ?? "Review this output setting and preserve it outside SDK Config when no equivalent exists."
|
|
928
|
+
};
|
|
929
|
+
}
|
|
930
|
+
var customerGenerationAssetSchema = z.discriminatedUnion("type", [
|
|
931
|
+
z.strictObject({ type: z.literal("path"), location: nonEmptyStringSchema }),
|
|
932
|
+
z.strictObject({ type: z.literal("url"), location: nonEmptyStringSchema })
|
|
933
|
+
]);
|
|
934
|
+
var hookDependencySchema = z.strictObject({
|
|
935
|
+
name: nonEmptyStringSchema,
|
|
936
|
+
version: nonEmptyStringSchema,
|
|
937
|
+
groupId: nonEmptyStringSchema.optional()
|
|
938
|
+
});
|
|
939
|
+
var hooksConfigSchema = z.strictObject({
|
|
940
|
+
enabled: z.boolean(),
|
|
941
|
+
source: customerGenerationAssetSchema.optional(),
|
|
942
|
+
dependencies: z.array(hookDependencySchema).optional()
|
|
943
|
+
});
|
|
944
|
+
var customCodeConfigSchema = z.strictObject({
|
|
945
|
+
enabled: z.boolean(),
|
|
946
|
+
source: customerGenerationAssetSchema.optional(),
|
|
947
|
+
conflictStrategy: z.enum(["mark", "ours", "theirs"]).optional(),
|
|
948
|
+
trackChanges: z.boolean().optional(),
|
|
949
|
+
protectedFiles: z.array(nonEmptyStringSchema).optional()
|
|
950
|
+
});
|
|
951
|
+
var workflowConfigSchema = z.strictObject({
|
|
952
|
+
path: nonEmptyStringSchema,
|
|
953
|
+
outputName: nonEmptyStringSchema.optional()
|
|
954
|
+
});
|
|
955
|
+
var analyticsHeaderSchema = z.union([
|
|
956
|
+
z.strictObject({ name: nonEmptyStringSchema, value: z.string() }),
|
|
957
|
+
z.strictObject({
|
|
958
|
+
name: nonEmptyStringSchema,
|
|
959
|
+
valueRef: nonEmptyStringSchema
|
|
960
|
+
})
|
|
961
|
+
]);
|
|
962
|
+
var analyticsConfigSchema = z.strictObject({
|
|
963
|
+
enabled: z.boolean(),
|
|
964
|
+
endpoint: nonEmptyStringSchema.optional(),
|
|
965
|
+
exporter: z.enum(["otlp-http", "console"]).optional(),
|
|
966
|
+
headers: z.array(analyticsHeaderSchema).optional(),
|
|
967
|
+
batchSize: z.number().int().positive().optional(),
|
|
968
|
+
scheduledDelayMs: z.number().nonnegative().optional(),
|
|
969
|
+
exportTimeoutMs: z.number().nonnegative().optional()
|
|
970
|
+
}).superRefine(({ enabled, endpoint }, context) => {
|
|
971
|
+
if (enabled && endpoint === void 0) {
|
|
972
|
+
context.addIssue({
|
|
973
|
+
code: "custom",
|
|
974
|
+
message: "endpoint is required when analytics is enabled",
|
|
975
|
+
path: ["endpoint"]
|
|
976
|
+
});
|
|
977
|
+
}
|
|
978
|
+
});
|
|
979
|
+
var wireTestsSchema = z.strictObject({
|
|
980
|
+
enabled: z.boolean(),
|
|
981
|
+
exclusions: z.array(nonEmptyStringSchema).optional(),
|
|
982
|
+
fallbackToGeneratedErrorExamples: z.boolean().optional(),
|
|
983
|
+
fixtureSource: z.enum(["synthetic", "recorded", "auto"]).optional()
|
|
984
|
+
});
|
|
985
|
+
var unitTestsSchema = z.strictObject({
|
|
986
|
+
enabled: z.boolean(),
|
|
987
|
+
mode: z.enum(["core-runtime", "schema-driven", "both"]).optional(),
|
|
988
|
+
exclusions: z.array(nonEmptyStringSchema).optional()
|
|
989
|
+
});
|
|
990
|
+
var streamsSchema = z.strictObject({
|
|
991
|
+
enabled: z.boolean(),
|
|
992
|
+
responseType: z.enum(["wrapper", "native", "web"]).optional(),
|
|
993
|
+
fileResponseType: z.enum(["stream", "binary-response"]).optional(),
|
|
994
|
+
defaultChunkSizeBytes: z.number().int().positive().optional()
|
|
995
|
+
});
|
|
996
|
+
var namingConfigSchema = z.strictObject({
|
|
997
|
+
clientName: nonEmptyStringSchema.optional(),
|
|
998
|
+
exportedClientName: nonEmptyStringSchema.optional(),
|
|
999
|
+
environmentTypeName: nonEmptyStringSchema.optional(),
|
|
1000
|
+
apiErrorName: nonEmptyStringSchema.optional(),
|
|
1001
|
+
baseErrorName: nonEmptyStringSchema.optional(),
|
|
1002
|
+
pagerName: nonEmptyStringSchema.optional()
|
|
1003
|
+
});
|
|
1004
|
+
var layoutConfigSchema = z.strictObject({
|
|
1005
|
+
outputDirectory: z.enum(["project-root", "source-root"]).optional(),
|
|
1006
|
+
packagePath: nonEmptyStringSchema.optional()
|
|
1007
|
+
});
|
|
1008
|
+
var serializationConfigSchema = z.strictObject({
|
|
1009
|
+
enumRepresentation: z.enum(["enum", "union", "literal", "forward-compatible-enum", "language-default"]).optional(),
|
|
1010
|
+
additionalProperties: z.enum(["allow", "forbid", "ignore", "language-default"]).optional(),
|
|
1011
|
+
inlineTypes: z.boolean().optional(),
|
|
1012
|
+
omitUndefined: z.boolean().optional()
|
|
1013
|
+
});
|
|
1014
|
+
var sdkConfigV1GenerationConfigSchema = z.strictObject({
|
|
1015
|
+
includeWatermark: z.boolean().default(false),
|
|
1016
|
+
ai: z.boolean().default(false),
|
|
1017
|
+
includeOptionalSnippetParameters: z.boolean().optional(),
|
|
1018
|
+
buildAllModels: z.boolean().default(false),
|
|
1019
|
+
inferServiceNames: z.boolean().default(false),
|
|
1020
|
+
includeDeprecatedOperations: z.boolean().default(true),
|
|
1021
|
+
multipleResponses: z.boolean().default(false),
|
|
1022
|
+
devContainer: z.boolean().default(false),
|
|
1023
|
+
allowMockClient: z.boolean().default(false),
|
|
1024
|
+
ignoreFiles: z.array(nonEmptyStringSchema).optional(),
|
|
1025
|
+
reservedKeywords: z.array(nonEmptyStringSchema).optional(),
|
|
1026
|
+
hooks: hooksConfigSchema.optional(),
|
|
1027
|
+
customCode: customCodeConfigSchema.optional(),
|
|
1028
|
+
workflows: z.array(workflowConfigSchema).optional(),
|
|
1029
|
+
customQueryPaths: z.array(nonEmptyStringSchema).optional(),
|
|
1030
|
+
analytics: analyticsConfigSchema.optional(),
|
|
1031
|
+
wireTests: wireTestsSchema.optional(),
|
|
1032
|
+
unitTests: unitTestsSchema.optional(),
|
|
1033
|
+
webSockets: z.boolean().optional(),
|
|
1034
|
+
streams: streamsSchema.optional(),
|
|
1035
|
+
naming: namingConfigSchema.optional(),
|
|
1036
|
+
layout: layoutConfigSchema.optional(),
|
|
1037
|
+
serialization: serializationConfigSchema.optional()
|
|
1038
|
+
});
|
|
1039
|
+
var sdkConfigV1PublishRegistrySchema = z.enum([
|
|
1040
|
+
"npm",
|
|
1041
|
+
"pypi",
|
|
1042
|
+
"maven",
|
|
1043
|
+
"nuget",
|
|
1044
|
+
"rubygems",
|
|
1045
|
+
"crates",
|
|
1046
|
+
"go",
|
|
1047
|
+
"composer"
|
|
1048
|
+
]);
|
|
1049
|
+
var commonPublishShape = {
|
|
1050
|
+
url: nonEmptyStringSchema.optional(),
|
|
1051
|
+
releaseBranch: nonEmptyStringSchema.optional(),
|
|
1052
|
+
tolerateRepublish: z.boolean().optional()
|
|
1053
|
+
};
|
|
1054
|
+
var sdkConfigV1PublishConfigSchema = z.discriminatedUnion("registry", [
|
|
1055
|
+
z.strictObject({ registry: z.literal("npm"), ...commonPublishShape }),
|
|
1056
|
+
z.strictObject({ registry: z.literal("pypi"), ...commonPublishShape }),
|
|
1057
|
+
z.strictObject({ registry: z.literal("maven"), ...commonPublishShape }),
|
|
1058
|
+
z.strictObject({ registry: z.literal("nuget"), ...commonPublishShape }),
|
|
1059
|
+
z.strictObject({ registry: z.literal("rubygems"), ...commonPublishShape }),
|
|
1060
|
+
z.strictObject({ registry: z.literal("crates"), ...commonPublishShape }),
|
|
1061
|
+
z.strictObject({ registry: z.literal("go"), ...commonPublishShape }),
|
|
1062
|
+
z.strictObject({ registry: z.literal("composer"), ...commonPublishShape })
|
|
1063
|
+
]);
|
|
1064
|
+
var reviewersSchema = z.strictObject({
|
|
1065
|
+
teams: z.array(nonEmptyStringSchema).optional(),
|
|
1066
|
+
users: z.array(nonEmptyStringSchema).optional()
|
|
1067
|
+
});
|
|
1068
|
+
var githubOutputSchema = z.strictObject({
|
|
1069
|
+
repository: nonEmptyStringSchema,
|
|
1070
|
+
host: nonEmptyStringSchema.optional(),
|
|
1071
|
+
branch: nonEmptyStringSchema.optional(),
|
|
1072
|
+
mode: z.enum(["release", "pull-request", "push"]).optional(),
|
|
1073
|
+
reviewers: reviewersSchema.optional(),
|
|
1074
|
+
privateRepository: z.boolean().optional()
|
|
1075
|
+
});
|
|
1076
|
+
var filesOutputSchema = z.strictObject({
|
|
1077
|
+
delivery: z.literal("files"),
|
|
1078
|
+
path: nonEmptyStringSchema.optional(),
|
|
1079
|
+
publish: sdkConfigV1PublishConfigSchema.optional()
|
|
1080
|
+
});
|
|
1081
|
+
var zipOutputSchema = z.strictObject({
|
|
1082
|
+
delivery: z.literal("zip"),
|
|
1083
|
+
fileName: nonEmptyStringSchema.optional(),
|
|
1084
|
+
publish: sdkConfigV1PublishConfigSchema.optional()
|
|
1085
|
+
});
|
|
1086
|
+
var githubDeliverySchema = z.strictObject({
|
|
1087
|
+
delivery: z.literal("github"),
|
|
1088
|
+
github: githubOutputSchema,
|
|
1089
|
+
publish: sdkConfigV1PublishConfigSchema.optional()
|
|
1090
|
+
});
|
|
1091
|
+
var sdkConfigV1OutputConfigSchema = z.discriminatedUnion(
|
|
1092
|
+
"delivery",
|
|
1093
|
+
[filesOutputSchema, zipOutputSchema, githubDeliverySchema],
|
|
1094
|
+
{ error: 'output.delivery must be one of "files", "zip", or "github"' }
|
|
1095
|
+
);
|
|
1096
|
+
|
|
1097
|
+
// src/sdk-config/v1/package.ts
|
|
1098
|
+
var sdkConfigV1DependencySchema = dependencySchema;
|
|
1099
|
+
var sdkConfigV1PackageConfigSchema = packageConfigSchema;
|
|
297
1100
|
var cliGenerationConfigSchema = z.strictObject({
|
|
298
1101
|
paginationParameters: z.array(nonEmptyStringSchema).optional(),
|
|
299
1102
|
skills: z.boolean().optional()
|
|
@@ -303,10 +1106,15 @@ var csharpGenerationConfigSchema = z.strictObject({
|
|
|
303
1106
|
simplifyObjectDictionaries: z.boolean().optional(),
|
|
304
1107
|
explicitNamespaces: z.boolean().optional(),
|
|
305
1108
|
rootNamespaceForCoreClasses: z.boolean().optional(),
|
|
306
|
-
includeExceptionHandler: z.boolean().optional()
|
|
1109
|
+
includeExceptionHandler: z.boolean().optional(),
|
|
1110
|
+
experimentalExplicitNullableOptional: z.boolean().optional()
|
|
307
1111
|
});
|
|
308
1112
|
var goGenerationConfigSchema = z.strictObject({
|
|
309
1113
|
legacyComplexModels: z.boolean().optional(),
|
|
1114
|
+
/** Uppercase common initialisms in generated names (`UserID` rather than `UserId`). */
|
|
1115
|
+
smartCasing: z.boolean().optional(),
|
|
1116
|
+
/** Overrides the fern root-client constructor independently from the client type name. */
|
|
1117
|
+
clientConstructorName: nonEmptyStringSchema.optional(),
|
|
310
1118
|
unionVersion: z.enum(["v0", "v1"]).optional(),
|
|
311
1119
|
includeLegacyClientOptions: z.boolean().optional()
|
|
312
1120
|
});
|
|
@@ -316,15 +1124,17 @@ var jvmGenerationConfigSchema = z.strictObject({
|
|
|
316
1124
|
collapseOptionalNullable: z.boolean().optional(),
|
|
317
1125
|
gradleDistributionUrl: z.string().min(1).optional(),
|
|
318
1126
|
gradlePluginManagement: z.string().optional(),
|
|
319
|
-
gradleCentralDependencyManagement: z.boolean().optional()
|
|
1127
|
+
gradleCentralDependencyManagement: z.boolean().optional(),
|
|
1128
|
+
/** Selects co-located async methods or a separate async client surface. */
|
|
1129
|
+
asyncStyle: z.enum(["dedicated-client", "twin-methods"]).optional()
|
|
320
1130
|
});
|
|
321
1131
|
|
|
322
|
-
// src/sdk-config-
|
|
1132
|
+
// src/sdk-config-domain/v1/language/java.ts
|
|
323
1133
|
var javaGenerationConfigSchema = jvmGenerationConfigSchema.extend({
|
|
324
1134
|
includeKotlinSnippets: z.boolean().optional()
|
|
325
1135
|
});
|
|
326
1136
|
|
|
327
|
-
// src/sdk-config-
|
|
1137
|
+
// src/sdk-config-domain/v1/language/kotlin.ts
|
|
328
1138
|
var kotlinGenerationConfigSchema = jvmGenerationConfigSchema;
|
|
329
1139
|
var compilerOptionsSchema = z.strictObject({
|
|
330
1140
|
target: nonEmptyStringSchema.optional(),
|
|
@@ -356,8 +1166,32 @@ var typescriptGenerationConfigSchema = z.strictObject({
|
|
|
356
1166
|
scripts: z.array(packageScriptSchema).optional()
|
|
357
1167
|
});
|
|
358
1168
|
|
|
359
|
-
// src/sdk-config-
|
|
360
|
-
var
|
|
1169
|
+
// src/sdk-config-domain/v1/language/mcp.ts
|
|
1170
|
+
var mcpAvailabilityStatuses = [
|
|
1171
|
+
"IN_DEVELOPMENT",
|
|
1172
|
+
"PRE_RELEASE",
|
|
1173
|
+
"GENERAL_AVAILABILITY",
|
|
1174
|
+
"DEPRECATED",
|
|
1175
|
+
"ALPHA",
|
|
1176
|
+
"BETA",
|
|
1177
|
+
"PREVIEW",
|
|
1178
|
+
"LEGACY"
|
|
1179
|
+
];
|
|
1180
|
+
var mcpToolFilterSchema = z.strictObject({
|
|
1181
|
+
include: z.array(nonEmptyStringSchema).optional(),
|
|
1182
|
+
exclude: z.array(nonEmptyStringSchema).optional()
|
|
1183
|
+
});
|
|
1184
|
+
var mcpToolsetNameSchema = nonEmptyStringSchema.refine(
|
|
1185
|
+
(name) => name !== "default" && /^[a-z0-9-]+$/.test(name),
|
|
1186
|
+
'toolset names must match [a-z0-9-]+ and cannot be "default"'
|
|
1187
|
+
);
|
|
1188
|
+
var mcpGenerationConfigSchema = typescriptGenerationConfigSchema.extend({
|
|
1189
|
+
serverName: nonEmptyStringSchema.optional(),
|
|
1190
|
+
serverDescription: nonEmptyStringSchema.optional(),
|
|
1191
|
+
excludeAvailability: z.array(z.enum(mcpAvailabilityStatuses)).optional(),
|
|
1192
|
+
tools: mcpToolFilterSchema.optional(),
|
|
1193
|
+
toolsets: z.record(mcpToolsetNameSchema, mcpToolFilterSchema).optional()
|
|
1194
|
+
});
|
|
361
1195
|
var phpGenerationConfigSchema = z.strictObject({
|
|
362
1196
|
propertyAccess: z.enum(["public", "private"]).optional(),
|
|
363
1197
|
generateClientInterfaces: z.boolean().optional()
|
|
@@ -398,126 +1232,1002 @@ var rustGenerationConfigSchema = z.strictObject({
|
|
|
398
1232
|
defaultFeatures: z.array(nonEmptyStringSchema).optional()
|
|
399
1233
|
});
|
|
400
1234
|
var swiftGenerationConfigSchema = z.strictObject({
|
|
401
|
-
moduleName: nonEmptyStringSchema.optional()
|
|
1235
|
+
moduleName: nonEmptyStringSchema.optional(),
|
|
1236
|
+
nullableAsOptional: z.boolean().optional()
|
|
402
1237
|
});
|
|
403
|
-
var
|
|
404
|
-
|
|
405
|
-
|
|
406
|
-
);
|
|
407
|
-
var
|
|
408
|
-
|
|
409
|
-
|
|
410
|
-
);
|
|
411
|
-
var authorSchema = z.strictObject({
|
|
412
|
-
name: nonEmptyStringSchema,
|
|
413
|
-
email: z.email().optional()
|
|
1238
|
+
var planModifierSourceSchema = z.discriminatedUnion("enabled", [
|
|
1239
|
+
z.strictObject({ enabled: z.literal(true), sourceDir: nonEmptyStringSchema }),
|
|
1240
|
+
z.strictObject({ enabled: z.literal(false) })
|
|
1241
|
+
]);
|
|
1242
|
+
var planModifiersSchema = z.strictObject({
|
|
1243
|
+
resources: planModifierSourceSchema,
|
|
1244
|
+
attributes: planModifierSourceSchema
|
|
414
1245
|
});
|
|
415
|
-
var
|
|
416
|
-
|
|
417
|
-
|
|
418
|
-
organization: nonEmptyStringSchema.optional(),
|
|
419
|
-
organizationUrl: nonEmptyStringSchema.optional()
|
|
1246
|
+
var providerSchemaSchema = z.strictObject({
|
|
1247
|
+
addressKey: nonEmptyStringSchema,
|
|
1248
|
+
authTokenKey: nonEmptyStringSchema
|
|
420
1249
|
});
|
|
421
|
-
var
|
|
422
|
-
|
|
423
|
-
|
|
424
|
-
|
|
425
|
-
|
|
1250
|
+
var terraformGenerationConfigSchema = z.strictObject({
|
|
1251
|
+
providerName: nonEmptyStringSchema.optional(),
|
|
1252
|
+
providerVersion: nonEmptyStringSchema.optional(),
|
|
1253
|
+
providerModulePath: goModulePathSchema.optional(),
|
|
1254
|
+
mockAcceptance: z.boolean().optional(),
|
|
1255
|
+
hideComputedDiff: z.boolean().optional(),
|
|
1256
|
+
providerSchema: providerSchemaSchema.optional(),
|
|
1257
|
+
planModifiers: planModifiersSchema.optional()
|
|
1258
|
+
});
|
|
1259
|
+
|
|
1260
|
+
// src/sdk-config/v1/target.ts
|
|
1261
|
+
var targetOverrideShape = {
|
|
1262
|
+
generatorVersion: exactSemverSchema.optional(),
|
|
1263
|
+
sdkName: nonEmptyStringSchema.optional(),
|
|
1264
|
+
sdkVersion: nonEmptyStringSchema.optional(),
|
|
1265
|
+
package: sdkConfigV1PackageConfigSchema.optional(),
|
|
1266
|
+
output: sdkConfigV1OutputConfigSchema.optional()
|
|
1267
|
+
};
|
|
1268
|
+
var sdkConfigV1TargetSchema = z.discriminatedUnion("language", [
|
|
1269
|
+
z.strictObject({
|
|
1270
|
+
language: z.literal("typescript"),
|
|
1271
|
+
generation: typescriptGenerationConfigSchema.optional(),
|
|
1272
|
+
...targetOverrideShape
|
|
1273
|
+
}),
|
|
1274
|
+
z.strictObject({
|
|
1275
|
+
language: z.literal("python"),
|
|
1276
|
+
generation: pythonGenerationConfigSchema.optional(),
|
|
1277
|
+
...targetOverrideShape
|
|
1278
|
+
}),
|
|
1279
|
+
z.strictObject({
|
|
1280
|
+
language: z.literal("java"),
|
|
1281
|
+
generation: javaGenerationConfigSchema.optional(),
|
|
1282
|
+
...targetOverrideShape
|
|
1283
|
+
}),
|
|
1284
|
+
z.strictObject({
|
|
1285
|
+
language: z.literal("kotlin"),
|
|
1286
|
+
generation: kotlinGenerationConfigSchema.optional(),
|
|
1287
|
+
...targetOverrideShape
|
|
1288
|
+
}),
|
|
1289
|
+
z.strictObject({
|
|
1290
|
+
language: z.literal("go"),
|
|
1291
|
+
generation: goGenerationConfigSchema.optional(),
|
|
1292
|
+
...targetOverrideShape
|
|
1293
|
+
}),
|
|
1294
|
+
z.strictObject({
|
|
1295
|
+
language: z.literal("csharp"),
|
|
1296
|
+
generation: csharpGenerationConfigSchema.optional(),
|
|
1297
|
+
...targetOverrideShape
|
|
1298
|
+
}),
|
|
1299
|
+
z.strictObject({
|
|
1300
|
+
language: z.literal("php"),
|
|
1301
|
+
generation: phpGenerationConfigSchema.optional(),
|
|
1302
|
+
...targetOverrideShape
|
|
1303
|
+
}),
|
|
1304
|
+
z.strictObject({
|
|
1305
|
+
language: z.literal("ruby"),
|
|
1306
|
+
generation: rubyGenerationConfigSchema.optional(),
|
|
1307
|
+
...targetOverrideShape
|
|
1308
|
+
}),
|
|
1309
|
+
z.strictObject({
|
|
1310
|
+
language: z.literal("rust"),
|
|
1311
|
+
generation: rustGenerationConfigSchema.optional(),
|
|
1312
|
+
...targetOverrideShape
|
|
1313
|
+
}),
|
|
1314
|
+
z.strictObject({
|
|
1315
|
+
language: z.literal("swift"),
|
|
1316
|
+
generation: swiftGenerationConfigSchema.optional(),
|
|
1317
|
+
...targetOverrideShape
|
|
1318
|
+
}),
|
|
1319
|
+
z.strictObject({
|
|
1320
|
+
language: z.literal("cli"),
|
|
1321
|
+
generation: cliGenerationConfigSchema.optional(),
|
|
1322
|
+
...targetOverrideShape
|
|
1323
|
+
}),
|
|
1324
|
+
z.strictObject({
|
|
1325
|
+
language: z.literal("mcp"),
|
|
1326
|
+
generation: mcpGenerationConfigSchema.optional(),
|
|
1327
|
+
...targetOverrideShape
|
|
1328
|
+
}),
|
|
1329
|
+
z.strictObject({
|
|
1330
|
+
language: z.literal("terraform"),
|
|
1331
|
+
generation: terraformGenerationConfigSchema.optional(),
|
|
1332
|
+
...targetOverrideShape
|
|
1333
|
+
})
|
|
1334
|
+
]);
|
|
1335
|
+
|
|
1336
|
+
// src/sdk-config/v1/sdk-config-v1.ts
|
|
1337
|
+
var SDK_CONFIG_V1_SCHEMA_VERSION = "sdk-config/v1";
|
|
1338
|
+
var publishRegistryLanguages = {
|
|
1339
|
+
npm: ["typescript", "mcp"],
|
|
1340
|
+
pypi: ["python"],
|
|
1341
|
+
maven: ["java", "kotlin"],
|
|
1342
|
+
nuget: ["csharp"],
|
|
1343
|
+
rubygems: ["ruby"],
|
|
1344
|
+
crates: ["rust"],
|
|
1345
|
+
go: ["go"],
|
|
1346
|
+
composer: ["php"]
|
|
1347
|
+
};
|
|
1348
|
+
var packageNameRegistries = /* @__PURE__ */ new Set([
|
|
1349
|
+
"npm",
|
|
1350
|
+
"pypi",
|
|
1351
|
+
"nuget",
|
|
1352
|
+
"rubygems",
|
|
1353
|
+
"crates",
|
|
1354
|
+
"composer"
|
|
1355
|
+
]);
|
|
1356
|
+
function validatePublishingIdentity(packageConfig, registry, targetIndex, context) {
|
|
1357
|
+
const pathPrefix = ["targets", targetIndex, "package"];
|
|
1358
|
+
if (packageNameRegistries.has(registry) && !packageConfig.packageName) {
|
|
1359
|
+
context.addIssue({
|
|
1360
|
+
code: "custom",
|
|
1361
|
+
message: `packageName is required when publishing to "${registry}"`,
|
|
1362
|
+
path: [...pathPrefix, "packageName"]
|
|
1363
|
+
});
|
|
1364
|
+
}
|
|
1365
|
+
if (registry === "composer" && packageConfig.packageName) {
|
|
1366
|
+
const result = composerPackageNameSchema.safeParse(packageConfig.packageName);
|
|
1367
|
+
if (!result.success) {
|
|
1368
|
+
context.addIssue({
|
|
1369
|
+
code: "custom",
|
|
1370
|
+
message: result.error.issues[0]?.message ?? "Invalid Composer package name",
|
|
1371
|
+
path: [...pathPrefix, "packageName"]
|
|
1372
|
+
});
|
|
1373
|
+
}
|
|
1374
|
+
}
|
|
1375
|
+
if (registry === "go" && !packageConfig.modulePath) {
|
|
1376
|
+
context.addIssue({
|
|
1377
|
+
code: "custom",
|
|
1378
|
+
message: "modulePath is required when publishing a Go module",
|
|
1379
|
+
path: [...pathPrefix, "modulePath"]
|
|
1380
|
+
});
|
|
1381
|
+
}
|
|
1382
|
+
if (registry === "maven") {
|
|
1383
|
+
["groupId", "artifactId"].forEach((field) => {
|
|
1384
|
+
if (!packageConfig[field]) {
|
|
1385
|
+
context.addIssue({
|
|
1386
|
+
code: "custom",
|
|
1387
|
+
message: `${field} is required when publishing to Maven`,
|
|
1388
|
+
path: [...pathPrefix, field]
|
|
1389
|
+
});
|
|
1390
|
+
}
|
|
1391
|
+
});
|
|
1392
|
+
}
|
|
1393
|
+
}
|
|
1394
|
+
function validateTargetPublishing(target, targetIndex, globalPackage, globalOutput, context) {
|
|
1395
|
+
const output = target.output ?? globalOutput;
|
|
1396
|
+
if (!output.publish) {
|
|
1397
|
+
return;
|
|
1398
|
+
}
|
|
1399
|
+
const registry = output.publish.registry;
|
|
1400
|
+
if (!publishRegistryLanguages[registry].some((language) => language === target.language)) {
|
|
1401
|
+
context.addIssue({
|
|
1402
|
+
code: "custom",
|
|
1403
|
+
message: `registry "${registry}" is not supported for target language "${target.language}"`,
|
|
1404
|
+
path: ["targets", targetIndex, target.output ? "output" : "language"]
|
|
1405
|
+
});
|
|
1406
|
+
return;
|
|
1407
|
+
}
|
|
1408
|
+
validatePublishingIdentity(
|
|
1409
|
+
{ ...globalPackage, ...target.package },
|
|
1410
|
+
registry,
|
|
1411
|
+
targetIndex,
|
|
1412
|
+
context
|
|
1413
|
+
);
|
|
1414
|
+
}
|
|
1415
|
+
var sdkConfigV1Schema = z.strictObject({
|
|
1416
|
+
schemaVersion: z.literal(SDK_CONFIG_V1_SCHEMA_VERSION),
|
|
1417
|
+
sdkName: nonEmptyStringSchema,
|
|
1418
|
+
sdkVersion: nonEmptyStringSchema.default("1.0.0"),
|
|
1419
|
+
apiVersion: nonEmptyStringSchema.optional(),
|
|
1420
|
+
api: sdkConfigV1ApiConfigSchema,
|
|
1421
|
+
client: sdkConfigV1ClientConfigSchema,
|
|
1422
|
+
package: sdkConfigV1PackageConfigSchema,
|
|
1423
|
+
output: sdkConfigV1OutputConfigSchema,
|
|
1424
|
+
docs: sdkConfigV1DocsConfigSchema,
|
|
1425
|
+
generation: sdkConfigV1GenerationConfigSchema,
|
|
1426
|
+
targets: z.array(sdkConfigV1TargetSchema).min(1)
|
|
1427
|
+
}).superRefine(({ output, package: globalPackage, targets }, context) => {
|
|
1428
|
+
const configuredLanguages = /* @__PURE__ */ new Set();
|
|
1429
|
+
targets.forEach((target, targetIndex) => {
|
|
1430
|
+
if (configuredLanguages.has(target.language)) {
|
|
1431
|
+
context.addIssue({
|
|
1432
|
+
code: "custom",
|
|
1433
|
+
message: `target language "${target.language}" must be unique`,
|
|
1434
|
+
path: ["targets", targetIndex, "language"]
|
|
1435
|
+
});
|
|
1436
|
+
}
|
|
1437
|
+
configuredLanguages.add(target.language);
|
|
1438
|
+
validateTargetPublishing(target, targetIndex, globalPackage, output, context);
|
|
1439
|
+
});
|
|
426
1440
|
});
|
|
427
|
-
|
|
428
|
-
|
|
429
|
-
|
|
430
|
-
|
|
431
|
-
|
|
432
|
-
|
|
433
|
-
|
|
434
|
-
|
|
435
|
-
|
|
436
|
-
|
|
437
|
-
|
|
438
|
-
|
|
439
|
-
|
|
440
|
-
|
|
441
|
-
|
|
442
|
-
|
|
443
|
-
|
|
444
|
-
|
|
445
|
-
|
|
446
|
-
|
|
447
|
-
|
|
448
|
-
|
|
449
|
-
|
|
450
|
-
|
|
451
|
-
|
|
452
|
-
|
|
453
|
-
|
|
454
|
-
|
|
1441
|
+
function parseSdkConfigV1(value) {
|
|
1442
|
+
return sdkConfigV1Schema.parse(value);
|
|
1443
|
+
}
|
|
1444
|
+
|
|
1445
|
+
// src/sdk-config/v1/fern-config-mapper.ts
|
|
1446
|
+
var generatorLanguages = {
|
|
1447
|
+
"fernapi/fern-typescript": "typescript",
|
|
1448
|
+
"fernapi/fern-typescript-sdk": "typescript",
|
|
1449
|
+
"fernapi/fern-typescript-node-sdk": "typescript",
|
|
1450
|
+
"fernapi/fern-typescript-browser-sdk": "typescript",
|
|
1451
|
+
"fernapi/fern-python-sdk": "python",
|
|
1452
|
+
"fernapi/fern-java-sdk": "java",
|
|
1453
|
+
"fernapi/fern-kotlin-sdk": "kotlin",
|
|
1454
|
+
"fernapi/fern-go-sdk": "go",
|
|
1455
|
+
"fernapi/fern-csharp-sdk": "csharp",
|
|
1456
|
+
"fernapi/fern-php-sdk": "php",
|
|
1457
|
+
"fernapi/fern-ruby-sdk": "ruby",
|
|
1458
|
+
"fernapi/fern-ruby-sdk-v2": "ruby",
|
|
1459
|
+
"fernapi/fern-rust-sdk": "rust",
|
|
1460
|
+
"fernapi/fern-swift-sdk": "swift",
|
|
1461
|
+
"fernapi/fern-cli": "cli",
|
|
1462
|
+
"fernapi/fern-cli-generator": "cli",
|
|
1463
|
+
"fernapi/fern-mcp-server": "mcp"
|
|
1464
|
+
};
|
|
1465
|
+
function mapFernConfigToSdkConfigV1(input) {
|
|
1466
|
+
if (input.group.generators.length === 0) {
|
|
1467
|
+
fail(
|
|
1468
|
+
"FERN_GENERATORS_REQUIRED",
|
|
1469
|
+
["group", "generators"],
|
|
1470
|
+
"Fern generator group must contain at least one generator",
|
|
1471
|
+
"Select a Fern generator group containing at least one SDK generator."
|
|
1472
|
+
);
|
|
1473
|
+
}
|
|
1474
|
+
const mapped = input.group.generators.map((generator, index) => {
|
|
1475
|
+
const language = resolveLanguage(generator, index);
|
|
1476
|
+
const invocation = mapInvocation(generator, language, index);
|
|
1477
|
+
const outputMapping = generator.output ? { output: generator.output, unsupportedFields: [] } : mapOutput(generator, language, index);
|
|
1478
|
+
return {
|
|
1479
|
+
generator,
|
|
1480
|
+
language,
|
|
1481
|
+
invocation,
|
|
1482
|
+
...outputMapping
|
|
1483
|
+
};
|
|
1484
|
+
});
|
|
1485
|
+
requireUniqueLanguages(mapped.map(({ language }) => language));
|
|
1486
|
+
const client = requireSharedBlock(
|
|
1487
|
+
mapped.map(({ invocation }) => invocation.client),
|
|
1488
|
+
"client",
|
|
1489
|
+
(value) => sdkConfigV1ClientConfigSchema.parse(value)
|
|
1490
|
+
);
|
|
1491
|
+
const docs = requireSharedBlock(
|
|
1492
|
+
mapped.map(({ invocation }) => invocation.docs),
|
|
1493
|
+
"docs",
|
|
1494
|
+
(value) => sdkConfigV1DocsConfigSchema.parse(value)
|
|
1495
|
+
);
|
|
1496
|
+
const generation = requireSharedBlock(
|
|
1497
|
+
mapped.map(({ invocation }) => invocation.generation),
|
|
1498
|
+
"generation",
|
|
1499
|
+
(value) => sdkConfigV1GenerationConfigSchema.parse(value)
|
|
1500
|
+
);
|
|
1501
|
+
const api = { ...input.api ?? {} };
|
|
1502
|
+
delete api.audiences;
|
|
1503
|
+
if (input.group.audiences.type === "select") {
|
|
1504
|
+
api.audiences = [...input.group.audiences.audiences];
|
|
1505
|
+
}
|
|
1506
|
+
const targets = mapped.map(
|
|
1507
|
+
({ generator, invocation, language, output, package: outputPackage }, index) => {
|
|
1508
|
+
const target = {
|
|
1509
|
+
language,
|
|
1510
|
+
output,
|
|
1511
|
+
...optional("sdkName", generator.sdkName),
|
|
1512
|
+
...optional("sdkVersion", generator.sdkVersion)
|
|
1513
|
+
};
|
|
1514
|
+
if (Object.keys(invocation.package).length > 0 || outputPackage || generator.package) {
|
|
1515
|
+
target.package = { ...invocation.package, ...outputPackage, ...generator.package };
|
|
1516
|
+
}
|
|
1517
|
+
if (Object.keys(invocation.targetGeneration).length > 0) {
|
|
1518
|
+
target.generation = invocation.targetGeneration;
|
|
1519
|
+
}
|
|
1520
|
+
if (generator.version) {
|
|
1521
|
+
if (exactSemverSchema.safeParse(generator.version).success) {
|
|
1522
|
+
target.generatorVersion = generator.version;
|
|
1523
|
+
} else {
|
|
1524
|
+
invocation.unsupportedFields.push({
|
|
1525
|
+
code: "FERN_GENERATOR_VERSION_NOT_EXACT",
|
|
1526
|
+
severity: "warning",
|
|
1527
|
+
path: ["group", "generators", index, "version"],
|
|
1528
|
+
reason: "SDK Config requires an exact generator semantic version",
|
|
1529
|
+
sdkConfigPath: ["targets", index, "generatorVersion"],
|
|
1530
|
+
suggestedAction: "Resolve the Fern generator tag to an exact semantic version and set target.generatorVersion manually, or leave it omitted."
|
|
1531
|
+
});
|
|
1532
|
+
}
|
|
1533
|
+
}
|
|
1534
|
+
return target;
|
|
1535
|
+
}
|
|
1536
|
+
);
|
|
1537
|
+
const parsed = sdkConfigV1Schema.safeParse({
|
|
1538
|
+
schemaVersion: "sdk-config/v1",
|
|
1539
|
+
sdkName: input.apiName,
|
|
1540
|
+
...optional("sdkVersion", input.sdkVersion),
|
|
1541
|
+
...optional("apiVersion", input.apiVersion),
|
|
1542
|
+
api,
|
|
1543
|
+
client,
|
|
1544
|
+
package: {},
|
|
1545
|
+
output: mapped[0].output,
|
|
1546
|
+
docs,
|
|
1547
|
+
generation,
|
|
1548
|
+
targets
|
|
1549
|
+
});
|
|
1550
|
+
if (!parsed.success) {
|
|
1551
|
+
throw new FernConfigMappingError(
|
|
1552
|
+
parsed.error.issues.map((issue) => {
|
|
1553
|
+
const path = issue.path.map(
|
|
1554
|
+
(part) => typeof part === "symbol" ? part.description ?? part.toString() : part
|
|
1555
|
+
);
|
|
1556
|
+
return {
|
|
1557
|
+
code: "SDK_CONFIG_VALIDATION_FAILED",
|
|
1558
|
+
severity: "error",
|
|
1559
|
+
path: ["mappedSdkConfig", ...path],
|
|
1560
|
+
reason: issue.message,
|
|
1561
|
+
sdkConfigPath: path,
|
|
1562
|
+
suggestedAction: `Set ${path.join(".")} manually to a valid SDK Config v1 value.`
|
|
1563
|
+
};
|
|
1564
|
+
})
|
|
1565
|
+
);
|
|
1566
|
+
}
|
|
1567
|
+
return {
|
|
1568
|
+
sdkConfig: parsed.data,
|
|
1569
|
+
unsupportedFields: mapped.flatMap(({ invocation, unsupportedFields }) => [
|
|
1570
|
+
...invocation.unsupportedFields,
|
|
1571
|
+
...unsupportedFields
|
|
1572
|
+
])
|
|
1573
|
+
};
|
|
1574
|
+
}
|
|
1575
|
+
function resolveLanguage(generator, index) {
|
|
1576
|
+
const language = generator.sdkLanguage ?? generatorLanguages[generator.name];
|
|
1577
|
+
if (!language || !isFernLanguage(language)) {
|
|
1578
|
+
fail(
|
|
1579
|
+
"FERN_SDK_LANGUAGE_REQUIRED",
|
|
1580
|
+
["group", "generators", index, "name"],
|
|
1581
|
+
`Cannot determine an SDK language for Fern generator ${generator.name}`,
|
|
1582
|
+
"Set sdkLanguage explicitly if this custom generator produces one of the SDK Config v1 target languages.",
|
|
1583
|
+
["targets", index, "language"]
|
|
1584
|
+
);
|
|
1585
|
+
}
|
|
1586
|
+
return language;
|
|
1587
|
+
}
|
|
1588
|
+
function isFernLanguage(value) {
|
|
1589
|
+
return [
|
|
1590
|
+
"typescript",
|
|
1591
|
+
"python",
|
|
1592
|
+
"java",
|
|
1593
|
+
"kotlin",
|
|
1594
|
+
"go",
|
|
1595
|
+
"csharp",
|
|
1596
|
+
"php",
|
|
1597
|
+
"ruby",
|
|
1598
|
+
"rust",
|
|
1599
|
+
"swift",
|
|
1600
|
+
"cli",
|
|
1601
|
+
"mcp",
|
|
1602
|
+
"terraform"
|
|
1603
|
+
].includes(value);
|
|
1604
|
+
}
|
|
1605
|
+
function requireUniqueLanguages(languages) {
|
|
1606
|
+
const seen = /* @__PURE__ */ new Set();
|
|
1607
|
+
for (const language of languages) {
|
|
1608
|
+
if (seen.has(language)) {
|
|
1609
|
+
fail(
|
|
1610
|
+
"FERN_DUPLICATE_TARGET_LANGUAGE",
|
|
1611
|
+
["group", "generators"],
|
|
1612
|
+
`SDK Config v1 cannot represent multiple Fern generators for language "${language}"`,
|
|
1613
|
+
"Create a separate SDK Config document for each generator that targets the same language.",
|
|
1614
|
+
["targets"]
|
|
1615
|
+
);
|
|
1616
|
+
}
|
|
1617
|
+
seen.add(language);
|
|
1618
|
+
}
|
|
1619
|
+
}
|
|
1620
|
+
function requireSharedBlock(values, name, normalize) {
|
|
1621
|
+
const first = normalize(values[0]);
|
|
1622
|
+
const serialized = stableJson(first);
|
|
1623
|
+
if (values.some((value) => stableJson(normalize(value)) !== serialized)) {
|
|
1624
|
+
fail(
|
|
1625
|
+
"FERN_TARGET_SPECIFIC_SHARED_CONFIG",
|
|
1626
|
+
["group", "generators"],
|
|
1627
|
+
`SDK Config v1 cannot represent target-specific Fern ${name} configuration`,
|
|
1628
|
+
`Choose one shared ${name} configuration manually or create separate SDK Config documents for the differing targets.`,
|
|
1629
|
+
[name]
|
|
1630
|
+
);
|
|
1631
|
+
}
|
|
1632
|
+
return first;
|
|
1633
|
+
}
|
|
1634
|
+
function mapInvocation(generator, language, index) {
|
|
1635
|
+
const prefix = ["group", "generators", index];
|
|
1636
|
+
const state = { consumedPaths: /* @__PURE__ */ new Set() };
|
|
1637
|
+
const config = isObject(generator.config) ? generator.config : {};
|
|
1638
|
+
const client = {};
|
|
1639
|
+
const generation = {};
|
|
1640
|
+
const packageConfig = {};
|
|
1641
|
+
mapCommonConfig(config, state, client, generation, packageConfig, [...prefix, "config"]);
|
|
1642
|
+
const targetGeneration = mapLanguageConfig(language, config, state, packageConfig, [
|
|
1643
|
+
...prefix,
|
|
1644
|
+
"config"
|
|
1645
|
+
]);
|
|
1646
|
+
mapPublishMetadata(generator.publishMetadata, packageConfig);
|
|
1647
|
+
if (language === "go" && generator.smartCasing !== void 0) {
|
|
1648
|
+
targetGeneration.smartCasing = generator.smartCasing;
|
|
1649
|
+
}
|
|
1650
|
+
if (generator.keywords?.length) {
|
|
1651
|
+
generation.reservedKeywords = [...generator.keywords];
|
|
1652
|
+
}
|
|
1653
|
+
const settings = isObject(generator.settings) ? generator.settings : void 0;
|
|
1654
|
+
if (settings) {
|
|
1655
|
+
const inlinePathParameters = takeBoolean(settings, ["inlinePathParameters"], state, [
|
|
1656
|
+
...prefix,
|
|
1657
|
+
"settings"
|
|
1658
|
+
]);
|
|
1659
|
+
if (inlinePathParameters !== void 0 && client.pathParameterStyle === void 0) {
|
|
1660
|
+
client.pathParameterStyle = inlinePathParameters ? "inline" : "wrapped";
|
|
1661
|
+
}
|
|
1662
|
+
}
|
|
1663
|
+
const docs = mapReadme(generator.readme, state, [...prefix, "readme"]);
|
|
1664
|
+
const unsupportedFields = [
|
|
1665
|
+
...collectUnsupported(config, [...prefix, "config"], state),
|
|
1666
|
+
...settings ? collectUnsupported(settings, [...prefix, "settings"], state) : [],
|
|
1667
|
+
...isObject(generator.readme) ? collectUnsupported(generator.readme, [...prefix, "readme"], state) : [],
|
|
1668
|
+
...unsupportedResolvedFields(generator, index, language)
|
|
1669
|
+
];
|
|
1670
|
+
return { client, docs, generation, package: packageConfig, targetGeneration, unsupportedFields };
|
|
1671
|
+
}
|
|
1672
|
+
function unsupportedResolvedFields(generator, index, language) {
|
|
1673
|
+
const values = [
|
|
1674
|
+
["automation", isDefaultAutomation(generator.automation) ? void 0 : generator.automation],
|
|
1675
|
+
["containerImage", generator.containerImage],
|
|
1676
|
+
["irVersionOverride", generator.irVersionOverride],
|
|
1677
|
+
["idempotencyKeyGenerationConfig", generator.idempotencyKeyGenerationConfig],
|
|
1678
|
+
["absolutePathToLocalSnippets", generator.absolutePathToLocalSnippets],
|
|
1679
|
+
[
|
|
1680
|
+
"smartCasingDigitWordBoundary",
|
|
1681
|
+
generator.smartCasingDigitWordBoundary === false ? void 0 : generator.smartCasingDigitWordBoundary
|
|
1682
|
+
],
|
|
1683
|
+
[
|
|
1684
|
+
"disableExamples",
|
|
1685
|
+
generator.disableExamples === false ? void 0 : generator.disableExamples
|
|
1686
|
+
],
|
|
1687
|
+
["apiOverride", generator.apiOverride],
|
|
1688
|
+
...language === "go" || generator.smartCasing === true ? [] : [["smartCasing", generator.smartCasing]]
|
|
1689
|
+
];
|
|
1690
|
+
return values.flatMap(([field, value]) => {
|
|
1691
|
+
if (value === void 0) return [];
|
|
1692
|
+
const guidance = resolvedFieldGuidance(field);
|
|
1693
|
+
return [
|
|
1694
|
+
{
|
|
1695
|
+
code: "FERN_RESOLVED_FIELD_UNSUPPORTED",
|
|
1696
|
+
severity: "warning",
|
|
1697
|
+
path: ["group", "generators", index, field],
|
|
1698
|
+
reason: "Resolved Fern field is not represented by SDK Config v1",
|
|
1699
|
+
...optional("sdkConfigPath", guidance.sdkConfigPath),
|
|
1700
|
+
suggestedAction: guidance.suggestedAction
|
|
1701
|
+
}
|
|
1702
|
+
];
|
|
1703
|
+
});
|
|
1704
|
+
}
|
|
1705
|
+
function resolvedFieldGuidance(field) {
|
|
1706
|
+
if (field === "absolutePathToLocalSnippets") {
|
|
1707
|
+
return {
|
|
1708
|
+
sdkConfigPath: ["docs", "snippets", "outputPath"],
|
|
1709
|
+
suggestedAction: "Choose a portable relative snippet path and set docs.snippets.outputPath manually."
|
|
1710
|
+
};
|
|
1711
|
+
}
|
|
1712
|
+
if (field === "idempotencyKeyGenerationConfig") {
|
|
1713
|
+
return {
|
|
1714
|
+
suggestedAction: "Preserve this orchestration setting outside SDK Config; public v1 has no idempotency-generation field."
|
|
1715
|
+
};
|
|
1716
|
+
}
|
|
1717
|
+
return {
|
|
1718
|
+
suggestedAction: "Review this Fern setting and preserve it outside SDK Config, or set an equivalent SDK Config field manually if one is introduced."
|
|
1719
|
+
};
|
|
1720
|
+
}
|
|
1721
|
+
function isDefaultAutomation(value) {
|
|
1722
|
+
return isObject(value) && value.generate === true && value.upgrade === true && value.preview === true && value.verify === true;
|
|
1723
|
+
}
|
|
1724
|
+
function mapCommonConfig(config, state, client, generation, packageConfig, basePath) {
|
|
1725
|
+
const inlinePath = takeBoolean(config, ["inlinePathParameters"], state, basePath);
|
|
1726
|
+
const inlineFile = takeBoolean(config, ["inlineFileProperties"], state, basePath);
|
|
1727
|
+
const inlineRequest = takeBoolean(config, ["inlineRequestParams"], state, basePath);
|
|
1728
|
+
if (inlinePath !== void 0) client.pathParameterStyle = inlinePath ? "inline" : "wrapped";
|
|
1729
|
+
if (inlineFile !== void 0) client.filePropertyStyle = inlineFile ? "inline" : "wrapped";
|
|
1730
|
+
if (inlineRequest !== void 0)
|
|
1731
|
+
client.requestParameterStyle = inlineRequest ? "inline" : "wrapped";
|
|
1732
|
+
const timeoutMs = takeTimeoutMs(config, state, basePath);
|
|
1733
|
+
if (timeoutMs !== void 0) client.timeoutMs = timeoutMs;
|
|
1734
|
+
const skipValidation = takeBoolean(
|
|
1735
|
+
config,
|
|
1736
|
+
["skipResponseValidation", "skipValidation"],
|
|
1737
|
+
state,
|
|
1738
|
+
basePath
|
|
1739
|
+
);
|
|
1740
|
+
if (skipValidation !== void 0) client.responseValidation = !skipValidation;
|
|
1741
|
+
const useDefaults = takeBoolean(config, ["useDefaultRequestParameterValues"], state, basePath);
|
|
1742
|
+
if (useDefaults !== void 0) client.useDefaultRequestParameterValues = useDefaults;
|
|
1743
|
+
const respectOptionalBody = takeBoolean(config, ["respectOptionalRequestBody"], state, basePath);
|
|
1744
|
+
if (respectOptionalBody !== void 0) client.respectOptionalRequestBody = respectOptionalBody;
|
|
1745
|
+
const maxRetries = takeNumber(config, ["maxRetries"], state, basePath);
|
|
1746
|
+
const statusCodeProfile = takeEnum(
|
|
1747
|
+
config,
|
|
1748
|
+
["retryStatusCodes"],
|
|
1749
|
+
["legacy", "recommended"],
|
|
1750
|
+
state,
|
|
1751
|
+
basePath
|
|
1752
|
+
);
|
|
1753
|
+
if (maxRetries !== void 0 || statusCodeProfile !== void 0) {
|
|
1754
|
+
client.retry = {
|
|
1755
|
+
...maxRetries === void 0 ? {} : { maxAttempts: maxRetries + 1 },
|
|
1756
|
+
...optional("statusCodeProfile", statusCodeProfile)
|
|
1757
|
+
};
|
|
1758
|
+
}
|
|
1759
|
+
const naming = compact({
|
|
1760
|
+
pagerName: takeString(
|
|
1761
|
+
config,
|
|
1762
|
+
["customPagerName", "customPagerClassname", "customPagerClassName"],
|
|
1763
|
+
state,
|
|
1764
|
+
basePath
|
|
1765
|
+
),
|
|
1766
|
+
clientName: takeString(config, ["clientName", "clientClassName"], state, basePath),
|
|
1767
|
+
exportedClientName: takeString(
|
|
1768
|
+
config,
|
|
1769
|
+
["exportedClientName", "exportedClientClassName"],
|
|
1770
|
+
state,
|
|
1771
|
+
basePath
|
|
1772
|
+
),
|
|
1773
|
+
environmentTypeName: takeString(
|
|
1774
|
+
config,
|
|
1775
|
+
["environmentClassName", "environmentEnumName"],
|
|
1776
|
+
state,
|
|
1777
|
+
basePath
|
|
1778
|
+
),
|
|
1779
|
+
apiErrorName: takeString(config, ["baseApiExceptionClassName"], state, basePath),
|
|
1780
|
+
baseErrorName: takeString(config, ["baseExceptionClassName"], state, basePath)
|
|
1781
|
+
});
|
|
1782
|
+
if (Object.keys(naming).length) generation.naming = naming;
|
|
1783
|
+
const wireTests = takeBoolean(config, ["enableWireTests", "generateWireTests"], state, basePath);
|
|
1784
|
+
if (wireTests !== void 0) generation.wireTests = { enabled: wireTests };
|
|
1785
|
+
const webSockets = takeBoolean(
|
|
1786
|
+
config,
|
|
1787
|
+
["generateWebSocketClients", "shouldGenerateWebsocketClients", "enableWebsockets"],
|
|
1788
|
+
state,
|
|
1789
|
+
basePath
|
|
1790
|
+
);
|
|
1791
|
+
if (webSockets !== void 0) generation.webSockets = webSockets;
|
|
1792
|
+
const inlineTypes = takeBoolean(config, ["enableInlineTypes"], state, basePath);
|
|
1793
|
+
const omitUndefined = takeBoolean(config, ["omitUndefined"], state, basePath);
|
|
1794
|
+
const forwardEnums = takeBoolean(config, ["enableForwardCompatibleEnums"], state, basePath);
|
|
1795
|
+
const serialization = compact({
|
|
1796
|
+
inlineTypes,
|
|
1797
|
+
omitUndefined,
|
|
1798
|
+
enumRepresentation: forwardEnums === void 0 ? void 0 : forwardEnums ? "forward-compatible-enum" : "language-default"
|
|
1799
|
+
});
|
|
1800
|
+
if (Object.keys(serialization).length) generation.serialization = serialization;
|
|
1801
|
+
const namespace = takeString(config, ["namespace", "packagePrefix"], state, basePath);
|
|
1802
|
+
if (namespace !== void 0) packageConfig.namespace = namespace;
|
|
1803
|
+
const packagePath = takeString(config, ["packagePath"], state, basePath);
|
|
1804
|
+
if (packagePath !== void 0) generation.layout = { packagePath };
|
|
1805
|
+
mapDependencies(config, state, packageConfig, basePath);
|
|
1806
|
+
}
|
|
1807
|
+
function mapLanguageConfig(language, config, state, packageConfig, basePath) {
|
|
1808
|
+
switch (language) {
|
|
1809
|
+
case "typescript":
|
|
1810
|
+
return mapTypescript(config, state, packageConfig, basePath);
|
|
1811
|
+
case "mcp":
|
|
1812
|
+
return {
|
|
1813
|
+
...mapTypescript(config, state, packageConfig, basePath),
|
|
1814
|
+
...mapMcp(config, state, basePath)
|
|
1815
|
+
};
|
|
1816
|
+
case "python":
|
|
1817
|
+
return mapPython(config, state, packageConfig, basePath);
|
|
1818
|
+
case "java":
|
|
1819
|
+
case "kotlin":
|
|
1820
|
+
return mapJvm(language, config, state, packageConfig, basePath);
|
|
1821
|
+
case "go":
|
|
1822
|
+
return mapGo(config, state, packageConfig, basePath);
|
|
1823
|
+
case "csharp":
|
|
1824
|
+
return mapCsharp(config, state, packageConfig, basePath);
|
|
1825
|
+
case "php":
|
|
1826
|
+
return mapPhp(config, state, packageConfig, basePath);
|
|
1827
|
+
case "ruby":
|
|
1828
|
+
return mapRuby(config, state, packageConfig, basePath);
|
|
1829
|
+
case "rust":
|
|
1830
|
+
return mapRust(config, state, packageConfig, basePath);
|
|
1831
|
+
case "swift":
|
|
1832
|
+
return compact({ moduleName: takeString(config, ["moduleName"], state, basePath) });
|
|
1833
|
+
case "cli":
|
|
1834
|
+
return mapCli(config, state, packageConfig, basePath);
|
|
1835
|
+
case "terraform":
|
|
1836
|
+
return mapTerraform(config, state, packageConfig, basePath);
|
|
1837
|
+
}
|
|
1838
|
+
}
|
|
1839
|
+
function mapTypescript(config, state, packageConfig, basePath) {
|
|
1840
|
+
const packageJson = takeObject(config, ["packageJson"], state, basePath);
|
|
1841
|
+
const packageName = packageJson ? takeString(packageJson.value, ["name"], state, packageJson.path) : void 0;
|
|
1842
|
+
if (packageName !== void 0) packageConfig.packageName = packageName;
|
|
1843
|
+
const serdeLayer = takeBoolean(config, ["serdeLayer"], state, basePath);
|
|
1844
|
+
const noSerdeLayer = takeBoolean(config, ["noSerdeLayer"], state, basePath);
|
|
1845
|
+
return compact({
|
|
1846
|
+
typescriptVersion: takeString(config, ["typescriptVersion"], state, basePath),
|
|
1847
|
+
zodVersion: takeString(config, ["zodVersion"], state, basePath),
|
|
1848
|
+
packageManager: takeEnum(config, ["packageManager"], ["pnpm", "yarn"], state, basePath),
|
|
1849
|
+
testFramework: takeEnum(config, ["testFramework"], ["jest", "vitest"], state, basePath),
|
|
1850
|
+
bundle: takeBoolean(config, ["bundle"], state, basePath),
|
|
1851
|
+
exportClassDefault: takeBoolean(config, ["exportClassDefault"], state, basePath),
|
|
1852
|
+
allowCustomFetcher: takeBoolean(config, ["allowCustomFetcher"], state, basePath),
|
|
1853
|
+
useBrandedStringAliases: takeBoolean(config, ["useBrandedStringAliases"], state, basePath),
|
|
1854
|
+
useLegacyExports: takeBoolean(config, ["useLegacyExports"], state, basePath),
|
|
1855
|
+
useBigInt: takeBoolean(config, ["useBigInt"], state, basePath),
|
|
1856
|
+
serdeLayer: serdeLayer ?? (noSerdeLayer === void 0 ? void 0 : !noSerdeLayer)
|
|
1857
|
+
});
|
|
1858
|
+
}
|
|
1859
|
+
function mapPython(config, state, packageConfig, basePath) {
|
|
1860
|
+
const moduleName = takeString(config, ["packageName"], state, basePath);
|
|
1861
|
+
const packageName = takeString(config, ["pypiPackageName"], state, basePath);
|
|
1862
|
+
if (moduleName !== void 0) packageConfig.moduleName = moduleName;
|
|
1863
|
+
if (packageName !== void 0) packageConfig.packageName = packageName;
|
|
1864
|
+
return compact({
|
|
1865
|
+
pythonVersion: takeString(config, ["pythonVersion", "pyprojectPythonVersion"], state, basePath),
|
|
1866
|
+
pydanticVersion: takeString(config, ["pydanticVersion"], state, basePath),
|
|
1867
|
+
alwaysInitializeOptionals: takeBoolean(config, ["alwaysInitializeOptionals"], state, basePath),
|
|
1868
|
+
useTypedDictRequests: takeBoolean(config, ["useTypedDictRequests"], state, basePath)
|
|
1869
|
+
});
|
|
1870
|
+
}
|
|
1871
|
+
function mapJvm(language, config, state, packageConfig, basePath) {
|
|
1872
|
+
const namespace = takeString(config, ["packageName", "packagePrefix"], state, basePath);
|
|
1873
|
+
const groupId = takeString(config, ["group", "groupId"], state, basePath);
|
|
1874
|
+
const artifactId = takeString(config, ["artifact", "artifactId"], state, basePath);
|
|
1875
|
+
if (namespace !== void 0) packageConfig.namespace = namespace;
|
|
1876
|
+
if (groupId !== void 0) packageConfig.groupId = groupId;
|
|
1877
|
+
if (artifactId !== void 0) packageConfig.artifactId = artifactId;
|
|
1878
|
+
return compact({
|
|
1879
|
+
packageLayout: takeEnum(config, ["packageLayout"], ["flat", "nested"], state, basePath),
|
|
1880
|
+
useLocalDateForDates: takeBoolean(config, ["useLocalDateForDates"], state, basePath),
|
|
1881
|
+
collapseOptionalNullable: takeBoolean(config, ["collapseOptionalNullable"], state, basePath),
|
|
1882
|
+
gradleDistributionUrl: takeString(config, ["gradleDistributionUrl"], state, basePath),
|
|
1883
|
+
gradlePluginManagement: takeString(config, ["gradlePluginManagement"], state, basePath),
|
|
1884
|
+
gradleCentralDependencyManagement: takeBoolean(
|
|
1885
|
+
config,
|
|
1886
|
+
["gradleCentralDependencyManagement"],
|
|
1887
|
+
state,
|
|
1888
|
+
basePath
|
|
1889
|
+
),
|
|
1890
|
+
asyncStyle: takeEnum(
|
|
1891
|
+
config,
|
|
1892
|
+
["asyncStyle"],
|
|
1893
|
+
["dedicated-client", "twin-methods"],
|
|
1894
|
+
state,
|
|
1895
|
+
basePath
|
|
1896
|
+
),
|
|
1897
|
+
...language === "java" ? {
|
|
1898
|
+
includeKotlinSnippets: takeBoolean(config, ["includeKotlinSnippets"], state, basePath)
|
|
1899
|
+
} : {}
|
|
1900
|
+
});
|
|
1901
|
+
}
|
|
1902
|
+
function mapGo(config, state, packageConfig, basePath) {
|
|
1903
|
+
const module = takeObject(config, ["module"], state, basePath);
|
|
1904
|
+
const modulePath = module ? takeGoModulePath(module.value, ["path"], state, module.path) : void 0;
|
|
1905
|
+
const packageName = takeString(config, ["packageName"], state, basePath);
|
|
1906
|
+
if (modulePath !== void 0) packageConfig.modulePath = modulePath;
|
|
1907
|
+
if (packageName !== void 0) packageConfig.packageName = packageName;
|
|
1908
|
+
return compact({
|
|
1909
|
+
legacyComplexModels: takeBoolean(config, ["legacyComplexModels"], state, basePath),
|
|
1910
|
+
unionVersion: takeEnum(config, ["union"], ["v0", "v1"], state, basePath),
|
|
1911
|
+
includeLegacyClientOptions: takeBoolean(
|
|
1912
|
+
config,
|
|
1913
|
+
["includeLegacyClientOptions"],
|
|
1914
|
+
state,
|
|
1915
|
+
basePath
|
|
1916
|
+
),
|
|
1917
|
+
clientConstructorName: takeString(config, ["clientConstructorName"], state, basePath)
|
|
1918
|
+
});
|
|
1919
|
+
}
|
|
1920
|
+
function mapCsharp(config, state, packageConfig, basePath) {
|
|
1921
|
+
const packageName = takeString(config, ["packageId"], state, basePath);
|
|
1922
|
+
if (packageName !== void 0) packageConfig.packageName = packageName;
|
|
1923
|
+
return compact({
|
|
1924
|
+
useOptionalWrapper: takeBoolean(config, ["useOptionalWrapper"], state, basePath),
|
|
1925
|
+
simplifyObjectDictionaries: takeBoolean(
|
|
1926
|
+
config,
|
|
1927
|
+
["simplifyObjectDictionaries"],
|
|
1928
|
+
state,
|
|
1929
|
+
basePath
|
|
1930
|
+
),
|
|
1931
|
+
explicitNamespaces: takeBoolean(config, ["explicitNamespaces"], state, basePath),
|
|
1932
|
+
rootNamespaceForCoreClasses: takeBoolean(
|
|
1933
|
+
config,
|
|
1934
|
+
["rootNamespaceForCoreClasses"],
|
|
1935
|
+
state,
|
|
1936
|
+
basePath
|
|
1937
|
+
),
|
|
1938
|
+
includeExceptionHandler: takeBoolean(config, ["includeExceptionHandler"], state, basePath),
|
|
1939
|
+
experimentalExplicitNullableOptional: takeBoolean(
|
|
1940
|
+
config,
|
|
1941
|
+
["experimentalExplicitNullableOptional"],
|
|
1942
|
+
state,
|
|
1943
|
+
basePath
|
|
1944
|
+
)
|
|
1945
|
+
});
|
|
1946
|
+
}
|
|
1947
|
+
function mapPhp(config, state, packageConfig, basePath) {
|
|
1948
|
+
const packageName = takeString(config, ["packageName"], state, basePath);
|
|
1949
|
+
if (packageName !== void 0) packageConfig.packageName = packageName;
|
|
1950
|
+
return compact({
|
|
1951
|
+
propertyAccess: takeEnum(config, ["propertyAccess"], ["public", "private"], state, basePath),
|
|
1952
|
+
generateClientInterfaces: takeBoolean(config, ["generateClientInterfaces"], state, basePath)
|
|
1953
|
+
});
|
|
1954
|
+
}
|
|
1955
|
+
function mapRuby(config, state, packageConfig, basePath) {
|
|
1956
|
+
const moduleName = takeString(config, ["moduleName"], state, basePath);
|
|
1957
|
+
if (moduleName !== void 0) packageConfig.moduleName = moduleName;
|
|
1958
|
+
return compact({ requirePaths: takeStringArray(config, ["requirePaths"], state, basePath) });
|
|
1959
|
+
}
|
|
1960
|
+
function mapRust(config, state, packageConfig, basePath) {
|
|
1961
|
+
const packageName = takeString(config, ["crateName"], state, basePath);
|
|
1962
|
+
const repository = takeString(config, ["packageRepository"], state, basePath);
|
|
1963
|
+
const description = takeString(config, ["packageDescription"], state, basePath);
|
|
1964
|
+
const documentationUrl = takeString(config, ["packageDocumentation"], state, basePath);
|
|
1965
|
+
Object.assign(packageConfig, compact({ packageName, repository, description, documentationUrl }));
|
|
1966
|
+
return compact({
|
|
1967
|
+
dateTimeType: takeEnum(config, ["dateTimeType"], ["offset", "utc"], state, basePath),
|
|
1968
|
+
capitalizeInitialisms: takeBoolean(config, ["capitalizeInitialisms"], state, basePath),
|
|
1969
|
+
features: takeStringArrayRecord(config, ["features"], state, basePath),
|
|
1970
|
+
defaultFeatures: takeStringArray(config, ["defaultFeatures"], state, basePath)
|
|
1971
|
+
});
|
|
1972
|
+
}
|
|
1973
|
+
function mapCli(config, state, packageConfig, basePath) {
|
|
1974
|
+
const identity = takeObject(config, ["packageIdentity"], state, basePath);
|
|
1975
|
+
if (identity) {
|
|
1976
|
+
Object.assign(
|
|
1977
|
+
packageConfig,
|
|
1978
|
+
compact({
|
|
1979
|
+
packageName: takeString(identity.value, ["name"], state, identity.path),
|
|
1980
|
+
repository: takeString(identity.value, ["repository"], state, identity.path),
|
|
1981
|
+
description: takeString(identity.value, ["description"], state, identity.path)
|
|
1982
|
+
})
|
|
1983
|
+
);
|
|
1984
|
+
}
|
|
1985
|
+
return compact({
|
|
1986
|
+
paginationParameters: takeStringArray(config, ["paginationParameters"], state, basePath),
|
|
1987
|
+
skills: takeBoolean(config, ["skills"], state, basePath)
|
|
1988
|
+
});
|
|
1989
|
+
}
|
|
1990
|
+
function mapTerraform(config, state, packageConfig, basePath) {
|
|
1991
|
+
const providerModulePath = takeString(
|
|
1992
|
+
config,
|
|
1993
|
+
["providerModulePath", "providerGoModuleName"],
|
|
1994
|
+
state,
|
|
1995
|
+
basePath
|
|
1996
|
+
);
|
|
1997
|
+
if (providerModulePath !== void 0) packageConfig.modulePath = providerModulePath;
|
|
1998
|
+
return compact({
|
|
1999
|
+
providerName: takeString(config, ["providerName"], state, basePath),
|
|
2000
|
+
providerVersion: takeString(config, ["providerVersion"], state, basePath),
|
|
2001
|
+
providerModulePath,
|
|
2002
|
+
mockAcceptance: takeBoolean(config, ["mockAcceptance"], state, basePath),
|
|
2003
|
+
hideComputedDiff: takeBoolean(config, ["hideComputedDiff"], state, basePath)
|
|
2004
|
+
});
|
|
2005
|
+
}
|
|
2006
|
+
function mapMcp(config, state, basePath) {
|
|
2007
|
+
return compact({
|
|
2008
|
+
serverName: takeString(config, ["serverName"], state, basePath),
|
|
2009
|
+
serverDescription: takeString(config, ["serverDescription"], state, basePath),
|
|
2010
|
+
excludeAvailability: takeEnumArray(
|
|
2011
|
+
config,
|
|
2012
|
+
["excludeAvailability"],
|
|
2013
|
+
[
|
|
2014
|
+
"IN_DEVELOPMENT",
|
|
2015
|
+
"PRE_RELEASE",
|
|
2016
|
+
"GENERAL_AVAILABILITY",
|
|
2017
|
+
"DEPRECATED",
|
|
2018
|
+
"ALPHA",
|
|
2019
|
+
"BETA",
|
|
2020
|
+
"PREVIEW",
|
|
2021
|
+
"LEGACY"
|
|
2022
|
+
],
|
|
2023
|
+
state,
|
|
2024
|
+
basePath
|
|
2025
|
+
),
|
|
2026
|
+
tools: takeToolFilter(config, ["tools"], state, basePath),
|
|
2027
|
+
toolsets: takeToolsets(config, ["toolsets"], state, basePath)
|
|
2028
|
+
});
|
|
2029
|
+
}
|
|
2030
|
+
function mapReadme(value, state, basePath) {
|
|
2031
|
+
if (!isObject(value)) return {};
|
|
2032
|
+
const readme = compact({
|
|
2033
|
+
apiName: takeString(value, ["apiName"], state, basePath),
|
|
2034
|
+
introduction: takeString(value, ["introduction"], state, basePath),
|
|
2035
|
+
apiReferenceLink: takeString(value, ["apiReferenceLink"], state, basePath),
|
|
2036
|
+
bannerLink: takeString(value, ["bannerLink"], state, basePath),
|
|
2037
|
+
disabledSections: takeStringArray(value, ["disabledSections"], state, basePath),
|
|
2038
|
+
customSections: takeCustomSections(value, state, basePath),
|
|
2039
|
+
defaultEndpoint: takeReadmeEndpoint(value, ["defaultEndpoint"], state, basePath),
|
|
2040
|
+
features: takeReadmeFeatures(value, state, basePath)
|
|
2041
|
+
});
|
|
2042
|
+
return Object.keys(readme).length ? { readme } : {};
|
|
2043
|
+
}
|
|
2044
|
+
function mapPublishMetadata(value, packageConfig) {
|
|
2045
|
+
if (!isObject(value)) return;
|
|
2046
|
+
const publisherName = stringValue(value.publisherName);
|
|
2047
|
+
const publisherEmail = stringValue(value.publisherEmail);
|
|
2048
|
+
Object.assign(
|
|
2049
|
+
packageConfig,
|
|
2050
|
+
compact({
|
|
2051
|
+
description: stringValue(value.packageDescription),
|
|
2052
|
+
documentationUrl: stringValue(value.referenceUrl),
|
|
2053
|
+
authors: publisherName ? [{ name: publisherName, ...optional("email", publisherEmail) }] : void 0
|
|
2054
|
+
})
|
|
2055
|
+
);
|
|
2056
|
+
}
|
|
2057
|
+
function mapDependencies(config, state, packageConfig, basePath) {
|
|
2058
|
+
for (const field of [
|
|
2059
|
+
"extraDependencies",
|
|
2060
|
+
"extraDevDependencies",
|
|
2061
|
+
"extraPeerDependencies"
|
|
2062
|
+
]) {
|
|
2063
|
+
const located = takeObject(config, [field], state, basePath);
|
|
2064
|
+
if (!located) continue;
|
|
2065
|
+
const dependencies = Object.entries(located.value).flatMap(
|
|
2066
|
+
([name, dependency]) => mapDependency(name, dependency, state, [...located.path, name])
|
|
2067
|
+
);
|
|
2068
|
+
if (dependencies.length) packageConfig[field] = dependencies;
|
|
2069
|
+
}
|
|
2070
|
+
}
|
|
2071
|
+
function mapDependency(name, value, state, path) {
|
|
2072
|
+
if (typeof value === "string" && value) {
|
|
2073
|
+
consume(state, path);
|
|
2074
|
+
return [{ name, version: value }];
|
|
2075
|
+
}
|
|
2076
|
+
if (!isObject(value)) return [];
|
|
2077
|
+
const version = takeString(value, ["version"], state, path);
|
|
2078
|
+
const gitUrl = takeString(value, ["git"], state, path);
|
|
2079
|
+
const localPath = takeString(value, ["path"], state, path);
|
|
2080
|
+
const source = gitUrl ? {
|
|
2081
|
+
type: "git",
|
|
2082
|
+
url: gitUrl,
|
|
2083
|
+
...optional("ref", takeString(value, ["ref"], state, path))
|
|
2084
|
+
} : localPath ? { type: "path", path: localPath } : void 0;
|
|
2085
|
+
if (!version && !source) return [];
|
|
2086
|
+
return [
|
|
2087
|
+
{
|
|
2088
|
+
name,
|
|
2089
|
+
...optional("version", version),
|
|
2090
|
+
...optional("source", source),
|
|
2091
|
+
...optional("packageName", takeString(value, ["package"], state, path)),
|
|
2092
|
+
...optional("features", takeStringArray(value, ["features"], state, path)),
|
|
2093
|
+
...optional("extras", takeStringArray(value, ["extras"], state, path)),
|
|
2094
|
+
...optional("optional", takeBoolean(value, ["optional"], state, path)),
|
|
2095
|
+
...optional("defaultFeatures", takeBoolean(value, ["defaultFeatures"], state, path)),
|
|
2096
|
+
...optional("environmentMarker", takeString(value, ["python"], state, path))
|
|
2097
|
+
}
|
|
2098
|
+
];
|
|
2099
|
+
}
|
|
2100
|
+
function takeCustomSections(value, state, basePath) {
|
|
2101
|
+
const located = locate(value, ["customSections"], basePath);
|
|
2102
|
+
if (!located || !Array.isArray(located.value)) return void 0;
|
|
2103
|
+
const sections = located.value.flatMap(
|
|
2104
|
+
(section) => isObject(section) && section.language === void 0 && typeof section.title === "string" && typeof section.content === "string" ? [{ title: section.title, content: section.content }] : []
|
|
2105
|
+
);
|
|
2106
|
+
if (sections.length !== located.value.length) return void 0;
|
|
2107
|
+
consume(state, located.path);
|
|
2108
|
+
return sections;
|
|
2109
|
+
}
|
|
2110
|
+
function takeReadmeEndpoint(value, aliases, state, basePath) {
|
|
2111
|
+
const located = locate(value, aliases, basePath);
|
|
2112
|
+
if (!located) return void 0;
|
|
2113
|
+
const endpoint = parseReadmeEndpoint(located.value);
|
|
2114
|
+
if (endpoint) consume(state, located.path);
|
|
2115
|
+
return endpoint;
|
|
2116
|
+
}
|
|
2117
|
+
function takeReadmeFeatures(value, state, basePath) {
|
|
2118
|
+
const located = locate(value, ["features"], basePath);
|
|
2119
|
+
if (!located || !isObject(located.value)) return void 0;
|
|
2120
|
+
const features = {};
|
|
2121
|
+
for (const [name, endpoints] of Object.entries(located.value)) {
|
|
2122
|
+
if (!Array.isArray(endpoints)) return void 0;
|
|
2123
|
+
const parsed = endpoints.map(parseReadmeEndpoint);
|
|
2124
|
+
if (parsed.some((endpoint) => !endpoint)) return void 0;
|
|
2125
|
+
features[name] = parsed;
|
|
2126
|
+
}
|
|
2127
|
+
consume(state, located.path);
|
|
2128
|
+
return features;
|
|
2129
|
+
}
|
|
2130
|
+
function parseReadmeEndpoint(value) {
|
|
2131
|
+
if (typeof value === "string") {
|
|
2132
|
+
const match = /^(GET|POST|PUT|PATCH|DELETE|HEAD|OPTIONS|TRACE|CONNECT)\s+(\/\S*)$/.exec(
|
|
2133
|
+
value.trim()
|
|
2134
|
+
);
|
|
2135
|
+
return match ? { method: match[1], path: match[2] } : void 0;
|
|
2136
|
+
}
|
|
2137
|
+
if (!isObject(value) || typeof value.method !== "string" || typeof value.path !== "string") {
|
|
2138
|
+
return void 0;
|
|
2139
|
+
}
|
|
2140
|
+
const method = value.method.toUpperCase();
|
|
2141
|
+
if (!["GET", "POST", "PUT", "PATCH", "DELETE", "HEAD", "OPTIONS", "TRACE", "CONNECT"].includes(
|
|
2142
|
+
method
|
|
2143
|
+
)) {
|
|
2144
|
+
return void 0;
|
|
2145
|
+
}
|
|
2146
|
+
return {
|
|
2147
|
+
method,
|
|
2148
|
+
path: value.path,
|
|
2149
|
+
...optional("stream", typeof value.stream === "boolean" ? value.stream : void 0)
|
|
2150
|
+
};
|
|
2151
|
+
}
|
|
2152
|
+
function takeToolFilter(value, aliases, state, basePath) {
|
|
2153
|
+
const located = takeObject(value, aliases, state, basePath);
|
|
2154
|
+
if (!located) return void 0;
|
|
2155
|
+
const filter = compact({
|
|
2156
|
+
include: stringArrayValue(located.value.include),
|
|
2157
|
+
exclude: stringArrayValue(located.value.exclude)
|
|
2158
|
+
});
|
|
2159
|
+
if (Object.keys(filter).length === 0 && Object.keys(located.value).length > 0) return void 0;
|
|
2160
|
+
consume(state, located.path);
|
|
2161
|
+
return filter;
|
|
2162
|
+
}
|
|
2163
|
+
function takeToolsets(value, aliases, state, basePath) {
|
|
2164
|
+
const located = takeObject(value, aliases, state, basePath);
|
|
2165
|
+
if (!located) return void 0;
|
|
2166
|
+
const entries = Object.entries(located.value).map(([name, filter]) => {
|
|
2167
|
+
if (name === "default" || !/^[a-z0-9-]+$/.test(name)) {
|
|
2168
|
+
fail(
|
|
2169
|
+
"FERN_MCP_TOOLSET_NAME_INVALID",
|
|
2170
|
+
[...located.path, name],
|
|
2171
|
+
`MCP toolset name "${name}" is not valid in SDK Config v1`,
|
|
2172
|
+
'Rename the toolset to lowercase letters, numbers, or hyphens; "default" is reserved.',
|
|
2173
|
+
["targets", basePath[2], "generation", "toolsets", name]
|
|
2174
|
+
);
|
|
2175
|
+
}
|
|
2176
|
+
if (!isObject(filter)) return void 0;
|
|
2177
|
+
return [
|
|
2178
|
+
name,
|
|
2179
|
+
compact({
|
|
2180
|
+
include: stringArrayValue(filter.include),
|
|
2181
|
+
exclude: stringArrayValue(filter.exclude)
|
|
2182
|
+
})
|
|
2183
|
+
];
|
|
2184
|
+
});
|
|
2185
|
+
if (entries.some((entry) => !entry)) return void 0;
|
|
2186
|
+
consume(state, located.path);
|
|
2187
|
+
return Object.fromEntries(entries.filter((entry) => entry !== void 0));
|
|
2188
|
+
}
|
|
2189
|
+
var unsupportedFieldSchema = z.strictObject({
|
|
2190
|
+
source: z.enum(["fern", "postman", "sdk-config-ir"]),
|
|
2191
|
+
path: z.array(z.union([nonEmptyStringSchema, z.number().int().nonnegative()])).min(1),
|
|
2192
|
+
code: nonEmptyStringSchema.optional(),
|
|
2193
|
+
reason: nonEmptyStringSchema,
|
|
2194
|
+
severity: z.enum(["error", "warning", "info"]),
|
|
2195
|
+
risk: z.enum(["high", "medium", "low"]),
|
|
2196
|
+
owner: nonEmptyStringSchema,
|
|
2197
|
+
suggestedAction: nonEmptyStringSchema
|
|
455
2198
|
});
|
|
456
|
-
var
|
|
457
|
-
|
|
458
|
-
|
|
2199
|
+
var postmanLegacyInputSchema = z.strictObject({
|
|
2200
|
+
kind: z.literal("postman-build-parameters"),
|
|
2201
|
+
value: jsonObjectSchema
|
|
459
2202
|
});
|
|
460
|
-
var
|
|
461
|
-
|
|
462
|
-
|
|
463
|
-
modulePath: goModulePathSchema.optional(),
|
|
464
|
-
namespace: nonEmptyStringSchema.optional(),
|
|
465
|
-
groupId: nonEmptyStringSchema.optional(),
|
|
466
|
-
artifactId: nonEmptyStringSchema.optional(),
|
|
467
|
-
description: z.string().optional(),
|
|
468
|
-
repository: nonEmptyStringSchema.optional(),
|
|
469
|
-
homepage: nonEmptyStringSchema.optional(),
|
|
470
|
-
documentationUrl: nonEmptyStringSchema.optional(),
|
|
471
|
-
authors: z.array(authorSchema).optional(),
|
|
472
|
-
developers: z.array(developerSchema).optional(),
|
|
473
|
-
license: licenseSchema.optional(),
|
|
474
|
-
keywords: z.array(nonEmptyStringSchema).optional(),
|
|
475
|
-
classifiers: z.array(nonEmptyStringSchema).optional(),
|
|
476
|
-
projectUrls: z.array(projectUrlSchema).optional(),
|
|
477
|
-
extraDependencies: z.array(dependencySchema).optional(),
|
|
478
|
-
extraDevDependencies: z.array(dependencySchema).optional(),
|
|
479
|
-
extraPeerDependencies: z.array(dependencySchema).optional()
|
|
2203
|
+
var fernLegacyInputSchema = z.strictObject({
|
|
2204
|
+
kind: z.literal("fern-generator-invocation"),
|
|
2205
|
+
value: jsonObjectSchema
|
|
480
2206
|
});
|
|
481
|
-
|
|
482
|
-
|
|
483
|
-
|
|
484
|
-
z.strictObject({ enabled: z.literal(true), sourceDir: nonEmptyStringSchema }),
|
|
485
|
-
z.strictObject({ enabled: z.literal(false) })
|
|
2207
|
+
var legacyInputSchema = z.discriminatedUnion("kind", [
|
|
2208
|
+
postmanLegacyInputSchema,
|
|
2209
|
+
fernLegacyInputSchema
|
|
486
2210
|
]);
|
|
487
|
-
var
|
|
488
|
-
|
|
489
|
-
|
|
490
|
-
|
|
491
|
-
var providerSchemaSchema = z.strictObject({
|
|
492
|
-
addressKey: nonEmptyStringSchema,
|
|
493
|
-
authTokenKey: nonEmptyStringSchema
|
|
494
|
-
});
|
|
495
|
-
var terraformGenerationConfigSchema = z.strictObject({
|
|
496
|
-
providerName: nonEmptyStringSchema.optional(),
|
|
497
|
-
providerVersion: nonEmptyStringSchema.optional(),
|
|
498
|
-
providerModulePath: goModulePathSchema.optional(),
|
|
499
|
-
mockAcceptance: z.boolean().optional(),
|
|
500
|
-
hideComputedDiff: z.boolean().optional(),
|
|
501
|
-
providerSchema: providerSchemaSchema.optional(),
|
|
502
|
-
planModifiers: planModifiersSchema.optional()
|
|
2211
|
+
var compatibilityConfigSchema = z.strictObject({
|
|
2212
|
+
outputProfile: z.enum(["converged", "postman-legacy", "fern-legacy"]),
|
|
2213
|
+
legacyInput: legacyInputSchema.optional(),
|
|
2214
|
+
unsupportedFields: z.array(unsupportedFieldSchema).optional()
|
|
503
2215
|
});
|
|
504
|
-
|
|
505
|
-
// src/sdk-config-ir/v1/generation.ts
|
|
506
2216
|
var generationAssetSchema = z.strictObject({
|
|
507
2217
|
type: z.enum(["path", "url", "artifact"]),
|
|
508
2218
|
location: nonEmptyStringSchema
|
|
509
2219
|
});
|
|
510
|
-
var
|
|
2220
|
+
var hookDependencySchema2 = z.strictObject({
|
|
511
2221
|
name: nonEmptyStringSchema,
|
|
512
2222
|
version: nonEmptyStringSchema,
|
|
513
2223
|
groupId: nonEmptyStringSchema.optional()
|
|
514
2224
|
});
|
|
515
|
-
var
|
|
2225
|
+
var hooksConfigSchema2 = z.strictObject({
|
|
516
2226
|
enabled: z.boolean(),
|
|
517
2227
|
source: generationAssetSchema.optional(),
|
|
518
|
-
dependencies: z.array(
|
|
2228
|
+
dependencies: z.array(hookDependencySchema2).optional()
|
|
519
2229
|
});
|
|
520
|
-
var
|
|
2230
|
+
var customCodeConfigSchema2 = z.strictObject({
|
|
521
2231
|
enabled: z.boolean(),
|
|
522
2232
|
source: generationAssetSchema.optional(),
|
|
523
2233
|
conflictStrategy: z.enum(["mark", "ours", "theirs"]).optional(),
|
|
@@ -525,19 +2235,19 @@ var customCodeConfigSchema = z.strictObject({
|
|
|
525
2235
|
previousBuildId: z.number().int().positive().optional(),
|
|
526
2236
|
protectedFiles: z.array(nonEmptyStringSchema).optional()
|
|
527
2237
|
});
|
|
528
|
-
var
|
|
2238
|
+
var workflowConfigSchema2 = z.strictObject({
|
|
529
2239
|
path: nonEmptyStringSchema,
|
|
530
2240
|
outputName: nonEmptyStringSchema.optional()
|
|
531
2241
|
});
|
|
532
|
-
var
|
|
2242
|
+
var analyticsHeaderSchema2 = z.union([
|
|
533
2243
|
z.strictObject({ name: nonEmptyStringSchema, value: z.string() }),
|
|
534
2244
|
z.strictObject({ name: nonEmptyStringSchema, valueRef: nonEmptyStringSchema })
|
|
535
2245
|
]);
|
|
536
|
-
var
|
|
2246
|
+
var analyticsConfigSchema2 = z.strictObject({
|
|
537
2247
|
enabled: z.boolean(),
|
|
538
2248
|
endpoint: nonEmptyStringSchema.optional(),
|
|
539
2249
|
exporter: z.enum(["otlp-http", "console"]).optional(),
|
|
540
|
-
headers: z.array(
|
|
2250
|
+
headers: z.array(analyticsHeaderSchema2).optional(),
|
|
541
2251
|
batchSize: z.number().int().positive().optional(),
|
|
542
2252
|
scheduledDelayMs: z.number().nonnegative().optional(),
|
|
543
2253
|
exportTimeoutMs: z.number().nonnegative().optional()
|
|
@@ -550,24 +2260,29 @@ var analyticsConfigSchema = z.strictObject({
|
|
|
550
2260
|
});
|
|
551
2261
|
}
|
|
552
2262
|
});
|
|
553
|
-
var
|
|
2263
|
+
var wireTestsSchema2 = z.strictObject({
|
|
554
2264
|
enabled: z.boolean(),
|
|
555
2265
|
exclusions: z.array(nonEmptyStringSchema).optional(),
|
|
556
2266
|
fallbackToGeneratedErrorExamples: z.boolean().optional(),
|
|
557
2267
|
fixtureSource: z.enum(["synthetic", "recorded", "auto"]).optional()
|
|
558
2268
|
});
|
|
559
|
-
var
|
|
2269
|
+
var unitTestsSchema2 = z.strictObject({
|
|
560
2270
|
enabled: z.boolean(),
|
|
561
2271
|
mode: z.enum(["core-runtime", "schema-driven", "both"]).optional(),
|
|
562
2272
|
exclusions: z.array(nonEmptyStringSchema).optional()
|
|
563
2273
|
});
|
|
564
|
-
var
|
|
2274
|
+
var fernDefinitionMetadataSchema = z.strictObject({
|
|
2275
|
+
definitionS3DownloadUrl: nonEmptyStringSchema,
|
|
2276
|
+
outputPath: nonEmptyStringSchema.optional(),
|
|
2277
|
+
cliVersion: nonEmptyStringSchema.optional()
|
|
2278
|
+
});
|
|
2279
|
+
var streamsSchema2 = z.strictObject({
|
|
565
2280
|
enabled: z.boolean(),
|
|
566
2281
|
responseType: z.enum(["wrapper", "native", "web"]).optional(),
|
|
567
2282
|
fileResponseType: z.enum(["stream", "binary-response"]).optional(),
|
|
568
2283
|
defaultChunkSizeBytes: z.number().int().positive().optional()
|
|
569
2284
|
});
|
|
570
|
-
var
|
|
2285
|
+
var namingConfigSchema2 = z.strictObject({
|
|
571
2286
|
clientName: nonEmptyStringSchema.optional(),
|
|
572
2287
|
exportedClientName: nonEmptyStringSchema.optional(),
|
|
573
2288
|
environmentTypeName: nonEmptyStringSchema.optional(),
|
|
@@ -575,11 +2290,11 @@ var namingConfigSchema = z.strictObject({
|
|
|
575
2290
|
baseErrorName: nonEmptyStringSchema.optional(),
|
|
576
2291
|
pagerName: nonEmptyStringSchema.optional()
|
|
577
2292
|
});
|
|
578
|
-
var
|
|
2293
|
+
var layoutConfigSchema2 = z.strictObject({
|
|
579
2294
|
outputDirectory: z.enum(["project-root", "source-root"]).optional(),
|
|
580
2295
|
packagePath: nonEmptyStringSchema.optional()
|
|
581
2296
|
});
|
|
582
|
-
var
|
|
2297
|
+
var serializationConfigSchema2 = z.strictObject({
|
|
583
2298
|
enumRepresentation: z.enum(["enum", "union", "literal", "forward-compatible-enum", "language-default"]).optional(),
|
|
584
2299
|
additionalProperties: z.enum(["allow", "forbid", "ignore", "language-default"]).optional(),
|
|
585
2300
|
inlineTypes: z.boolean().optional(),
|
|
@@ -612,19 +2327,30 @@ var generationConfigSchema = z.strictObject({
|
|
|
612
2327
|
devContainer: z.boolean().default(false),
|
|
613
2328
|
allowMockClient: z.boolean().default(false),
|
|
614
2329
|
ignoreFiles: z.array(nonEmptyStringSchema).optional(),
|
|
2330
|
+
/**
|
|
2331
|
+
* Raw .fernignore file contents supplied to external publishers that need Fern ignore semantics.
|
|
2332
|
+
* This is separate from generation.ignoreFiles because raw contents preserve comments, ordering,
|
|
2333
|
+
* blank lines, and negation rules.
|
|
2334
|
+
*/
|
|
2335
|
+
fernignoreContents: z.string().optional(),
|
|
2336
|
+
/**
|
|
2337
|
+
* Optional Fern definition metadata for publisher paths that need to write definition or
|
|
2338
|
+
* mock-server support files. This is not required for core GitHub artifact publishing.
|
|
2339
|
+
*/
|
|
2340
|
+
fernDefinitionMetadata: fernDefinitionMetadataSchema.optional(),
|
|
615
2341
|
reservedKeywords: z.array(nonEmptyStringSchema).optional(),
|
|
616
|
-
hooks:
|
|
617
|
-
customCode:
|
|
618
|
-
workflows: z.array(
|
|
2342
|
+
hooks: hooksConfigSchema2.optional(),
|
|
2343
|
+
customCode: customCodeConfigSchema2.optional(),
|
|
2344
|
+
workflows: z.array(workflowConfigSchema2).optional(),
|
|
619
2345
|
customQueryPaths: z.array(nonEmptyStringSchema).optional(),
|
|
620
|
-
analytics:
|
|
621
|
-
wireTests:
|
|
622
|
-
unitTests:
|
|
2346
|
+
analytics: analyticsConfigSchema2.optional(),
|
|
2347
|
+
wireTests: wireTestsSchema2.optional(),
|
|
2348
|
+
unitTests: unitTestsSchema2.optional(),
|
|
623
2349
|
webSockets: z.boolean().optional(),
|
|
624
|
-
streams:
|
|
625
|
-
naming:
|
|
626
|
-
layout:
|
|
627
|
-
serialization:
|
|
2350
|
+
streams: streamsSchema2.optional(),
|
|
2351
|
+
naming: namingConfigSchema2.optional(),
|
|
2352
|
+
layout: layoutConfigSchema2.optional(),
|
|
2353
|
+
serialization: serializationConfigSchema2.optional(),
|
|
628
2354
|
language: languageGenerationConfigSchema.optional()
|
|
629
2355
|
});
|
|
630
2356
|
var publishRegistrySchema = z.enum([
|
|
@@ -637,57 +2363,95 @@ var publishRegistrySchema = z.enum([
|
|
|
637
2363
|
"go",
|
|
638
2364
|
"composer"
|
|
639
2365
|
]);
|
|
640
|
-
var
|
|
2366
|
+
var credentialResolutionSchema = z.enum([
|
|
2367
|
+
"refs-only",
|
|
2368
|
+
"resolved-by-orchestrator",
|
|
2369
|
+
"resolved-by-fiddle"
|
|
2370
|
+
]);
|
|
2371
|
+
var commonPublishShape2 = {
|
|
641
2372
|
url: nonEmptyStringSchema.optional(),
|
|
2373
|
+
/**
|
|
2374
|
+
* Reference to registry publishing credentials. Raw tokens/passwords are intentionally not part of
|
|
2375
|
+
* SDK Config IR; the external publisher or orchestrator resolves this reference before use.
|
|
2376
|
+
*/
|
|
642
2377
|
credentialsRef: nonEmptyStringSchema.optional(),
|
|
643
2378
|
releaseBranch: nonEmptyStringSchema.optional(),
|
|
644
2379
|
tolerateRepublish: z.boolean().optional()
|
|
645
2380
|
};
|
|
646
2381
|
var publishConfigSchema = z.discriminatedUnion("registry", [
|
|
647
|
-
z.strictObject({ registry: z.literal("npm"), ...
|
|
648
|
-
z.strictObject({ registry: z.literal("pypi"), ...
|
|
649
|
-
z.strictObject({ registry: z.literal("nuget"), ...
|
|
650
|
-
z.strictObject({ registry: z.literal("rubygems"), ...
|
|
651
|
-
z.strictObject({ registry: z.literal("crates"), ...
|
|
652
|
-
z.strictObject({ registry: z.literal("go"), ...
|
|
653
|
-
z.strictObject({ registry: z.literal("composer"), ...
|
|
2382
|
+
z.strictObject({ registry: z.literal("npm"), ...commonPublishShape2 }),
|
|
2383
|
+
z.strictObject({ registry: z.literal("pypi"), ...commonPublishShape2 }),
|
|
2384
|
+
z.strictObject({ registry: z.literal("nuget"), ...commonPublishShape2 }),
|
|
2385
|
+
z.strictObject({ registry: z.literal("rubygems"), ...commonPublishShape2 }),
|
|
2386
|
+
z.strictObject({ registry: z.literal("crates"), ...commonPublishShape2 }),
|
|
2387
|
+
z.strictObject({ registry: z.literal("go"), ...commonPublishShape2 }),
|
|
2388
|
+
z.strictObject({ registry: z.literal("composer"), ...commonPublishShape2 }),
|
|
654
2389
|
z.strictObject({
|
|
655
2390
|
registry: z.literal("maven"),
|
|
2391
|
+
/**
|
|
2392
|
+
* Reference to Maven signing credentials. Raw signing keys are intentionally not part of SDK
|
|
2393
|
+
* Config IR; the external publisher or orchestrator resolves this reference before use.
|
|
2394
|
+
*/
|
|
656
2395
|
signingCredentialsRef: nonEmptyStringSchema.optional(),
|
|
657
|
-
...
|
|
2396
|
+
...commonPublishShape2
|
|
658
2397
|
})
|
|
659
2398
|
]);
|
|
660
|
-
var
|
|
2399
|
+
var reviewersSchema2 = z.strictObject({
|
|
661
2400
|
teams: z.array(nonEmptyStringSchema).optional(),
|
|
662
2401
|
users: z.array(nonEmptyStringSchema).optional()
|
|
663
2402
|
});
|
|
664
|
-
var
|
|
2403
|
+
var replayControlSchema = z.strictObject({
|
|
2404
|
+
enabled: z.boolean()
|
|
2405
|
+
});
|
|
2406
|
+
var githubOutputSchema2 = z.strictObject({
|
|
665
2407
|
repository: nonEmptyStringSchema,
|
|
666
2408
|
host: nonEmptyStringSchema.optional(),
|
|
667
2409
|
branch: nonEmptyStringSchema.optional(),
|
|
668
2410
|
mode: z.enum(["release", "pull-request", "push"]).optional(),
|
|
669
|
-
reviewers:
|
|
2411
|
+
reviewers: reviewersSchema2.optional(),
|
|
2412
|
+
/**
|
|
2413
|
+
* Reference to GitHub credentials. Raw tokens are intentionally not part of SDK Config IR; the
|
|
2414
|
+
* external publisher or orchestrator resolves this reference before use.
|
|
2415
|
+
*/
|
|
670
2416
|
credentialsRef: nonEmptyStringSchema.optional(),
|
|
671
|
-
privateRepository: z.boolean().optional()
|
|
672
|
-
|
|
673
|
-
|
|
2417
|
+
privateRepository: z.boolean().optional(),
|
|
2418
|
+
/** GitHub replay control. If omitted, the external publisher applies its default behavior. */
|
|
2419
|
+
replay: replayControlSchema.optional(),
|
|
2420
|
+
/** Run GitHub publishing verification. Defaults to false to match current Fiddle job behavior. */
|
|
2421
|
+
verify: z.boolean().default(false),
|
|
2422
|
+
/** Skip creating/updating a GitHub PR when no files changed. Defaults to false. */
|
|
2423
|
+
skipIfNoDiff: z.boolean().default(false),
|
|
2424
|
+
/** Automatically merge the GitHub publishing PR. Defaults to false. */
|
|
2425
|
+
autoMerge: z.boolean().default(false)
|
|
2426
|
+
});
|
|
2427
|
+
var credentialResolutionShape = {
|
|
2428
|
+
/**
|
|
2429
|
+
* Where output credential references are resolved. SDK Config IR carries refs only; raw resolved
|
|
2430
|
+
* credentials belong at the external publisher/orchestrator boundary, not in this config.
|
|
2431
|
+
*/
|
|
2432
|
+
credentialResolution: credentialResolutionSchema.default("refs-only")
|
|
2433
|
+
};
|
|
2434
|
+
var filesOutputSchema2 = z.strictObject({
|
|
674
2435
|
delivery: z.literal("files"),
|
|
675
2436
|
path: nonEmptyStringSchema.optional(),
|
|
676
|
-
publish: publishConfigSchema.optional()
|
|
2437
|
+
publish: publishConfigSchema.optional(),
|
|
2438
|
+
...credentialResolutionShape
|
|
677
2439
|
});
|
|
678
|
-
var
|
|
2440
|
+
var zipOutputSchema2 = z.strictObject({
|
|
679
2441
|
delivery: z.literal("zip"),
|
|
680
2442
|
fileName: nonEmptyStringSchema.optional(),
|
|
681
|
-
publish: publishConfigSchema.optional()
|
|
2443
|
+
publish: publishConfigSchema.optional(),
|
|
2444
|
+
...credentialResolutionShape
|
|
682
2445
|
});
|
|
683
|
-
var
|
|
2446
|
+
var githubDeliverySchema2 = z.strictObject({
|
|
684
2447
|
delivery: z.literal("github"),
|
|
685
|
-
github:
|
|
686
|
-
publish: publishConfigSchema.optional()
|
|
2448
|
+
github: githubOutputSchema2,
|
|
2449
|
+
publish: publishConfigSchema.optional(),
|
|
2450
|
+
...credentialResolutionShape
|
|
687
2451
|
});
|
|
688
2452
|
var outputConfigSchema = z.discriminatedUnion(
|
|
689
2453
|
"delivery",
|
|
690
|
-
[
|
|
2454
|
+
[filesOutputSchema2, zipOutputSchema2, githubDeliverySchema2],
|
|
691
2455
|
{
|
|
692
2456
|
error: 'output.delivery must be one of "files", "zip", or "github"'
|
|
693
2457
|
}
|
|
@@ -703,7 +2467,8 @@ var apiImportSettingsSchema = z.strictObject({
|
|
|
703
2467
|
onlyIncludeReferencedSchemas: z.boolean().optional(),
|
|
704
2468
|
objectQueryParameters: z.boolean().optional(),
|
|
705
2469
|
typeDatesAsStrings: z.boolean().optional(),
|
|
706
|
-
groupMultiApiEnvironments: z.boolean().optional()
|
|
2470
|
+
groupMultiApiEnvironments: z.boolean().optional(),
|
|
2471
|
+
defaultIntegerFormat: z.enum(["int32", "int64", "uint32", "uint64"]).optional()
|
|
707
2472
|
});
|
|
708
2473
|
var sourceSpecTypeSchema = z.enum([
|
|
709
2474
|
"openapi",
|
|
@@ -760,15 +2525,27 @@ var targetConfigSchema = z.strictObject({
|
|
|
760
2525
|
generatorVersion: exactSemverSchema.optional(),
|
|
761
2526
|
sourceOrigin: z.enum(["postman", "fern"]),
|
|
762
2527
|
sdkName: nonEmptyStringSchema,
|
|
2528
|
+
/**
|
|
2529
|
+
* Stable Fern/Fiddle API identity for external publishing.
|
|
2530
|
+
* Producers must set this explicitly for GitHub or registry publishing; it is not inferred from
|
|
2531
|
+
* target.sdkName because SDK display names and Fern API names are not equivalent.
|
|
2532
|
+
*/
|
|
2533
|
+
apiName: nonEmptyStringSchema.optional(),
|
|
763
2534
|
organization: nonEmptyStringSchema.optional(),
|
|
2535
|
+
/**
|
|
2536
|
+
* Stable Fern/Fiddle organization identity for external publishing.
|
|
2537
|
+
* Producers must set this explicitly for GitHub or registry publishing; it is not inferred from
|
|
2538
|
+
* target.organization because source organization metadata is optional and may not match Fern.
|
|
2539
|
+
*/
|
|
2540
|
+
organizationName: nonEmptyStringSchema.optional(),
|
|
764
2541
|
sdkVersion: nonEmptyStringSchema.default("1.0.0"),
|
|
765
2542
|
apiVersion: nonEmptyStringSchema.optional()
|
|
766
2543
|
});
|
|
767
2544
|
|
|
768
2545
|
// src/sdk-config-ir/v1/sdk-config-ir-v1.ts
|
|
769
2546
|
var SDK_CONFIG_IR_V1_SCHEMA_VERSION = "sdk-config-ir/v1";
|
|
770
|
-
var
|
|
771
|
-
npm: ["typescript"],
|
|
2547
|
+
var publishRegistryLanguages2 = {
|
|
2548
|
+
npm: ["typescript", "mcp"],
|
|
772
2549
|
pypi: ["python"],
|
|
773
2550
|
maven: ["java", "kotlin"],
|
|
774
2551
|
nuget: ["csharp"],
|
|
@@ -777,7 +2554,7 @@ var publishRegistryLanguages = {
|
|
|
777
2554
|
go: ["go"],
|
|
778
2555
|
composer: ["php"]
|
|
779
2556
|
};
|
|
780
|
-
var
|
|
2557
|
+
var packageNameRegistries2 = /* @__PURE__ */ new Set([
|
|
781
2558
|
"npm",
|
|
782
2559
|
"pypi",
|
|
783
2560
|
"nuget",
|
|
@@ -785,8 +2562,8 @@ var packageNameRegistries = /* @__PURE__ */ new Set([
|
|
|
785
2562
|
"crates",
|
|
786
2563
|
"composer"
|
|
787
2564
|
]);
|
|
788
|
-
function
|
|
789
|
-
if (
|
|
2565
|
+
function validatePublishingIdentity2(packageConfig, registry, context) {
|
|
2566
|
+
if (packageNameRegistries2.has(registry) && !packageConfig.packageName) {
|
|
790
2567
|
context.addIssue({
|
|
791
2568
|
code: "custom",
|
|
792
2569
|
message: `package.packageName is required when publishing to "${registry}"`,
|
|
@@ -836,6 +2613,21 @@ var sdkConfigIrV1Schema = z.strictObject({
|
|
|
836
2613
|
compatibility: compatibilityConfigSchema.optional()
|
|
837
2614
|
}).superRefine(({ compatibility, generation, output, package: packageConfig, target }, context) => {
|
|
838
2615
|
const configuredLanguages = Object.keys(generation.language ?? {});
|
|
2616
|
+
const requiresExternalPublishIdentity = output.delivery === "github" || output.publish !== void 0;
|
|
2617
|
+
if (requiresExternalPublishIdentity) {
|
|
2618
|
+
[
|
|
2619
|
+
["apiName", "target.apiName is required for external publishing"],
|
|
2620
|
+
["organizationName", "target.organizationName is required for external publishing"]
|
|
2621
|
+
].forEach(([field, message]) => {
|
|
2622
|
+
if (!target[field]) {
|
|
2623
|
+
context.addIssue({
|
|
2624
|
+
code: "custom",
|
|
2625
|
+
message,
|
|
2626
|
+
path: ["target", field]
|
|
2627
|
+
});
|
|
2628
|
+
}
|
|
2629
|
+
});
|
|
2630
|
+
}
|
|
839
2631
|
configuredLanguages.forEach((language) => {
|
|
840
2632
|
if (language !== target.language) {
|
|
841
2633
|
context.addIssue({
|
|
@@ -845,7 +2637,7 @@ var sdkConfigIrV1Schema = z.strictObject({
|
|
|
845
2637
|
});
|
|
846
2638
|
}
|
|
847
2639
|
});
|
|
848
|
-
if (output.publish && !
|
|
2640
|
+
if (output.publish && !publishRegistryLanguages2[output.publish.registry].some(
|
|
849
2641
|
(language) => language === target.language
|
|
850
2642
|
)) {
|
|
851
2643
|
context.addIssue({
|
|
@@ -855,7 +2647,7 @@ var sdkConfigIrV1Schema = z.strictObject({
|
|
|
855
2647
|
});
|
|
856
2648
|
}
|
|
857
2649
|
if (output.publish) {
|
|
858
|
-
|
|
2650
|
+
validatePublishingIdentity2(packageConfig, output.publish.registry, context);
|
|
859
2651
|
}
|
|
860
2652
|
if (compatibility?.legacyInput) {
|
|
861
2653
|
const expectedKind = target.sourceOrigin === "postman" ? "postman-build-parameters" : "fern-generator-invocation";
|
|
@@ -872,6 +2664,6 @@ function parseSdkConfigIrV1(value) {
|
|
|
872
2664
|
return sdkConfigIrV1Schema.parse(value);
|
|
873
2665
|
}
|
|
874
2666
|
|
|
875
|
-
export { SDK_CONFIG_IR_V1_SCHEMA_VERSION, apiConfigSchema, apiImportSettingsSchema, authConfigSchema, authSchemeSchema, cliGenerationConfigSchema, clientConfigSchema, compatibilityConfigSchema, composerPackageNameSchema, csharpGenerationConfigSchema, dependencySchema, docsConfigSchema, exactSemverSchema, generationConfigSchema, goGenerationConfigSchema, goModulePathSchema, javaGenerationConfigSchema, jsonObjectSchema, jsonValueSchema, kotlinGenerationConfigSchema, languageGenerationConfigSchema, legacyInputSchema, mcpGenerationConfigSchema, nonEmptyStringSchema, outputConfigSchema, packageConfigSchema, parseSdkConfigIrV1, phpGenerationConfigSchema, publishConfigSchema, publishRegistrySchema, pythonGenerationConfigSchema, readmeEndpointSchema, rubyGenerationConfigSchema, rustGenerationConfigSchema, sdkConfigIrV1Schema, sourceConfigSchema, sourceSpecConfigSchema, sourceSpecTypeSchema, swiftGenerationConfigSchema, targetConfigSchema, targetLanguageSchema, terraformGenerationConfigSchema, typescriptGenerationConfigSchema, unsupportedFieldSchema };
|
|
2667
|
+
export { FernConfigMappingError, SDK_CONFIG_IR_V1_SCHEMA_VERSION, SDK_CONFIG_V1_SCHEMA_VERSION, apiConfigSchema, apiImportSettingsSchema, authConfigSchema, authSchemeSchema, cliGenerationConfigSchema, clientConfigSchema, compatibilityConfigSchema, composerPackageNameSchema, csharpGenerationConfigSchema, dependencySchema, docsConfigSchema, exactSemverSchema, generationConfigSchema, goGenerationConfigSchema, goModulePathSchema, javaGenerationConfigSchema, jsonObjectSchema, jsonValueSchema, kotlinGenerationConfigSchema, languageGenerationConfigSchema, legacyInputSchema, mapFernConfigToSdkConfigV1, mcpAvailabilityStatuses, mcpGenerationConfigSchema, nonEmptyStringSchema, outputConfigSchema, packageConfigSchema, parseSdkConfigIrV1, parseSdkConfigV1, phpGenerationConfigSchema, publishConfigSchema, publishRegistrySchema, pythonGenerationConfigSchema, readmeCustomSectionSchema, readmeEndpointSchema, rubyGenerationConfigSchema, rustGenerationConfigSchema, sdkConfigIrV1Schema, sdkConfigV1ApiConfigSchema, sdkConfigV1AuthConfigSchema, sdkConfigV1AuthSchemeSchema, cliGenerationConfigSchema as sdkConfigV1CliGenerationConfigSchema, sdkConfigV1ClientConfigSchema, composerPackageNameSchema as sdkConfigV1ComposerPackageNameSchema, csharpGenerationConfigSchema as sdkConfigV1CsharpGenerationConfigSchema, sdkConfigV1DependencySchema, sdkConfigV1DocsConfigSchema, exactSemverSchema as sdkConfigV1ExactSemverSchema, sdkConfigV1GenerationConfigSchema, goGenerationConfigSchema as sdkConfigV1GoGenerationConfigSchema, goModulePathSchema as sdkConfigV1GoModulePathSchema, javaGenerationConfigSchema as sdkConfigV1JavaGenerationConfigSchema, kotlinGenerationConfigSchema as sdkConfigV1KotlinGenerationConfigSchema, mcpGenerationConfigSchema as sdkConfigV1McpGenerationConfigSchema, nonEmptyStringSchema as sdkConfigV1NonEmptyStringSchema, sdkConfigV1OutputConfigSchema, sdkConfigV1PackageConfigSchema, phpGenerationConfigSchema as sdkConfigV1PhpGenerationConfigSchema, sdkConfigV1PublishConfigSchema, sdkConfigV1PublishRegistrySchema, pythonGenerationConfigSchema as sdkConfigV1PythonGenerationConfigSchema, sdkConfigV1ReadmeCustomSectionSchema, sdkConfigV1ReadmeEndpointSchema, rubyGenerationConfigSchema as sdkConfigV1RubyGenerationConfigSchema, rustGenerationConfigSchema as sdkConfigV1RustGenerationConfigSchema, sdkConfigV1Schema, swiftGenerationConfigSchema as sdkConfigV1SwiftGenerationConfigSchema, sdkConfigV1TargetSchema, terraformGenerationConfigSchema as sdkConfigV1TerraformGenerationConfigSchema, typescriptGenerationConfigSchema as sdkConfigV1TypescriptGenerationConfigSchema, sourceConfigSchema, sourceSpecConfigSchema, sourceSpecTypeSchema, swiftGenerationConfigSchema, targetConfigSchema, targetLanguageSchema, terraformGenerationConfigSchema, typescriptGenerationConfigSchema, unsupportedFieldSchema };
|
|
876
2668
|
//# sourceMappingURL=index.js.map
|
|
877
2669
|
//# sourceMappingURL=index.js.map
|