添加文件生成功能,支持自定义文件模板

This commit is contained in:
2024-07-13 12:29:57 +08:00
parent 34a98ab47e
commit eb50ad480e
3 changed files with 178 additions and 52 deletions

View File

@@ -1,23 +1,27 @@
import React, {Component} from 'react'; import React, {Component, Fragment} from 'react';
import {connect} from 'react-redux'; import {connect} from 'react-redux';
import PropTypes from 'prop-types'; import PropTypes from 'prop-types';
import {Form, Button, message} from 'antd'; import {Form, Button, message, Tabs, Modal, Input} from 'antd';
import {handleSwaggerUrlData} from 'client/reducer/modules/project'; import {handleSwaggerUrlData} from 'client/reducer/modules/project';
const {TabPane} = Tabs;
const FormItem = Form.Item; const FormItem = Form.Item;
const {confirm} = Modal;
import axios from 'axios'; import axios from 'axios';
import AceEditor from "../../../client/components/AceEditor/AceEditor"; import AceEditor from "../../../client/components/AceEditor/AceEditor";
// layout
const formItemLayout = { const formItemLayout = {
labelCol: { labelCol: {
lg: {span: 5}, lg: {span: 1},
xs: {span: 24}, xs: {span: 3},
sm: {span: 10} sm: {span: 2}
}, },
wrapperCol: { wrapperCol: {
lg: {span: 16}, lg: {span: 22},
xs: {span: 24}, xs: {span: 18},
sm: {span: 12} sm: {span: 20}
}, },
className: 'form-item' className: 'form-item'
}; };
@@ -50,22 +54,35 @@ export default class CodeGenTemplate extends Component {
handleSwaggerUrlData: PropTypes.func handleSwaggerUrlData: PropTypes.func
}; };
getAddTemplate(isDefault = false) {
let data = {tag_desc: "新增模板", tag: 'add'}
if (isDefault) {
data['tag_desc_t'] = '默认'
data['tag_t'] = 'default'
}
return data;
}
constructor(props) { constructor(props) {
super(props); super(props);
this.state = { this.state = {
config_data: {template_data: "", _id: null} config_data: {template_data: "", _id: null},
templateList: [],
activeKey: "default"
}; };
} }
handleSubmit = async () => { handleSubmit = async (data) => {
const {form, projectId} = this.props; const {form, projectId} = this.props;
let params = { let params = {
project_id: projectId, project_id: projectId,
template_data: this.state.config_data.template_data, tag: data.tag_t || data.tag,
tag_desc: data.tag_desc_t || data.tag_desc,
template_data: data.template_data,
uid: this.props.projectMsg.uid uid: this.props.projectMsg.uid
}; };
if (this.state.config_data._id) { if (data._id) {
params.id = this.state.config_data._id; params.id = data._id;
} }
form.validateFields(async (err, values) => { form.validateFields(async (err, values) => {
if (!err) { if (!err) {
@@ -73,6 +90,7 @@ export default class CodeGenTemplate extends Component {
await axios.post('/api/plugin/template/save', assignValue).then(res => { await axios.post('/api/plugin/template/save', assignValue).then(res => {
if (res.data.errcode === 0) { if (res.data.errcode === 0) {
message.success('保存成功'); message.success('保存成功');
this.getSyncData();
} else { } else {
message.error(res.data.errmsg); message.error(res.data.errmsg);
} }
@@ -86,7 +104,8 @@ export default class CodeGenTemplate extends Component {
UNSAFE_componentWillMount() { UNSAFE_componentWillMount() {
//查询同步任务 //查询同步任务
this.setState({ this.setState({
config_data: {} config_data: {template_data: "", _id: null},
templateList: []
}); });
this.getSyncData(); this.getSyncData();
} }
@@ -95,50 +114,158 @@ export default class CodeGenTemplate extends Component {
let projectId = this.props.projectMsg._id; let projectId = this.props.projectMsg._id;
let result = await axios.get('/api/plugin/template/get?projectId=' + projectId); let result = await axios.get('/api/plugin/template/get?projectId=' + projectId);
if (result.data.errcode === 0) { if (result.data.errcode === 0) {
if (result.data.data) { if (result.data.data && result.data.data.length) {
let templateData = result.data.data.find(it => it.tag === "default") let defaultTemplate = result.data.data.find(it => it.tag === "default")
if (templateData == null) { if (defaultTemplate == null) {
templateData = result.data.data[0] defaultTemplate = result.data.data[0] || {}
} }
this.setState({ this.setState({
config_data: templateData defaultTemplate,
activeKey: defaultTemplate.tag,
templateList: result.data.data
});
} else {
this.setState({
activeKey: "add",
templateList: [this.getAddTemplate(true)]
}); });
} }
} }
} }
handleTemplateInput = e => { handleTemplateInput = (e, data) => {
let config_data = this.state.config_data; data.template_data = e.text;
config_data.template_data = e.text; this.setState()
this.setState({
config_data: config_data
});
}; };
onTabChange(key) {
this.setState({
activeKey: key
})
}
async onTabEdit(targetKey, action) {
// this[action](targetKey);
let templateData = this.state.templateList.find(it => it.tag === targetKey)
console.log(targetKey, action, templateData)
confirm({
title: '是否要删除此模板?',
content: '删除后将无法找回,是否继续',
onOk: async () => {
await axios.delete('/api/plugin/template/' + templateData._id);
message.success("删除成功")
this.getSyncData();
},
onCancel() {
}
});
}
addNewTemplate() {
if (this.state.templateList.find(it => it.tag === 'add')) {
message.info("请先保存新增的模板")
this.setState({
activeKey: 'add'
})
return;
}
let data = [...this.state.templateList, this.getAddTemplate()];
console.log(data)
this.setState({
templateList: data,
activeKey: 'add'
})
}
render() { render() {
const templateEditor = ( const {getFieldDecorator} = this.props.form;
<FormItem {...formItemLayout} label="默认模板">
<AceEditor
data={this.state.config_data.template_data}
onChange={this.handleTemplateInput}
style={{minHeight: '300px'}}
/>
</FormItem> let panes = [];
console.log("this.state.templateList", this.state.templateList)
if (this.state.templateList) {
panes = this.state.templateList.map(it => {
return {
title: it.tag_desc,
key: it.tag,
content: it.tag,
data: it
}
})
}
let newTemplateData = this.state.templateList.find(it => it.tag === 'add');
let onFieldChange = (e, field) => {
newTemplateData[field] = e.text
}
const addContent = this.state.activeKey === 'add' && newTemplateData.tag_t !== 'default' && (
<Fragment key="add">
<FormItem label="文件名" {...formItemLayout}>
{getFieldDecorator('tag', {
rules: [
{
required: true,
message: '文件名必填哦,用来标识你的每个不同的模板'
}
],
initialValue: newTemplateData.tag_t
})(<Input onChange={(e) => onFieldChange(e, "tag_t")}/>)}
</FormItem>
<FormItem label="文件描述" {...formItemLayout}>
{getFieldDecorator('tag_desc', {
rules: [
{
required: true,
message: '文件描述必填哦'
}
],
initialValue: newTemplateData.tag_desc_t
})(<Input onChange={(e) => onFieldChange(e, "tag_desc_t")}/>)}
</FormItem>
</Fragment>
) )
return ( return (
<div className="m-panel"> <div className="m-panel">
<Form> <Tabs
<div> hideAdd
{templateEditor} onChange={key => this.onTabChange(key)}
</div> activeKey={this.state.activeKey}
<FormItem {...tailFormItemLayout}> type="card"
<Button type="primary" htmlType="submit" icon="save" size="large" onClick={this.handleSubmit}> tabBarExtraContent={<Button type="primary" onClick={() => this.addNewTemplate()}>新增模板</Button>}
保存 onEdit={(t, e) => this.onTabEdit(t, e)}
</Button> >
</FormItem> {panes.map(pane => (
</Form> <TabPane tab={pane.title}
key={pane.key}
closable={pane.key !== 'default'}
>
<Form>
<div style={{padding: "10px 0"}}>
{addContent}
<FormItem {...formItemLayout} label={"模板"}>
<AceEditor
data={pane.data.template_data}
onChange={e => this.handleTemplateInput(e, pane.data)}
style={{minHeight: '500px'}}
/>
</FormItem>
</div>
<FormItem {...tailFormItemLayout}>
<Button type="primary" htmlType="submit" icon="save" size="large"
onClick={() => this.handleSubmit(pane.data)}>
保存
</Button>
</FormItem>
</Form>
</TabPane>
))}
</Tabs>
</div> </div>
); );
} }

View File

@@ -90,16 +90,15 @@ class exportController extends baseController {
if ((await this.checkAuth(projectId, 'project', 'edit')) !== true) { if ((await this.checkAuth(projectId, 'project', 'edit')) !== true) {
return (ctx.body = yapi.commons.resReturn(null, 405, '没有权限')); return (ctx.body = yapi.commons.resReturn(null, 405, '没有权限'));
} }
let existData = await this.genCodeModel.listByProjectId(projectId);
if (existData.find(templ => templ.tag === requestBody.tag)){
return (ctx.body = yapi.commons.resReturn(null, 502, 'tag已存在'));
}
let result; let result;
if (requestBody.id) { if (requestBody.id) {
result = await this.genCodeModel.up(requestBody); result = await this.genCodeModel.up(requestBody);
} else { } else {
let existData = await this.genCodeModel.listByProjectId(projectId);
if (existData.find(templ => templ.tag === requestBody.tag)){
return (ctx.body = yapi.commons.resReturn(null, 502, 'tag已存在'));
}
result = await this.genCodeModel.save(requestBody); result = await this.genCodeModel.save(requestBody);
} }

View File

@@ -4,10 +4,10 @@
"description": "YAPI", "description": "YAPI",
"main": "server/app.js", "main": "server/app.js",
"scripts": { "scripts": {
"dev-copy-icon": "cp -r static/iconfont ./", "dev-copy-icon": "copy static\\iconfont .\\",
"dev-server": " nodemon server/app.js dev -L", "dev-server": " nodemon server/app.js dev -L",
"install-server": " node server/install.js", "install-server": " node server/install.js",
"dev-client": "npm run dev-copy-icon && ykit s -p 4000", "dev-client": "ykit s -p 4000",
"dev": "npm run dev-server & npm run dev-client", "dev": "npm run dev-server & npm run dev-client",
"start": " node server/app.js", "start": " node server/app.js",
"test": "ava", "test": "ava",