This question already has answers here:
In Swagger, how to define an API that consumes a file along with a schema parameter?
(3 answers)
Closed 2 years ago.
I'm using Swagger 2.0 and I have a problem to send multiple post parameters. I have a swagger error Operation cannot have a body parameter and a formData parameter and I don't know how to fix it. In my definition I have a body parameter and this parameter need a JSON format but a side I have other parameter like files to upload and filename.
How can I do to send body and formData parameters both ?
Here is the web service definition :
/updateDatas:
post:
summary: Upadate datas
description: |
Update datas
consumes:
- multipart/form-data
produces:
- application/json
parameters:
- name: firstFileName
in: formData
description: First file name.
required: true
type: string
- name: secondFileName
in: formData
description: Second file name.
required: true
type: string
- name: datas
in: body
description: Json object informations.
required: true
schema:
$ref: '#/definitions/Datas'
- name: firstFile
in: formData
description: First file .jpg
required: true
type: file
- name: clientFile
in: formData
description: Second file .jpg
required: true
type: file
tags:
- Application
responses:
'200':
description: Uploaded
schema:
$ref: '#/definitions/Upload'
'401':
description: Unauthorized Bad Token
According to the swagger specifications see, type:body and type:formData cannot exist together for the same operation.
One way to resolve the problem is to set "datas" as form parameter with the type "file". Here is an example:
parameters:
- name: petId
in: path
description: ID of pet to update
required: true
type: integer
format: int64
- name: additionalMetadata
in: formData
description: Additional data to pass to server
required: false
type: string
- name: file
in: formData
description: file to upload
required: false
type: file
Ref: https://github.com/swagger-api/swagger-codegen/blob/master/modules/swagger-codegen/src/test/resources/2_0/petstore.yaml#L257
UPDATE: body parameters and form parameters cannot co-exist: https://github.com/OAI/OpenAPI-Specification/blob/master/versions/2.0.md#parameterObject
Body - The payload that's appended to the HTTP request. Since there can only be one payload, there can only be one body parameter. The name of the body parameter has no effect on the parameter itself and is used for documentation purposes only. Since Form parameters are also in the payload, body and form parameters cannot exist together for the same operation.
Related
I'm using swagger to describe a simple endpoint to upload file with date(int64). There is request body:
put:
tags:
- files
description: Add an associated file to a project
operationId: addFile
parameters:
- name: projectId
in: path
required: true
schema:
type: string
format: uuid
requestBody:
content:
multipart/form-data:
schema:
$ref: "#/components/schemas/AddFileToProjectRequestBody"
required: true
responses:
200:
description: Successful
content: {}
and schema:
AddFileToProjectRequestBody:
required:
- file
type: object
properties:
file:
type: string
format: binary
description: The file to upload
fileDate:
type: integer
format: int64
minimum: 0
description: File modified date (Unix timestamp in milliseconds)
If I upload a simple file it works fine. But if I am trying to add a fileDate I get an error.
"request body has an error: doesn't match the schema: Error at "/fileDate": Field must be set to integer or not be present"
Looks like it fails to read number as int. Can someone explain to me why? I have tried to change it to string and it worked, but doesn't look logical to me to set date as string.
UPD:
------WebKitFormBoundaryGs2
Content-Disposition: form-data; name="fileDate"
1670485649000
------WebKitFormBoundaryGs2
Content-Disposition: form-data; name="projectFile"; filename="1.txt"
Content-Type: text/plain
------WebKitFormBoundaryGs2--
I registered at SwaggerHub and created a new API using OpenAPI 3.0. In my API, the /tasks path has 2 non-required parameters, but I can not set them as not required - the editor shows the "Not allowed Values" error.
Here's my API definition:
openapi: 3.0.0
info:
description: A Simple IP Address API
title: VTasks
version: v1
servers:
# Added by API Auto Mocking Plugin
- description: SwaggerHub API Auto Mocking
url: https://virtserver.swaggerhub.com/petrogromovo/Vtasks/1.0.0
- description: SwaggerHub API Auto Mocking
url: http://hosting.tk
paths:
/tasks:
get:
tags:
- tasks
summary: Get paginated / filtered tasks listing
operationId: tasks
parameters:
- name: page
in: path
description: The page number to be fetched. If missed default 1.
required: true
schema:
type: integer
- name: order_by
in: path
description: The order_by be fetched.
required: false // ERROR : should be equal to one of the allowed values allowedValues: true
schema:
type: string
- name: filter
in: path
description: The filter for title field.
required: false // ERROR : should be equal to one of the allowed values allowedValues: true
schema:
type: string
responses:
'200':
description: successful operation
'400':
description: Invalid tasks supplied
'404':
description: tasks were not found
But if I remove the required attributes, I get 2 errors:
should have required property 'required'
missingProperty: required
What is the valid syntax?
Are these parameters supposed to be path parameters or query parameters?
Path parameters (in: path) are part of the endpoint path, and as such must be indicated by {...} in the path template:
paths:
/tasks/{page}/{order_by}/{filter}:
Path parameters are always required, i.e. they must have required: true.
Query parameters are send in the query string, e.g. /tasks?page=...&order_by=.... To use query parameters, change the parameter location to in: query.
More information: Describing Parameters
In OpenAPI 2.0, in: body and in: formData parameters cannot exist together for the same operation, according to Swagger send body and formData parameter and OpenAPI 2.0 Specification. That makes sense.
But I'm using OpenAPI 3.0 and I wonder if there is a way to switch requestBody according to a path parameter? When store is path1, requestBody should use content with application/json; when store is path2, requestBody should use content with multipart/form-data.
/customs/{store}:
post:
description: Customs server calls Nomad to receive the filing result of one
order
operationId: post_customs_callback
parameters:
- description: ID of the store.
explode: true
in: path
name: store
required: true
schema:
type: string
style: simple
requestBody:
required: true
content:
multipart/form-data:
schema:
type: object
properties: # Request parts
openReq:
type: string
# application/json:
# schema:
# type: string
description: Order details
OpenAPI Specification does not have a way to vary request/response body based on specific parameter values. However, in your scenario you can use two non-parameterized paths instead – /customs/path1 for JSON requests and /customs/path2 for multipart requests.
openapi: 3.0.0
...
paths:
/customs/path1:
post:
...
requestBody:
required: true
content:
application/json:
schema:
...
/customs/path2:
post:
...
requestBody:
required: true
content:
multipart/form-data:
schema:
...
I have this 2 GET requests one is /report and the second one is /report/{id}.
paths:
/report:
get:
operationId: getReportsList
responses:
'200':
description: List of reports
content:
application/json:
schema:
items:
$ref: '#/components/schemas/Metadata'
get:
operationId: getReportById
parameters:
- in: path
name: id
required: true
schema:
type: string
responses:
'200':
description: Report is finished and returned
content:
application/json:
schema:
$ref: '#/components/schemas/Report'
SwaggerHub shows an error against second GET with a description
duplicated mapping key
Could you tell me what am I doing wrong and why Swagger does think that URLs with and without path variable are the same?
Add a new path where explicitly append your path variable /report/{id} for the second GET.
I have an OpenAPI v3 specification file with the following (showing just fragments):
paths:
/global/name:
get:
description: Some description
tags:
- Global settings
operationId: getGlobalSettingsName
responses:
# Response code
'200':
description: Successful response
content:
application/json:
schema:
$ref: '#/components/schemas/globalSettingsName'
components:
schemas:
globalSettingsName:
type: object
properties:
name:
type: integer
description: 'ID'
example: 1
required:
- name
but the server response is:
{
"name": "somestring"
}
Note the name property type is integer and in the server response, it is a string (on purpose) but dredd request passes (success).
Doesn't dredd check for response property types?
I redefined the response as string (not JSON):
responses:
# Response code
'200':
description: Successful response
content:
application/json:
schema:
type: string
and dredd doesn't complain about either.
I even changed the property of the schema:
globalSettingsName:
type: object
properties:
www:
type: string
description: 'some description'
example: 'somestring'
required:
- www
And same (success) result when it is expected to fail.
Aren't these validation supported by dredd? Am I using specification wrong?
It results that the current version (8.0.5) only supports example value in content: https://github.com/apiaryio/dredd/issues/1281