import React, { Component } from 'react' import PropTypes from 'prop-types' import { connect } from 'react-redux' import { Button, Input, Select, Card, Alert, Spin, Icon, message } from 'antd' import { autobind } from 'core-decorators'; import crossRequest from 'cross-request'; import { withRouter } from 'react-router'; import axios from 'axios'; import URL from 'url'; import { } from '../../../actions/group.js' import './InterfaceTest.scss' const { TextArea } = Input; const InputGroup = Input.Group; const Option = Select.Option; @connect( state => ({ reqParams: state.addInterface.reqParams, method: state.addInterface.method, url: state.addInterface.url, seqGroup: state.addInterface.seqGroup, interfaceName: state.addInterface.interfaceName, interfaceProject: state.addInterface.project }) ) @withRouter export default class InterfaceTest extends Component { static propTypes = { reqParams: PropTypes.string, method: PropTypes.string, url: PropTypes.string, interfaceName: PropTypes.string, seqGroup: PropTypes.array, match: PropTypes.object, interfaceProject: PropTypes.object } state = { res: '', method: 'GET', domains: [], pathname: '', query: {}, params: {}, paramsNotJson: false, headers: {}, currDomain: '', paramsType: 'from' } constructor(props) { super(props) } componentWillMount() { this.getInterfaceState() } componentWillReceiveProps(nextProps) { this.getInterfaceState(nextProps) } @autobind getInterfaceState(nextProps) { const props = nextProps || this.props; const { method, url, seqGroup, interfaceProject } = props; const { prd_host, basepath, protocol, env } = interfaceProject; const pathname = (basepath + url).replace(/\/+/g, '/'); const domains = {prd: protocol + '://' + prd_host}; env.forEach(item => { domains[item.name] = item.domain; }) const query = []; let params = []; let reqParams = this.props.reqParams ? this.props.reqParams : '{}'; let paramsNotJson = false; try { reqParams = JSON.parse(reqParams); // paramsNotJson = false; } catch (e) { // paramsNotJson = true; reqParams = {}; message.error('请求参数不是 JSON 格式'); } if (method === 'GET') { Object.keys(reqParams).forEach(key => { const value = typeof reqParams[key] === 'object' ? JSON.stringify(reqParams[key]) : reqParams[key].toString(); query.push({key, value}) }) } else if (method === 'POST') { // params = reqParams; Object.keys(reqParams).forEach(key => { const value = typeof reqParams[key] === 'object' ? JSON.stringify(reqParams[key]) : reqParams[key].toString(); query.push({key, value, type: 'text'}) }) } const headers = [] let contentTypeIndex = -1; seqGroup.forEach((headerItem, index) => { if (headerItem.name) { // TODO 'Content-Type' 排除大小写不同格式影响 if (headerItem.name === 'Content-Type'){ contentTypeIndex = index; headerItem.value = headerItem.value || 'application/x-www-form-urlencoded'; } headers.push({name: headerItem.name, value: headerItem.value}); } }) if (contentTypeIndex === -1) { headers.push({name: 'Content-Type', value: 'application/x-www-form-urlencoded'}); } this.setState({ method, domains, pathname, query, params, paramsNotJson, headers, currDomain: domains.prd, loading: false, paramsType: 'form' }); } @autobind requestInterface() { const { headers, params, currDomain, method, pathname, query } = this.state; const urlObj = URL.parse(currDomain); const href = URL.format({ protocol: urlObj.protocol || 'http', host: urlObj.host, pathname, query: this.getQueryObj(query) }); this.setState({ loading: true }) crossRequest({ url: href, method, headers: this.getHeadersObj(headers), data: this.arrToObj(params), files: this.getFiles(params), success: (res) => { try { res = JSON.parse(res) } catch (e) { null } this.setState({res}) this.setState({ loading: false }) }, error: (err) => { this.setState({res: err || '请求失败'}) this.setState({ loading: false }) } }) } @autobind changeDomain(value) { this.setState({ currDomain: value }); } @autobind selectDomain(value) { this.setState({ currDomain: value }); } @autobind changeHeader(e, index, isName) { const headers = JSON.parse(JSON.stringify(this.state.headers)); const v = e.target.value; if (isName) { headers[index].name = v; } else { headers[index].value = v; } this.setState({ headers }); } @autobind addHeader() { const { headers } = this.state; this.setState({headers: headers.concat([{name: '', value: ''}])}) } @autobind deleteHeader(index) { const { headers } = this.state; this.setState({headers: headers.filter((item, i) => +index !== +i)}); } @autobind setContentType(type) { const headersObj = this.getHeadersObj(this.state.headers); headersObj['Content-Type'] = type; this.setState({headers: this.objToArr(headersObj, 'name')}) } @autobind changeQuery(e, index, isKey) { const query = JSON.parse(JSON.stringify(this.state.query)); const v = e.target.value; if (isKey) { query[index].key = v; } else { query[index].value = v; } this.setState({ query }); } @autobind addQuery() { const { query } = this.state; this.setState({query: query.concat([{key: '', value: ''}])}) } @autobind deleteQuery(index) { const { query } = this.state; this.setState({query: query.filter((item, i) => +index !== +i)}); } @autobind changeParams(e, index, type) { const params = JSON.parse(JSON.stringify(this.state.params)); switch (type) { case 'key': params[index].key = e.target.value break; case 'type': params[index].type = e break; case 'value': if (params[index].type === 'file') { params[index].value = e.target.id } else { params[index].value = e.target.value } break; default: break; } if (type === 'type' && e === 'file') { this.setContentType('multipart/form-data') } this.setState({ params }); } @autobind addParams() { const { params } = this.state; this.setState({params: params.concat([{key: '', value: '', type: 'text'}])}) } @autobind deleteParams(index) { const { params } = this.state; this.setState({params: params.filter((item, i) => +index !== +i)}); } @autobind changeMethod(value) { this.setState({ method: value }); } @autobind changePath(e) { const path = e.target.value; const urlObj = URL.parse(path, true); this.setState({ query: this.objToArr(urlObj.query), pathname: urlObj.pathname }) } @autobind changeParamsType(value) { this.setState({paramsType: value}) } hasCrossRequestPlugin() { const dom = document.getElementById('y-request'); return dom.getAttribute('key') === 'yapi'; } objToArr(obj, key, value) { const keyName = key || 'key'; const valueName = value || 'value'; const arr = [] Object.keys(obj).forEach((_key) => { if (_key) { arr.push({[keyName]: _key, [valueName]: obj[_key]}); } }) return arr; } arrToObj(arr) { const obj = {}; arr.forEach(item => { if (item.key && item.type !== 'file') { obj[item.key] = item.value || ''; } }) return obj; } getFiles(params) { const files = {}; params.forEach(item => { if (item.key && item.type === 'file') { files[item.key] = item.value } }) return files; } getQueryObj(query) { const queryObj = {}; query.forEach(item => { if (item.key) { queryObj[item.key] = item.value || ''; } }) return queryObj; } getHeadersObj(headers) { const headersObj = {}; headers.forEach(item => { if (item.name && item.value) { headersObj[item.name] = item.value; } }) return headersObj; } @autobind fileChange(e, index) { console.log(e) console.log(index) } render () { const { interfaceName } = this.props; const { method, domains, pathname, query, headers, params, currDomain, paramsType } = this.state; const hasPlugin = this.hasCrossRequestPlugin(); const search = decodeURIComponent(URL.format({query: this.getQueryObj(query)})); console.log(axios) window.axios = axios return (
{ hasPlugin ? '' : 温馨提示:当前正在使用接口测试服务,请安装我们为您免费提供的  测试增强插件 [点击获取]!
} type="warning" /> }
{interfaceName}
{/* url */}
(请求测试真实接口)
{ query.map((item, index) => { return (
this.changeQuery(e, index, true)} style={{display: 'inline-block', width: 200, margin: 10}} />{' = '} this.changeQuery(e, index)} style={{display: 'inline-block', width: 200, margin: 10}} /> this.deleteQuery(index)} />
) }) }
{ headers.map((item, index) => { return (
this.changeHeader(e, index, true)} style={{display: 'inline-block', width: 200, margin: 10}} />{' = '} this.changeHeader(e, index)} style={{display: 'inline-block', width: 200, margin: 10}} /> this.deleteHeader(index)} />
) }) }
{ method === 'POST' && paramsType !== 'form' && paramsType !== 'file' &&
{paramsType}
} { method === 'POST' && paramsType === 'form' && (
{ params.map((item, index) => { return (
this.changeParams(e, index, 'key')} style={{display: 'inline-block', width: 200, margin: 10}} /> []{' = '} {item.type === 'file' ? this.changeParams(e, index, 'value')} multiple style={{display: 'inline-block', width: 200, margin: 10}} /> : this.changeParams(e, index, 'value')} style={{display: 'inline-block', width: 200, margin: 10}} /> }
) }) }
) } { method === 'POST' && paramsType === 'file' && (
) } { method !== 'POST' && (
GET 请求没有 Body。
) }
) } }