Skip to content

Commit

Permalink
feat: work on multipart/form-data support
Browse files Browse the repository at this point in the history
  • Loading branch information
albanm committed Oct 23, 2018
1 parent 17c0cd1 commit 33082ed
Show file tree
Hide file tree
Showing 7 changed files with 274 additions and 42 deletions.
80 changes: 51 additions & 29 deletions package-lock.json

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

1 change: 1 addition & 0 deletions package.json
Original file line number Diff line number Diff line change
Expand Up @@ -26,6 +26,7 @@
"test": "echo \"Error: no test specified\" && exit 1"
},
"dependencies": {
"form-data": "^2.3.3",
"json-formatter-js": "^2.2.0",
"json-schema-ref-parser": "^5.0.3",
"json-schema-view-js": "^1.0.1",
Expand Down
81 changes: 81 additions & 0 deletions src/MultipartForm.vue
Original file line number Diff line number Diff line change
@@ -0,0 +1,81 @@
<template lang="html">
<md-layout column md-flex="100">
<md-layout row md-flex="100" v-for="key in Object.keys(properties)" :key="key">
<!-- File upload -->
<md-input-container v-if="properties[key].type === 'string' && properties[key].format === 'binary'">
<label>{{properties[key].title || key}}</label>
<md-file @selected="files => onFileUpload(key, files)"></md-file>
</md-input-container>

<!-- simple enum -->
<md-input-container v-else-if="properties[key].type === 'array' && properties[key].items.enum">
<label>{{properties[key].title || key}}</label>
<md-select v-model="model[key]" multiple>
<md-option v-for="val in properties[key].items.enum" :key="val" :value="val">{{val}}</md-option>
</md-select>
</md-input-container>

<!-- multi enum -->
<md-input-container v-else-if="properties[key].enum">
<label>{{properties[key].title || key}}</label>
<md-select v-model="model[key]">
<md-option v-for="val in properties[key].enum" :key="val" :value="val">{{val}}</md-option>
</md-select>
</md-input-container>

<!-- boolean -->
<md-checkbox v-else-if="properties[key].type === 'boolean'" v-model="model[key]">{{properties[key].title || key}}</md-checkbox>

<!-- generic input -->
<md-input-container v-else-if="properties[key].type === 'string' || properties[key].type === 'integer' || properties[key].type === 'number'">
<label>{{properties[key].title || key}}</label>
<md-input v-model="model[key]" :type="properties[key].type === 'string' ? 'text' : 'number'"></md-input>
</md-input-container>

<!-- objects in textarea -->
<md-input-container v-else>
<label>{{properties[key].title || key}}</label>
<md-textarea v-model="model[key]"></md-textarea>
</md-input-container>
</md-layout>
</md-layout>
</template>

<script>
const FormData = require('form-data')
export default {
props: ['requestBody'],
data() {
return {model: {}}
},
computed: {
properties() {
return this.requestBody.content['multipart/form-data'].schema.properties
}
},
mounted() {
Object.keys(this.properties).forEach(key => {
this.$set(this.model, key, null)
})
},
methods: {
onFileUpload(key, files) {
this.model[key] = files[0]
},
getFormData() {
const form = new FormData()
Object.keys(this.properties)
.filter(key => this.model[key] !== null)
.forEach(key => {
console.log('APPEND', key, this.model[key])
form.append(key, this.model[key])
})
return form
}
}
}
</script>

<style lang="css">
</style>
17 changes: 11 additions & 6 deletions src/OpenApi.vue
Original file line number Diff line number Diff line change
Expand Up @@ -58,15 +58,15 @@
</md-tab>
<md-tab v-if="api.servers && api.servers.length" md-label="Make request">
<md-layout md-row>
<md-layout md-column md-flex="40">
<md-layout md-column md-flex-small="100" md-flex="40">
<h2>Request</h2>
<request-form :selectedEntry="selectedEntry" :currentRequest="currentRequest"></request-form>
<request-form ref="requestForm" :selectedEntry="selectedEntry" :currentRequest="currentRequest"></request-form>
<div>
<md-button class="md-raised md-accent" @click.native="request">Execute</md-button>
</div>
</md-layout>

<md-layout md-column md-flex="60">
<md-layout md-column md-flex-small="100" md-flex="60">
<h2>Response</h2>
<response-display v-if="currentResponse" :entry="selectedEntry" :response="currentResponse"></response-display>
</md-layout>
Expand Down Expand Up @@ -281,7 +281,12 @@ export default {
},
request() {
this.currentResponse = null
fetch(this.currentRequest, this.selectedEntry, this.api).then(res => {
let formData
if (this.selectedEntry.requestBody && this.selectedEntry.requestBody.selectedType === 'multipart/form-data') {
formData = this.$refs.requestForm.getFormData()
}
console.log('formData', formData)
fetch(this.currentRequest, this.selectedEntry, this.api, formData).then(res => {
this.currentResponse = res
}, res => {
this.currentResponse = res
Expand All @@ -294,7 +299,7 @@ export default {
* HTTP requests utils
*/
function fetch(request, entry, api) {
function fetch(request, entry, api, formData) {
let params = Object.assign({}, ...(entry.parameters || [])
.filter(p => p.in === 'query' && (p.schema.type === 'array' ? request.params[p.name].length : request.params[p.name]))
.map(p => ({
Expand All @@ -319,7 +324,7 @@ function fetch(request, entry, api) {
}
if (entry.requestBody) {
httpRequest.headers['Content-type'] = entry.requestBody.selectedType
httpRequest.body = request.body
httpRequest.body = formData || request.body
}
return Vue.http(httpRequest)
}
Expand Down
Loading

0 comments on commit 33082ed

Please sign in to comment.