-
Notifications
You must be signed in to change notification settings - Fork 8
/
openapi-codegen.config.ts
123 lines (102 loc) · 3.83 KB
/
openapi-codegen.config.ts
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
import { defineConfig } from '@openapi-codegen/cli';
import { Context } from '@openapi-codegen/cli/lib/types';
import { addPathParam, generateFetchers, generateSchemaTypes, renameComponent } from '@openapi-codegen/typescript';
export default defineConfig({
controlPlane: {
from: {
source: 'github',
owner: 'xataio',
ref: 'main',
repository: 'xata',
specPath: 'openapi/bundled/api_xata_io.yaml'
},
outputDir: 'packages/client/src/api',
to: async (context) => {
const filenamePrefix = 'controlPlane';
context.openAPIDocument = removeDraftPaths({ openAPIDocument: context.openAPIDocument });
const { schemasFiles } = await generateSchemaTypes(context, { filenamePrefix });
await generateFetchers(context, { filenamePrefix, schemasFiles });
}
},
dataPlane: {
from: {
source: 'github',
owner: 'xataio',
ref: 'main',
repository: 'xata',
specPath: 'openapi/bundled/xata_sh.yaml'
},
outputDir: 'packages/client/src/api',
to: async (context) => {
// TODO: Fix me, allow no filenamePrefix
const filenamePrefix = 'dataPlane';
context.openAPIDocument = removeDraftPaths({ openAPIDocument: context.openAPIDocument });
// Avoid conflict with typescript `Record<>` type helper
context.openAPIDocument = renameComponent({
openAPIDocument: context.openAPIDocument,
from: '#/components/schemas/Record',
to: '#/components/schemas/XataRecord'
});
context.openAPIDocument = removeDeprecatedObjectType({ openAPIDocument: context.openAPIDocument });
// Inject path param in all requests (for now, this should be server url variables)
context.openAPIDocument = addPathParam({
openAPIDocument: context.openAPIDocument,
pathParam: 'workspace',
required: true
});
context.openAPIDocument = addPathParam({
openAPIDocument: context.openAPIDocument,
pathParam: 'region',
required: true
});
const { schemasFiles } = await generateSchemaTypes(context, { filenamePrefix });
await generateFetchers(context, { filenamePrefix, schemasFiles });
}
}
});
function removeDraftPaths({ openAPIDocument }: { openAPIDocument: Context['openAPIDocument'] }) {
const paths = Object.fromEntries(
Object.entries(openAPIDocument.paths).map(([route, verbs]) => {
const updatedVerbs = Object.entries(verbs).reduce((acc, [verb, operation]) => {
if (isVerb(verb) && isDraft(operation)) {
return acc;
}
return { ...acc, [verb]: operation };
}, {});
return [route, updatedVerbs];
})
);
return { ...openAPIDocument, paths };
}
const isVerb = (verb: string): verb is 'get' | 'post' | 'patch' | 'put' | 'delete' =>
['get', 'post', 'patch', 'put', 'delete'].includes(verb);
const isDraft = (operation: unknown) => {
if (!operation || typeof operation !== 'object') {
return false;
}
return operation['x-draft'] === true;
};
function removeDeprecatedObjectType({ openAPIDocument }: { openAPIDocument: Context['openAPIDocument'] }) {
const schemas = Object.fromEntries(
Object.entries(openAPIDocument.components?.schemas ?? {}).map(([schemaName, schema]) => {
if (schemaName === 'Column') {
const updatedSchema = {
...schema,
properties: {
...(schema as any).properties,
type: {
...(schema as any).properties.type,
// Make Column type a string without enum values
enum: undefined
}
}
};
// Remove `columns` property
delete updatedSchema.properties['columns'];
return [schemaName, updatedSchema];
}
return [schemaName, schema];
})
);
return { ...openAPIDocument, components: { ...openAPIDocument.components, schemas } };
}