spug/spug_web/src/pages/deploy/app/Ext1Setup3.js

222 lines
9.0 KiB
JavaScript
Raw Blame History

This file contains ambiguous Unicode characters!

This file contains ambiguous Unicode characters that may be confused with others in your current locale. If your use case is intentional and legitimate, you can safely ignore this warning. Use the Escape button to highlight these characters.

/**
* Copyright (c) OpenSpug Organization. https://github.com/openspug/spug
* Copyright (c) <spug.dev@gmail.com>
* Released under the AGPL-3.0 License.
*/
import React from 'react';
import { observer } from 'mobx-react';
import { Form, Row, Col, Button, Radio, Icon, Tooltip, message } from "antd";
import { LinkButton } from 'components';
import Editor from 'react-ace';
import 'ace-builds/src-noconflict/mode-text';
import 'ace-builds/src-noconflict/mode-sh';
import 'ace-builds/src-noconflict/theme-tomorrow';
import store from './store';
import http from 'libs/http';
import styles from './index.module.css';
import { cleanCommand } from "../../../libs";
@observer
class Ext1Setup3 extends React.Component {
constructor(props) {
super(props);
this.helpMap = {
'2': <span>
Spug 内置了一些全局变量这些变量可以直接使用请参考官方文档
<a target="_blank" rel="noopener noreferrer"
href="https://spug.dev/docs/deploy-config/#%E5%85%A8%E5%B1%80%E5%8F%98%E9%87%8F">全局变量</a>
</span>,
'3': '在部署 Spug 的服务器上运行,可以执行任意自定义命令。',
'4': '在部署 Spug 的服务器上运行,当前目录为检出后待发布的源代码目录,可执行任意自定义命令。',
'5': '在发布的目标主机上运行,当前目录为目标主机上待发布的源代码目录,可执行任意自定义命令。',
'6': '在发布的目标主机上运行,当前目录为已发布的应用目录,可执行任意自定义命令。'
};
this.state = {
loading: false,
full: ''
}
}
handleSubmit = () => {
this.setState({loading: true});
const info = store.deploy;
info['app_id'] = store.app_id;
info['extend'] = '1';
info['host_ids'] = info['host_ids'].filter(x => x);
http.post('/api/app/deploy/', info)
.then(() => {
message.success('保存成功');
store.loadDeploys(store.app_id);
store.ext1Visible = false
}, () => this.setState({loading: false}))
};
FilterLabel = (props) => (
<div style={{display: 'inline-block', height: 39, width: 390}}>
<span style={{float: 'left'}}>文件过滤<span style={{margin: '0 8px 0 2px'}}>:</span></span>
<Radio.Group
disabled={store.isReadOnly}
style={{marginLeft: 20, float: 'left'}}
value={props.type}
onChange={e => store.deploy['filter_rule']['type'] = e.target.value}>
<Radio value="contain">包含
<Tooltip title="请输入相对于项目根目录的文件路径,仅将匹配到文件传输至要发布的目标主机。">
<Icon type="info-circle" style={{color: '#515151', marginLeft: 8}}/>
</Tooltip>
</Radio>
<Radio value="exclude">排除
<Tooltip title="支持模糊匹配,如果路径以 / 开头则基于项目根目录匹配,匹配到文件将不会被传输。">
<Icon type="info-circle" style={{color: '#515151', marginLeft: 8}}/>
</Tooltip>
</Radio>
</Radio.Group>
{this.state.full === '1' ? (
<LinkButton onClick={() => this.setState({full: ''})}>退出全屏</LinkButton>
) : (
<LinkButton onClick={() => this.setState({full: '1'})}>全屏</LinkButton>
)}
</div>
);
NormalLabel = (props) => (
<div style={{display: 'inline-block', height: 39, width: 390}}>
<span style={{float: 'left'}}>
{props.title}<span style={{margin: '0 8px 0 2px'}}>:</span>
<Tooltip title={this.helpMap[props.id]}>
<Icon type="info-circle" style={{color: '#515151'}}/>
</Tooltip>
</span>
{this.state.full ? (
<span style={{color: '#1890ff', cursor: 'pointer'}} onClick={() => this.setState({full: ''})}>退出全屏</span>
) : (
<span style={{color: '#1890ff', cursor: 'pointer'}} onClick={() => this.setState({full: props.id})}>全屏</span>
)}
</div>
);
render() {
const info = store.deploy;
const {full} = this.state;
return (
<React.Fragment>
<Row>
<Col span={11}>
<Form.Item
colon={false}
className={full === '1' ? styles.fullScreen : null}
label={<this.FilterLabel type={info['filter_rule']['type']}/>}>
<Editor
readOnly={store.isReadOnly}
mode="text"
theme="tomorrow"
width="100%"
height={full === '1' ? '100vh' : '100px'}
placeholder="每行一条规则"
value={info['filter_rule']['data']}
onChange={v => info['filter_rule']['data'] = cleanCommand(v)}
style={{border: '1px solid #e8e8e8'}}/>
</Form.Item>
<Form.Item
colon={false}
className={full === '3' ? styles.fullScreen : null}
label={<this.NormalLabel title="代码检出前执行" id="3"/>}>
<Editor
readOnly={store.isReadOnly}
mode="sh"
theme="tomorrow"
width="100%"
height={full === '3' ? '100vh' : '100px'}
placeholder="输入要执行的命令"
value={info['hook_pre_server']}
onChange={v => info['hook_pre_server'] = cleanCommand(v)}
style={{border: '1px solid #e8e8e8'}}/>
</Form.Item>
<Form.Item
colon={false}
className={full === '5' ? styles.fullScreen : null}
label={<this.NormalLabel title="应用发布前执行" id="5"/>}>
<Editor
readOnly={store.isReadOnly}
mode="sh"
theme="tomorrow"
width="100%"
height={full === '5' ? '100vh' : '100px'}
placeholder="输入要执行的命令"
value={info['hook_pre_host']}
onChange={v => info['hook_pre_host'] = cleanCommand(v)}
style={{border: '1px solid #e8e8e8'}}/>
</Form.Item>
</Col>
<Col span={2}>
<div className={styles.deployBlock} style={{marginTop: 39}}>
<Icon type="setting" style={{fontSize: 32}}/>
<span style={{fontSize: 12, marginTop: 5}}>基础设置</span>
</div>
<div className={styles.deployBlock}>
<Icon type="gitlab" style={{fontSize: 32}}/>
<span style={{fontSize: 12, marginTop: 5}}>检出代码</span>
</div>
<div className={styles.deployBlock}>
<Icon type="swap" style={{fontSize: 32}}/>
<span style={{fontSize: 12, marginTop: 5}}>版本切换</span>
</div>
</Col>
<Col span={11}>
<Form.Item
colon={false}
className={full === '2' ? styles.fullScreen : null}
label={<this.NormalLabel title="自定义全局变量" id="2"/>}>
<Editor
readOnly={store.isReadOnly}
mode="text"
theme="tomorrow"
width="100%"
height={full === '2' ? '100vh' : '100px'}
placeholder="每行一个例如HOME=/data/spug"
value={info['custom_envs']}
onChange={v => info['custom_envs'] = cleanCommand(v)}
style={{border: '1px solid #e8e8e8'}}/>
</Form.Item>
<Form.Item
colon={false}
className={full === '4' ? styles.fullScreen : null}
label={<this.NormalLabel title="代码检出后执行" id="4"/>}>
<Editor
readOnly={store.isReadOnly}
mode="sh"
theme="tomorrow"
width="100%"
height={full === '4' ? '100vh' : '100px'}
placeholder="输入要执行的命令"
value={info['hook_post_server']}
onChange={v => info['hook_post_server'] = cleanCommand(v)}
style={{border: '1px solid #e8e8e8'}}/>
</Form.Item>
<Form.Item
colon={false}
className={full === '6' ? styles.fullScreen : null}
label={<this.NormalLabel title="应用发布后执行" id="6"/>}>
<Editor
readOnly={store.isReadOnly}
mode="sh"
theme="tomorrow"
width="100%"
height={full === '6' ? '100vh' : '100px'}
placeholder="输入要执行的命令"
value={info['hook_post_host']}
onChange={v => info['hook_post_host'] = cleanCommand(v)}
style={{border: '1px solid #e8e8e8'}}/>
</Form.Item>
</Col>
</Row>
<Form.Item wrapperCol={{span: 14, offset: 6}}>
<Button disabled={store.isReadOnly} type="primary" onClick={this.handleSubmit}>提交</Button>
<Button style={{marginLeft: 20}} onClick={() => store.page -= 1}>上一步</Button>
</Form.Item>
</React.Fragment>
)
}
}
export default Ext1Setup3