index.tsx 11 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387
  1. import { PageContainer } from '@ant-design/pro-layout';
  2. import { useRef, useState } from 'react';
  3. import type { ActionType, ProColumns } from '@jetlinks/pro-table';
  4. import {
  5. ArrowDownOutlined,
  6. BugOutlined,
  7. DeleteOutlined,
  8. EditOutlined,
  9. EyeOutlined,
  10. PlusOutlined,
  11. UnorderedListOutlined,
  12. } from '@ant-design/icons';
  13. import { Space, Upload } from 'antd';
  14. import { useIntl } from '@@/plugin-locale/localeExports';
  15. import Service from '@/pages/notice/Template/service';
  16. import ConfigService from '@/pages/notice/Config/service';
  17. import SearchComponent from '@/components/SearchComponent';
  18. import { history, useLocation } from 'umi';
  19. import { getMenuPathByParams, MENUS_CODE } from '@/utils/menu';
  20. import { model } from '@formily/reactive';
  21. import Debug from './Debug';
  22. import Log from '@/pages/notice/Template/Log';
  23. import { downloadObject, onlyMessage } from '@/utils/util';
  24. import moment from 'moment';
  25. import { PermissionButton, ProTableCard } from '@/components';
  26. import NoticeCard, { typeList } from '@/components/ProTableCard/CardItems/noticeTemplate';
  27. import { observer } from '@formily/react';
  28. import usePermissions from '@/hooks/permission';
  29. export const service = new Service('notifier/template');
  30. export const configService = new ConfigService('notifier/config');
  31. export const state = model<{
  32. current?: TemplateItem;
  33. debug?: boolean;
  34. log?: boolean;
  35. }>({
  36. debug: false,
  37. log: false,
  38. });
  39. const list = {
  40. weixin: {
  41. corpMessage: {
  42. text: '企业消息',
  43. status: 'corpMessage',
  44. },
  45. // officialMessage: {
  46. // text: '服务号消息',
  47. // status: 'officialMessage',
  48. // },
  49. },
  50. dingTalk: {
  51. dingTalkMessage: {
  52. text: '钉钉消息',
  53. status: 'dingTalkMessage',
  54. },
  55. dingTalkRobotWebHook: {
  56. text: '群机器人消息',
  57. status: 'dingTalkRobotWebHook',
  58. },
  59. },
  60. voice: {
  61. aliyun: {
  62. text: '阿里云语音',
  63. status: 'aliyun',
  64. },
  65. },
  66. sms: {
  67. aliyunSms: {
  68. text: '阿里云短信',
  69. status: 'aliyunSms',
  70. },
  71. },
  72. email: {
  73. embedded: {
  74. text: '邮件',
  75. status: 'embedded',
  76. },
  77. },
  78. webhook: {
  79. http: {
  80. text: 'Webhook',
  81. status: 'http',
  82. },
  83. },
  84. };
  85. const Template = observer(() => {
  86. const intl = useIntl();
  87. const location = useLocation<{ id: string }>();
  88. const id = (location as any).query?.id;
  89. const actionRef = useRef<ActionType>();
  90. const { permission: templatePermission } = usePermissions('notice');
  91. const columns: ProColumns<TemplateItem>[] = [
  92. {
  93. dataIndex: 'name',
  94. title: '模版名称',
  95. ellipsis: true,
  96. },
  97. {
  98. dataIndex: 'provider',
  99. title: '通知方式',
  100. renderText: (text, record) => typeList[record.type][record.provider],
  101. valueType: 'select',
  102. valueEnum: list[id],
  103. },
  104. {
  105. dataIndex: 'description',
  106. title: '说明',
  107. ellipsis: true,
  108. },
  109. {
  110. title: intl.formatMessage({
  111. id: 'pages.data.option',
  112. defaultMessage: '操作',
  113. }),
  114. valueType: 'option',
  115. align: 'left',
  116. width: 200,
  117. render: (text, record) => [
  118. <PermissionButton
  119. key="edit"
  120. style={{ padding: 0 }}
  121. type="link"
  122. isPermission={templatePermission.update}
  123. onClick={() => {
  124. state.current = record;
  125. history.push(getMenuPathByParams(MENUS_CODE['notice/Template/Detail'], id));
  126. }}
  127. tooltip={{
  128. title: intl.formatMessage({
  129. id: 'pages.data.option.edit',
  130. defaultMessage: '编辑',
  131. }),
  132. }}
  133. >
  134. <EditOutlined />
  135. </PermissionButton>,
  136. <PermissionButton
  137. key="download"
  138. style={{ padding: 0 }}
  139. type="link"
  140. tooltip={{ title: '导出' }}
  141. isPermission={templatePermission.export}
  142. onClick={() => {
  143. downloadObject(
  144. record,
  145. `${record.name}-${moment(new Date()).format('YYYY/MM/DD HH:mm:ss')}`,
  146. );
  147. }}
  148. >
  149. <ArrowDownOutlined />
  150. </PermissionButton>,
  151. <PermissionButton
  152. isPermission={templatePermission.debug}
  153. key="debug"
  154. style={{ padding: 0 }}
  155. type="link"
  156. onClick={() => {
  157. state.debug = true;
  158. state.current = record;
  159. }}
  160. tooltip={{
  161. title: intl.formatMessage({
  162. id: 'pages.notice.option.debug',
  163. defaultMessage: '调试',
  164. }),
  165. }}
  166. >
  167. <BugOutlined />
  168. </PermissionButton>,
  169. <PermissionButton
  170. isPermission={templatePermission.log}
  171. key="log"
  172. style={{ padding: 0 }}
  173. type="link"
  174. onClick={() => {
  175. state.log = true;
  176. }}
  177. tooltip={{ title: '通知记录' }}
  178. >
  179. <UnorderedListOutlined />
  180. </PermissionButton>,
  181. <PermissionButton
  182. style={{ padding: 0 }}
  183. type="link"
  184. popConfirm={{
  185. title: '确认删除?',
  186. onConfirm: async () => {
  187. await service.remove(record.id);
  188. actionRef.current?.reload();
  189. },
  190. }}
  191. tooltip={{
  192. title: intl.formatMessage({
  193. id: 'pages.data.option.remove',
  194. defaultMessage: '删除',
  195. }),
  196. }}
  197. isPermission={templatePermission.delete}
  198. key="delete"
  199. >
  200. <DeleteOutlined />
  201. </PermissionButton>,
  202. ],
  203. },
  204. ];
  205. const [param, setParam] = useState({});
  206. return (
  207. <PageContainer>
  208. <SearchComponent
  209. defaultParam={[{ column: 'type$IN', value: id }]}
  210. field={columns}
  211. onSearch={(data) => {
  212. actionRef.current?.reset?.();
  213. setParam(data);
  214. }}
  215. />
  216. <ProTableCard<TemplateItem>
  217. actionRef={actionRef}
  218. rowKey="id"
  219. search={false}
  220. params={param}
  221. columns={columns}
  222. headerTitle={
  223. <Space>
  224. <PermissionButton
  225. isPermission={templatePermission.add}
  226. onClick={() => {
  227. state.current = undefined;
  228. history.push(getMenuPathByParams(MENUS_CODE['notice/Template/Detail'], id));
  229. }}
  230. key="button"
  231. icon={<PlusOutlined />}
  232. type="primary"
  233. >
  234. {intl.formatMessage({
  235. id: 'pages.data.option.add',
  236. defaultMessage: '新增',
  237. })}
  238. </PermissionButton>
  239. <Upload
  240. disabled={!templatePermission.import}
  241. key={'import'}
  242. accept=".json"
  243. showUploadList={false}
  244. beforeUpload={(file) => {
  245. const reader = new FileReader();
  246. reader.readAsText(file);
  247. reader.onload = async (result) => {
  248. const text = result.target?.result as string;
  249. if (!file.type.includes('json')) {
  250. onlyMessage('文件内容格式错误', 'warning');
  251. return;
  252. }
  253. try {
  254. const data = JSON.parse(text || '{}');
  255. const res: any = await service.savePatch(data);
  256. if (res.status === 200) {
  257. onlyMessage('操作成功');
  258. actionRef.current?.reload();
  259. }
  260. } catch {
  261. onlyMessage('文件内容格式错误', 'warning');
  262. }
  263. };
  264. return false;
  265. }}
  266. >
  267. <PermissionButton isPermission={templatePermission.import} style={{ marginLeft: 12 }}>
  268. 导入
  269. </PermissionButton>
  270. </Upload>
  271. <PermissionButton
  272. popConfirm={{
  273. title: '确认导出当前页数据?',
  274. onConfirm: async () => {
  275. const resp: any = await service.queryNoPagingPost({ ...param, paging: false });
  276. if (resp.status === 200) {
  277. downloadObject(resp.result, '通知模版数据');
  278. onlyMessage('导出成功');
  279. } else {
  280. onlyMessage('导出错误', 'error');
  281. }
  282. },
  283. }}
  284. isPermission={templatePermission.export}
  285. >
  286. 导出
  287. </PermissionButton>
  288. </Space>
  289. }
  290. gridColumn={3}
  291. cardRender={(record) => (
  292. <NoticeCard
  293. {...record}
  294. type={id}
  295. detail={
  296. <div
  297. style={{ fontSize: 18, padding: 8 }}
  298. onClick={() => {
  299. state.current = record;
  300. history.push(getMenuPathByParams(MENUS_CODE['notice/Template/Detail'], id));
  301. }}
  302. >
  303. <EyeOutlined />
  304. </div>
  305. }
  306. actions={[
  307. <PermissionButton
  308. isPermission={templatePermission.update}
  309. key="edit"
  310. onClick={() => {
  311. state.current = record;
  312. history.push(getMenuPathByParams(MENUS_CODE['notice/Template/Detail'], id));
  313. }}
  314. >
  315. <EditOutlined />
  316. 编辑
  317. </PermissionButton>,
  318. <PermissionButton
  319. isPermission={templatePermission.debug}
  320. key="debug"
  321. onClick={() => {
  322. state.debug = true;
  323. state.current = record;
  324. }}
  325. >
  326. <BugOutlined />
  327. 调试
  328. </PermissionButton>,
  329. <PermissionButton
  330. key="export"
  331. isPermission={templatePermission.export}
  332. onClick={() => {
  333. downloadObject(
  334. record,
  335. `${record.name}-${moment(new Date()).format('YYYY/MM/DD HH:mm:ss')}`,
  336. );
  337. }}
  338. >
  339. <ArrowDownOutlined />
  340. 导出
  341. </PermissionButton>,
  342. <PermissionButton
  343. isPermission={templatePermission.log}
  344. key="log"
  345. onClick={() => {
  346. state.log = true;
  347. state.current = record;
  348. }}
  349. >
  350. <UnorderedListOutlined />
  351. 通知记录
  352. </PermissionButton>,
  353. <PermissionButton
  354. popConfirm={{
  355. title: '确认删除?',
  356. onConfirm: async () => {
  357. await service.remove(record.id);
  358. actionRef.current?.reset?.();
  359. },
  360. }}
  361. isPermission={templatePermission.delete}
  362. key="delete"
  363. >
  364. <DeleteOutlined />
  365. </PermissionButton>,
  366. ]}
  367. />
  368. )}
  369. request={async (params) =>
  370. service.query({ ...params, sorts: [{ name: 'createTime', order: 'desc' }] })
  371. }
  372. />
  373. <Debug />
  374. {state.log && <Log />}
  375. </PageContainer>
  376. );
  377. });
  378. export default Template;