feature/2.15.2.2411.01业务线-数据推送

This commit is contained in:
lys 2024-11-20 15:30:14 +08:00
parent a2c5fdc5ec
commit 18a87cb45c
7 changed files with 403 additions and 14 deletions

View File

@ -16,3 +16,11 @@ export const deletePushSetting = (params) => {
export const getPushItemList = (params) => {
return postFetch("/api/bs/hrmsalary/push/item/list", params);
};
// 保存推送配置明细
export const savePushItemList = (params) => {
return postFetch("/api/bs/hrmsalary/push/item/save", params);
};
// 删除推送配置明细
export const deletePushItemList = (params) => {
return WeaTools.callApi("/api/bs/hrmsalary/push/item/delete", "GET", params);
};

View File

@ -10,22 +10,23 @@
import React, { Component } from "react";
import { inject, observer } from "mobx-react";
import { WeaButtonIcon, WeaLocaleProvider, WeaSearchGroup, WeaSlideModal, WeaTable, WeaTools } from "ecCom";
import PDetailDialog from "../PDDialog";
import { postFetch } from "../../../../util/request";
import * as API from "../../../../apis/datapush";
import { conditions } from "../../conditions";
import { getSearchs } from "../../../../util";
import { Button, message } from "antd";
import { Button, message, Modal } from "antd";
const getLabel = WeaLocaleProvider.getLabel;
const getKey = WeaTools.getKey;
@inject("baseFormStore")
@observer
@inject("baseFormStore") @observer
class Index extends Component {
constructor(props) {
super(props);
this.state = {
conditions: [], loading: false, columns: [], dataSource: []
conditions: [], loading: false, columns: [], dataSource: [],
PDDialog: { visible: false, title: "", settingId: "", detail: {} } //推送明细弹框
};
}
@ -61,15 +62,52 @@ class Index extends Component {
!_.isEmpty(detail) && this.getPushItemList(props);
});
};
getPushItemList = ({ detail }) => {
getPushItemList = (props) => {
const { detail } = props || this.props;
const { id: settingId } = detail;
API.getPushItemList({ settingId }).then(({ status, data }) => {
if (status) {
const { columns, list: dataSource } = data;
this.setState({ dataSource, columns });
this.setState({
dataSource, columns: [...columns, {
title: getLabel(111, "操作"), width: 120, render: (__, record) => (<React.Fragment>
<a href="javascript: void(0);" style={{ marginRight: 10 }}
onClick={() => this.handleOpts("edit", record)}>{getLabel(111, "编辑")}</a>
<a href="javascript: void(0);" style={{ marginRight: 10 }}
onClick={() => this.handleOpts("del", record.id)}>{getLabel(111, "删除")}</a>
</React.Fragment>)
}],
PDDialog: { ...this.state.PDDialog, settingId }
});
}
});
};
handleOpts = (type, detail = {}) => {
switch (type) {
case "edit":
const { PDDialog } = this.state;
this.setState({ PDDialog: { ...PDDialog, visible: true, title: getLabel(111, "编辑"), detail } });
break;
case "del":
Modal.confirm({
title: getLabel(111, "信息确认"),
content: getLabel(111, "确认要删除吗?"),
onOk: () => {
API.deletePushItemList({ id: detail }).then(({ status, errormsg }) => {
if (status) {
message.success(getLabel(111, "删除成功"));
this.getPushItemList();
} else {
message.error(errormsg);
}
});
}
});
break;
default:
break;
}
};
save = () => {
const { baseFormStore: { form }, detail } = this.props;
form.validateForm().then(f => {
@ -105,21 +143,24 @@ class Index extends Component {
};
render() {
const { baseFormStore: { form }, detail } = this.props, { conditions, columns, dataSource } = this.state;
const { baseFormStore: { form }, detail } = this.props, { conditions, columns, dataSource, PDDialog } = this.state;
return (<WeaSlideModal
className="pushdata_create_dialog" {...this.props} direction="right"
top={0} width={800} height={100} measureT="%" measureX="px" measureY="%" title={this.renderTitle()}
content={<div className="form-dialog-layout">
{getSearchs(form, conditions, 2, false)}
{
!_.isEmpty(detail) &&
{!_.isEmpty(detail) &&
<WeaSearchGroup title={getLabel(111, "推送明细")} showGroup needTigger className="pushdata_detail">
<div className="opts">
<WeaButtonIcon buttonType="add" type="primary" title={getLabel(111, "添加")}/>
<WeaButtonIcon buttonType="add" type="primary" title={getLabel(111, "添加")}
onClick={() => this.setState({
PDDialog: { ...PDDialog, visible: true, title: getLabel(111, "新建") }
})}/>
</div>
<WeaTable pagination={false} columns={columns} datas={dataSource} bordered/>
</WeaSearchGroup>
}
<WeaTable pagination={false} columns={columns} dataSource={dataSource} bordered/>
<PDetailDialog {...PDDialog} onSearch={this.getPushItemList}
onCancel={() => this.setState({ PDDialog: { ...PDDialog, visible: false } })}/>
</WeaSearchGroup>}
</div>}
/>);
}

View File

@ -0,0 +1,90 @@
/*
* 数据推送
* 自定义薪资项目选择树
* @Author: 黎永顺
* @Date: 2024/11/20
* @Wechat:
* @Email: 971387674@qq.com
* @description:
*/
import React, { Component } from "react";
import { WeaLocaleProvider } from "ecCom";
import { TreeSelect } from "antd";
import { formualSearchField, formualSearchGroup } from "../../../../apis/item";
import cs from "classnames";
const getLabel = WeaLocaleProvider.getLabel;
const TreeNode = TreeSelect.TreeNode;
class CustomTreeSelect extends Component {
constructor(props) {
super(props);
this.state = { sourceList: [] };
}
componentDidMount() {
formualSearchGroup({ referenceType: "sql" }).then(({ status, data }) => {
if (status) this.setState({ sourceList: _.map(data, o => ({ ...o, isLeaf: true })) });
});
}
getSourceItem = (sourceId) => {
formualSearchField({ sourceId, extendParam: { referenceType: "sql" } }).then(({ status, data }) => {
if (status) {
this.setState({
sourceList: _.map(this.state.sourceList, o => {
if (o.key === sourceId) return {
...o,
children: _.map(data, k => ({ key: k.fieldId, value: k.name, fieldType: k.fieldType, isLeaf: false }))
};
return { ...o };
})
});
}
});
};
generateTreeNodes = (data) => {
const treeNodes = [], showData = [...data];
showData.map((item) => {
let title = (
<div className="weapp-excel-code-action-list-variable">
<span className="weapp-excel-code-action-list-variable-name">{item.value}</span>
{
item.fieldType ?
<span
className={cs("weapp-excel-code-action-list-variable-tip", { "danger": item.fieldType === "string" })}>{item.fieldType === "number" ? getLabel(111, "数字") : getLabel(111, "文本")}</span> :
<span></span>
}
</div>
);
treeNodes.push(<TreeNode className="no-child-item" title={title} key={item.key} value={item.key}/>);
});
return treeNodes;
};
handleSelect = (nodeValue) => {
const { form } = this.props, { sourceList } = this.state;
const [source, item] = nodeValue.split("_");
const itemName = _.find(_.find(sourceList, o => o.key === source).children, k => k.key === nodeValue).value;
form.updateFields({ item, itemName, source });
};
render() {
const { sourceList } = this.state, { form } = this.props;
const { source, item } = form.getFormParams();
return (
<TreeSelect dropdownStyle={{ maxHeight: 320, overflow: "auto" }} value={`${source}_${item}`}
dropdownMatchSelectWidth className="custom_item_treeselect"
loadData={(node) => this.getSourceItem(node.props.value)}
onSelect={this.handleSelect}>
{
_.map(sourceList, o => (
<TreeNode title={o.value} key={o.key} value={o.key} isLeaf={o.isLeaf} selectable={false}>
{this.generateTreeNodes(o.children || [])}
</TreeNode>))
}
</TreeSelect>
);
}
}
export default CustomTreeSelect;

View File

@ -0,0 +1,135 @@
/*
* 数据推送
* 推送明细新增编辑
* @Author: 黎永顺
* @Date: 2024/11/20
* @Wechat:
* @Email: 971387674@qq.com
* @description:
*/
import React, { Component } from "react";
import { inject, observer } from "mobx-react";
import { WeaDialog, WeaFormItem, WeaLocaleProvider, WeaSearchGroup, WeaTools } from "ecCom";
import CustomTreeSelect from "./customTreeSelect";
import { commonEnumList } from "../../../../apis/ruleconfig";
import * as API from "../../../../apis/datapush";
import { PDConditions } from "../../conditions";
import { WeaSwitch } from "comsMobx";
import { Button, message } from "antd";
const getLabel = WeaLocaleProvider.getLabel;
const getKey = WeaTools.getKey;
@inject("baseFormStore")
@observer
class Index extends Component {
constructor(props) {
super(props);
this.state = {
conditions: [], loading: false
};
}
componentWillReceiveProps(nextProps, nextContext) {
if (nextProps.visible !== this.props.visible && nextProps.visible) this.initForm(nextProps);
if (nextProps.visible !== this.props.visible && !nextProps.visible) this.props.baseFormStore.initFormExtra();
}
initForm = async (props) => {
const { detail = {} } = props;
const { data: fieldType } = await commonEnumList({ enumClass: "com.engine.salary.enums.push.PushItemFieldEnum" });
this.setState({
conditions: _.map(PDConditions, item => ({
...item, items: _.map(item.items, o => {
o = { ...o, label: getLabel(o.lanId, o.label), value: detail[getKey(o)] ? String(detail[getKey(o)]) : "" };
if (getKey(o) === "fieldType") {
return {
...o, value: detail[getKey(o)] ? String(detail[getKey(o)]) : "",
options: _.map(fieldType, o => ({ key: o.enum, showname: o.defaultLabel }))
};
}
return { ...o };
})
}))
}, () => {
props.baseFormStore.formExtra.initFormFields(this.state.conditions);
});
};
renderRuleForm = () => {
const { conditions } = this.state;
const { baseFormStore: { formExtra } } = this.props, { isFormInit } = formExtra;
const formParams = formExtra.getFormParams();
let group = [];
isFormInit && conditions && conditions.map(c => {
let items = [];
c.items.map(fields => {
items.push({
com: (
<WeaFormItem label={fields.label} labelCol={{ span: `${fields.labelcol}` }}
wrapperCol={{ span: `${fields.fieldcol}` }} error={formExtra.getError(fields)}
tipPosition="bottom">
{
getKey(fields) === "item" ?
<React.Fragment>
<CustomTreeSelect fieldConfig={fields} form={formExtra} formParams={formParams}/>
{
_.isEmpty(formParams.item) &&
<span className="wea-required-e9" style={{ verticalAlign: "middle" }}>
<img src="/images/BacoError_wev9.png" alt=""/>
</span>
}
</React.Fragment>
: <WeaSwitch fieldConfig={fields} form={formExtra} formParams={formParams}/>
}
</WeaFormItem>),
colSpan: 1,
hide: fields.hide
});
});
!_.isEmpty(items) && group.push(
<WeaSearchGroup col={1} needTigger={true} showGroup={c.defaultshow} items={items} center={false}
title={c.title}/>);
});
return group;
};
save = () => {
const { baseFormStore: { formExtra }, id, settingId } = this.props;
formExtra.validateForm().then(f => {
if (f.isValid) {
const payload = formExtra.getFormParams();
this.setState({ loading: true });
API.savePushItemList({ ...payload, settingId, id })
.then(({ status, errormsg }) => {
this.setState({ loading: false });
if (status) {
message.success(getLabel(30700, "操作成功"));
this.props.onCancel(this.props.onSearch());
} else {
message.error(errormsg);
}
}).catch(() => this.setState({ loading: false }));
} else {
f.showErrors();
}
});
};
render() {
const { loading } = this.state;
return (
<WeaDialog
{...this.props} style={{ width: 480, height: 174 }} initLoadCss className="Pdetail_dialog"
buttons={[
<Button onClick={this.props.onCancel}>{getLabel(111, "取消")}</Button>,
<Button type="primary" onClick={this.save} loading={loading}>{getLabel(111, "保存")}</Button>
]}
>
<div className="form-dialog-layout">{this.renderRuleForm()}</div>
</WeaDialog>
);
}
}
export default Index;

View File

@ -73,4 +73,63 @@ export const conditions = [
lanId: 111,
defaultshow: true
}
];
];// 推送配置表单
export const PDConditions = [
{
items: [
{
conditionType: "INPUT",
domkey: ["item"],
fieldcol: 14,
label: "薪资项目",
lanId: 111,
labelcol: 6,
value: "",
rules: "required|string",
viewAttr: 3
},
{
conditionType: "INPUT",
domkey: ["itemName"],
fieldcol: 14,
label: "字段名称",
lanId: 111,
labelcol: 6,
viewAttr: 2,
hide: true
},
{
conditionType: "INPUT",
domkey: ["source"],
fieldcol: 14,
label: "字段名称",
lanId: 111,
labelcol: 6,
viewAttr: 2,
hide: true
},
{
conditionType: "INPUT",
domkey: ["fieldName"],
fieldcol: 14,
label: "字段名称",
lanId: 111,
labelcol: 6,
viewAttr: 2
},
{
conditionType: "SELECT",
domkey: ["fieldType"],
fieldcol: 14,
label: "字段类型",
lanId: 111,
labelcol: 6,
value: "",
options: [],
viewAttr: 2
}
],
title: "",
defaultshow: true
}
];// 推送详细配置表单

View File

@ -78,3 +78,57 @@
}
}
}
.custom_item_treeselect {
.weapp-excel-code-action-list-variable-tip {
display: none;
}
}
.no-child-item {
.ant-select-tree-switcher {
display: none !important;
}
.ant-select-tree-node-content-wrapper {
width: 100%;
}
.weapp-excel-code-action-list-variable {
width: 100%;
display: flex;
justify-content: space-between;
align-items: center;
.weapp-excel-code-action-list-variable-name {
height: 20px;
line-height: 18px;
-webkit-flex: 1 1;
flex: 1 1;
overflow: hidden;
text-overflow: ellipsis;
word-break: keep-all;
white-space: nowrap;
cursor: pointer;
}
.danger {
color: rgb(255, 102, 106) !important;
border: 1px solid rgb(255, 193, 195) !important;
background-color: rgb(255, 223, 224) !important;
}
.weapp-excel-code-action-list-variable-tip {
width: 40px;
height: 20px;
line-height: 18px;
text-align: center;
vertical-align: middle;
color: rgb(255, 205, 80);
border: 1px solid rgb(255, 222, 138);
background-color: rgb(255, 245, 219);
border-radius: 2px;
}
}
}

View File

@ -6,6 +6,8 @@ export class BaseFormStore {
// 全局设置仓库
@observable form = new WeaForm(); // 规则渲染form
@action("初始化form表单") initForm = () => this.form = new WeaForm();
@observable formExtra = new WeaForm(); // 规则渲染form
@action("初始化form表单") initFormExtra = () => this.formExtra = new WeaForm();
@observable logVisible = false; // 控制日志弹框的显影
@action("日志显隐开关")
setLogVisible = bool => this.logVisible = bool;