Skip to content

Commit 0b5bf99

Browse files
Merge pull request #685 from bitgopatmcl/fix-ref-titles
Use `allOf` for schemas that are refs
2 parents 9aaaad1 + 0321fa9 commit 0b5bf99

File tree

2 files changed

+154
-2
lines changed

2 files changed

+154
-2
lines changed

packages/openapi-generator/src/openapi.ts

Lines changed: 7 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -173,6 +173,13 @@ export function convertRoutesToOpenAPI(
173173
const openapiSchema = schemaToOpenAPI(schema);
174174
if (openapiSchema === undefined) {
175175
return acc;
176+
} else if ('$ref' in openapiSchema) {
177+
return {
178+
...acc,
179+
[name]: {
180+
allOf: [{ title: name }, openapiSchema],
181+
},
182+
};
176183
} else {
177184
return {
178185
...acc,

packages/openapi-generator/test/openapi.test.ts

Lines changed: 147 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -10,6 +10,7 @@ import {
1010
parseRoute,
1111
Project,
1212
type Route,
13+
type Schema,
1314
} from '../src';
1415

1516
async function testCase(
@@ -23,6 +24,7 @@ async function testCase(
2324

2425
const project = new Project();
2526
const routes: Route[] = [];
27+
const schemas: Record<string, Schema> = {};
2628
const errors: string[] = [];
2729
for (const symbol of sourceFile.symbols.declarations) {
2830
if (symbol.init !== undefined) {
@@ -36,7 +38,7 @@ async function testCase(
3638
}
3739
const result = parseRoute(project, routeSchemaE.right);
3840
if (E.isLeft(result)) {
39-
errors.push(result.left);
41+
schemas[symbol.name] = routeSchemaE.right;
4042
} else {
4143
routes.push(result.right);
4244
}
@@ -46,7 +48,7 @@ async function testCase(
4648
const actual = convertRoutesToOpenAPI(
4749
{ title: 'Test', version: '1.0.0' },
4850
routes,
49-
{},
51+
schemas,
5052
);
5153

5254
assert.deepStrictEqual(errors, expectedErrors);
@@ -538,3 +540,146 @@ testCase('object with no required properties', EMPTY_REQUIRED, {
538540
schemas: {},
539541
},
540542
});
543+
544+
const SCHEMA_REF = `
545+
import * as t from 'io-ts';
546+
import * as h from '@api-ts/io-ts-http';
547+
548+
export const route = h.httpRoute({
549+
path: '/foo',
550+
method: 'GET',
551+
request: t.type({
552+
body: Foo,
553+
}),
554+
response: {
555+
/** foo response */
556+
200: t.string
557+
},
558+
});
559+
560+
const Foo = t.type({ foo: t.string });
561+
`;
562+
563+
testCase('request body ref', SCHEMA_REF, {
564+
openapi: '3.0.0',
565+
info: {
566+
title: 'Test',
567+
version: '1.0.0',
568+
},
569+
paths: {
570+
'/foo': {
571+
get: {
572+
parameters: [],
573+
requestBody: {
574+
content: {
575+
'application/json': {
576+
schema: {
577+
$ref: '#/components/schemas/Foo',
578+
},
579+
},
580+
},
581+
},
582+
responses: {
583+
200: {
584+
description: 'foo response',
585+
content: {
586+
'application/json': {
587+
schema: {
588+
type: 'string',
589+
},
590+
},
591+
},
592+
},
593+
},
594+
},
595+
},
596+
},
597+
components: {
598+
schemas: {
599+
Foo: {
600+
title: 'Foo',
601+
type: 'object',
602+
properties: {
603+
foo: {
604+
type: 'string',
605+
},
606+
},
607+
required: ['foo'],
608+
},
609+
},
610+
},
611+
});
612+
613+
const SCHEMA_DOUBLE_REF = `
614+
import * as t from 'io-ts';
615+
import * as h from '@api-ts/io-ts-http';
616+
617+
export const route = h.httpRoute({
618+
path: '/foo',
619+
method: 'GET',
620+
request: t.type({
621+
body: Bar,
622+
}),
623+
response: {
624+
/** foo response */
625+
200: t.string
626+
},
627+
});
628+
629+
const Foo = t.type({ foo: t.string });
630+
631+
const Bar = Foo;
632+
`;
633+
634+
testCase('request body double ref', SCHEMA_DOUBLE_REF, {
635+
openapi: '3.0.0',
636+
info: {
637+
title: 'Test',
638+
version: '1.0.0',
639+
},
640+
paths: {
641+
'/foo': {
642+
get: {
643+
parameters: [],
644+
requestBody: {
645+
content: {
646+
'application/json': {
647+
schema: {
648+
$ref: '#/components/schemas/Bar',
649+
},
650+
},
651+
},
652+
},
653+
responses: {
654+
200: {
655+
description: 'foo response',
656+
content: {
657+
'application/json': {
658+
schema: {
659+
type: 'string',
660+
},
661+
},
662+
},
663+
},
664+
},
665+
},
666+
},
667+
},
668+
components: {
669+
schemas: {
670+
Foo: {
671+
title: 'Foo',
672+
type: 'object',
673+
properties: {
674+
foo: {
675+
type: 'string',
676+
},
677+
},
678+
required: ['foo'],
679+
},
680+
Bar: {
681+
allOf: [{ title: 'Bar' }, { $ref: '#/components/schemas/Foo' }],
682+
},
683+
},
684+
},
685+
});

0 commit comments

Comments
 (0)