diff --git a/packages/editor/src/editor/oas/v2/OasV2ParameterObjectsParser.ts b/packages/editor/src/editor/oas/v2/OasV2ParameterObjectsParser.ts index f40a0759..dbae7f60 100644 --- a/packages/editor/src/editor/oas/v2/OasV2ParameterObjectsParser.ts +++ b/packages/editor/src/editor/oas/v2/OasV2ParameterObjectsParser.ts @@ -11,6 +11,10 @@ export class OasV2ParameterObjectsParser extends BaseOasParameterObjectsParser< OpenAPIV2.Document, OpenAPIV2.ReferenceObject | OpenAPIV2.Parameter > { + private readonly DEFAULT_CONSUME_MEDIA_TYPE: OpenAPIV2.MimeTypes = [ + 'application/json' + ]; + constructor(doc: OpenAPIV2.Document, dereferencedDoc: OpenAPIV2.Document) { super(doc, dereferencedDoc); } @@ -73,14 +77,38 @@ export class OasV2ParameterObjectsParser extends BaseOasParameterObjectsParser< this.dereferencedDoc, jsonPointer.compile(jsonPointer.parse(pointer).slice(0, -2)) ); - const mimeTypes = operationObject.consumes || ['application/json']; + + if ('$ref' in parameter.schema) { + parameter = jsonPointer.get(this.dereferencedDoc, pointer); + } + const value = parameter.schema?.default; - return mimeTypes.map((mimeType) => ({ - paramType: 'requestBody', - bodyType: mimeType, - ...(value != null ? { value } : {}), - valueJsonPointer: this.getValueJsonPointer(`${pointer}/schema`) - })); + return this.resolveOperationConsumeMediaTypes(operationObject).map( + (mediaType) => ({ + paramType: 'requestBody', + bodyType: mediaType, + ...(value != null ? { value } : {}), + valueJsonPointer: this.getValueJsonPointer(`${pointer}/schema`) + }) + ); + } + + private resolveOperationConsumeMediaTypes( + operation: OpenAPIV2.OperationObject + ): OpenAPIV2.MimeTypes { + let mediaTypes: OpenAPIV2.MimeTypes; + + if (operation.consumes?.length) { + mediaTypes = operation.consumes; + } else if (this.doc.consumes?.length) { + mediaTypes = this.doc.consumes; + } + + mediaTypes = mediaTypes + ?.map((mediaType) => mediaType?.trim()) + .filter(Boolean); + + return mediaTypes?.length ? mediaTypes : this.DEFAULT_CONSUME_MEDIA_TYPE; } } diff --git a/packages/editor/tests/fixtures/oas2-missing-consumes.result.json b/packages/editor/tests/fixtures/oas2-missing-consumes.result.json new file mode 100644 index 00000000..70360883 --- /dev/null +++ b/packages/editor/tests/fixtures/oas2-missing-consumes.result.json @@ -0,0 +1,36 @@ +{ + "children": [ + { + "children": [ + { + "jsonPointer": "/paths/~1pet/post", + "method": "POST", + "parameters": [ + { + "bodyType": "application/json", + "paramType": "requestBody", + "value": { + "name": "Jack" + }, + "valueJsonPointer": "/paths/~1pet/post/parameters/0/schema/default" + } + ], + "path": "/pet" + } + ], + "jsonPointer": "/paths/~1pet", + "path": "/pet" + } + ], + "jsonPointer": "/", + "name": "Swagger Petstore", + "parameters": [ + { + "name": "host", + "paramType": "variable", + "value": "petstore.swagger.io", + "valueJsonPointer": "/host" + } + ], + "path": "/" +} diff --git a/packages/editor/tests/fixtures/oas2-missing-consumes.yaml b/packages/editor/tests/fixtures/oas2-missing-consumes.yaml new file mode 100644 index 00000000..a88b0e9a --- /dev/null +++ b/packages/editor/tests/fixtures/oas2-missing-consumes.yaml @@ -0,0 +1,32 @@ +swagger: '2.0' +info: + title: Swagger Petstore + version: 1.0.0 +host: petstore.swagger.io +basePath: /v2 +schemes: + - https +paths: + /pet: + post: + parameters: + - in: body + name: body + schema: + $ref: '#/definitions/Pet' + responses: + 200: + description: successful operation +definitions: + Pet: + properties: + name: + example: doggie + type: string + required: + - name + type: object + xml: + name: Pet + default: + name: Jack diff --git a/packages/editor/tests/fixtures/oas2-override-consumes.result.json b/packages/editor/tests/fixtures/oas2-override-consumes.result.json new file mode 100644 index 00000000..72d0de20 --- /dev/null +++ b/packages/editor/tests/fixtures/oas2-override-consumes.result.json @@ -0,0 +1,59 @@ +{ + "children": [ + { + "children": [ + { + "jsonPointer": "/paths/~1pet/post", + "method": "POST", + "parameters": [ + { + "bodyType": "application/x-www-form-urlencoded", + "paramType": "requestBody", + "value": { + "name": "Jack" + }, + "valueJsonPointer": "/paths/~1pet/post/parameters/0/schema/default" + }, + { + "bodyType": "multipart/form-data", + "paramType": "requestBody", + "value": { + "name": "Jack" + }, + "valueJsonPointer": "/paths/~1pet/post/parameters/0/schema/default" + } + ], + "path": "/pet" + }, + { + "jsonPointer": "/paths/~1pet/put", + "method": "PUT", + "parameters": [ + { + "bodyType": "application/json", + "paramType": "requestBody", + "value": { + "name": "Jack" + }, + "valueJsonPointer": "/paths/~1pet/put/parameters/0/schema/default" + } + ], + "path": "/pet" + } + ], + "jsonPointer": "/paths/~1pet", + "path": "/pet" + } + ], + "jsonPointer": "/", + "name": "Swagger Petstore", + "parameters": [ + { + "name": "host", + "paramType": "variable", + "value": "petstore.swagger.io", + "valueJsonPointer": "/host" + } + ], + "path": "/" +} diff --git a/packages/editor/tests/fixtures/oas2-override-consumes.yaml b/packages/editor/tests/fixtures/oas2-override-consumes.yaml new file mode 100644 index 00000000..4a489d59 --- /dev/null +++ b/packages/editor/tests/fixtures/oas2-override-consumes.yaml @@ -0,0 +1,49 @@ +swagger: '2.0' +info: + title: Swagger Petstore + version: 1.0.0 +host: petstore.swagger.io +basePath: /v2 +schemes: + - https +consumes: + - application/xml +paths: + /pet: + post: + consumes: + - application/x-www-form-urlencoded + - multipart/form-data + parameters: + - in: body + name: body + schema: + $ref: '#/definitions/Pet' + responses: + 200: + description: successful operation + put: + consumes: + - + parameters: + - in: body + name: body + schema: + $ref: '#/definitions/Pet' + responses: + 200: + description: successful operation +definitions: + Pet: + properties: + name: + example: doggie + type: string + required: + - name + type: object + xml: + name: Pet + default: + name: Jack + diff --git a/packages/editor/tests/oas2.spec.ts b/packages/editor/tests/oas2.spec.ts index 73f267ea..b06228a9 100644 --- a/packages/editor/tests/oas2.spec.ts +++ b/packages/editor/tests/oas2.spec.ts @@ -92,6 +92,33 @@ describe('OasV2Editor', () => { expect(result).toEqual(expected); }); + it.each([ + { + testCase: 'operation and root consumes nodes are missing', + input: 'oas2-missing-consumes.yaml', + expected: 'oas2-missing-consumes.result.json' + }, + { + testCase: 'operation consumes overrides root consumes node', + input: 'oas2-override-consumes.yaml', + expected: 'oas2-override-consumes.result.json' + } + ])('should pick media type when $testCase', async ({ input, expected }) => { + const sourceYaml = readFileSync( + resolve(__dirname, `./fixtures/${input}`), + 'utf-8' + ); + await openApiParser.setup(sourceYaml); + + const expectedJson = JSON.parse( + readFileSync(resolve(__dirname, `./fixtures/${expected}`), 'utf-8') + ); + + const result = openApiParser.parse(); + + expect(result).toEqual(expectedJson); + }); + it('should be exception on call "parse" before "setup"', () => expect(() => openApiParser.parse()).toThrowError( 'You have to call "setup" to initialize the document'