user-list.vue 10 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420
  1. <script setup lang="ts">
  2. import FormSearch, { type FormField } from "@/components/opts/form-search.vue";
  3. import TableButtons from "@/components/opts/btns2.vue";
  4. import UserResetPasswd from "./reset-passwd.vue";
  5. import UserEdit from "./user-edit.vue";
  6. import { PureTable } from "@pureadmin/table";
  7. import { enableOptions } from "@/constants/constants";
  8. import { reactive, computed, ref, onMounted } from "vue";
  9. import * as $userApi from "@/api/sys/user";
  10. import { roleQueryList } from "@/api/sys/role";
  11. import { onBeforeMount } from "vue";
  12. import { hasAuth } from "@/router/utils";
  13. import message from "@/utils/message";
  14. import { useRenderIcon } from "@/components/ReIcon/src/hooks";
  15. import { watch } from "vue";
  16. const userEditRef = ref();
  17. const userResetPasswdRef = ref();
  18. defineOptions({
  19. name: "userList"
  20. });
  21. const props: any = defineProps({
  22. mode: {
  23. required: false,
  24. type: String,
  25. default: "table"
  26. }
  27. });
  28. const searchFormFields = computed((): FormField[] => {
  29. const fields: FormField[] = [
  30. {
  31. type: "input",
  32. label: "帐号",
  33. prop: "username",
  34. placeholder: "请输入帐号模糊查询"
  35. },
  36. {
  37. type: "input",
  38. label: "姓名",
  39. prop: "nickname",
  40. placeholder: "请输入姓名模糊查询"
  41. },
  42. {
  43. type: "select",
  44. label: "状态",
  45. prop: "enable",
  46. placeholder: "请选择",
  47. dataSourceKey: "enabledOptions",
  48. options: {
  49. keys: {
  50. label: "label",
  51. value: "value",
  52. prop: "value"
  53. },
  54. filterable: true
  55. }
  56. }
  57. ];
  58. if (props.mode === "table") {
  59. return fields;
  60. } else {
  61. return fields;
  62. }
  63. });
  64. const pageData: any = reactive({
  65. mode: "table",
  66. permission: {
  67. query: ["user:query:page"],
  68. save: ["user:save"],
  69. update: ["user:update"],
  70. del: ["user:del"]
  71. },
  72. searchParam: {
  73. searchState: true,
  74. fields: [
  75. {
  76. type: "input",
  77. label: "帐号",
  78. prop: "username",
  79. placeholder: "请输入帐号模糊查询"
  80. },
  81. {
  82. type: "input",
  83. label: "姓名",
  84. prop: "nickname",
  85. placeholder: "请输入姓名模糊查询"
  86. },
  87. {
  88. type: "select",
  89. label: "状态",
  90. prop: "enable",
  91. placeholder: "请选择",
  92. dataSourceKey: "enabledOptions",
  93. options: {
  94. keys: {
  95. label: "label",
  96. value: "value",
  97. prop: "value"
  98. },
  99. filterable: true
  100. }
  101. }
  102. ],
  103. searchForm: {}
  104. },
  105. dataSource: {
  106. enabledOptions: enableOptions
  107. },
  108. /*按钮 */
  109. btnOpts: {
  110. size: "small",
  111. leftBtns: [
  112. {
  113. key: "add",
  114. label: "新增",
  115. type: "primary",
  116. icon: "ep:plus",
  117. state: true,
  118. permission: ["user:save"]
  119. }
  120. // {
  121. // key: "update",
  122. // label: "修改",
  123. // type: "success",
  124. // icon: "ep:edit",
  125. // state: false,
  126. // permission: ["user:update"]
  127. // }
  128. ],
  129. rightBtns: [
  130. {
  131. key: "search",
  132. label: "查询",
  133. icon: "ep:search",
  134. state: true,
  135. options: {
  136. circle: true
  137. }
  138. },
  139. {
  140. key: "refresh",
  141. label: "刷新",
  142. icon: "ep:refresh",
  143. state: true,
  144. options: {
  145. circle: true
  146. }
  147. },
  148. {
  149. key: "switch",
  150. label: "切换",
  151. icon: "ep:switch",
  152. state: true,
  153. options: {
  154. circle: true
  155. }
  156. }
  157. ]
  158. },
  159. tableParam: {
  160. list: [],
  161. columns: [
  162. {
  163. label: "用户帐号",
  164. prop: "username",
  165. slot: "username"
  166. },
  167. {
  168. label: "姓名",
  169. prop: "nickname",
  170. slot: "ellipsis"
  171. },
  172. {
  173. label: "状态",
  174. prop: "enable",
  175. slot: "enableScope"
  176. },
  177. {
  178. label: "更新人",
  179. prop: "updateUser",
  180. slot: "ellipsis"
  181. },
  182. {
  183. label: "更新时间",
  184. prop: "updateTime",
  185. slot: "ellipsis"
  186. },
  187. {
  188. label: "操作",
  189. fixed: "right",
  190. slot: "operation"
  191. }
  192. ],
  193. loading: false,
  194. pagination: {
  195. pageSize: 10,
  196. defaultPageSize: 10,
  197. currentPage: 1,
  198. background: true,
  199. total: 0
  200. }
  201. }
  202. });
  203. const btnClickHandle = (val: string) => {
  204. switch (val) {
  205. case "add":
  206. userEditRef.value!.open({ enable: 1 }, pageData.dataSource, "add");
  207. break;
  208. case "update":
  209. break;
  210. case "search":
  211. _updateSearchState();
  212. break;
  213. case "refresh":
  214. _loadData();
  215. break;
  216. case "switch":
  217. switchTable();
  218. break;
  219. default:
  220. break;
  221. }
  222. };
  223. const switchTable = () => {
  224. emits("switchMode", props.mode === "table" ? "tree" : "table");
  225. };
  226. /**
  227. * 更新搜索表单
  228. * @param data .
  229. */
  230. const _updateSearchFormData = (data: any) => {
  231. pageData.searchParam.searchForm = data;
  232. };
  233. /**
  234. * 点击搜索按钮
  235. */
  236. const _searchForm = (data: any) => {
  237. pageData.searchParam.searchForm = data;
  238. _loadData();
  239. };
  240. /**
  241. * 重置
  242. */
  243. const _resetSearchForm = (data?) => {
  244. pageData.searchParam.searchForm = data;
  245. };
  246. /**
  247. * 更新搜索表达的状态
  248. */
  249. const _updateSearchState = () => {
  250. pageData.searchParam.searchState = !pageData.searchParam.searchState;
  251. };
  252. const handleChangePageSize = (val: any) => {
  253. pageData.tableParam.pagination.pageSize = val;
  254. _loadData();
  255. };
  256. const handleChangeCurrentPage = (val: any) => {
  257. pageData.tableParam.pagination.currentPage = val;
  258. _loadData();
  259. };
  260. const getQueryParams = () => {
  261. const sqp = {};
  262. const param = Object.assign(sqp, pageData.searchParam.searchForm);
  263. param.current = pageData.tableParam.pagination.currentPage;
  264. param.size = pageData.tableParam.pagination.pageSize;
  265. return param;
  266. };
  267. const _loadData = (page?: number) => {
  268. const query = getQueryParams();
  269. if (page) {
  270. query.current = page;
  271. }
  272. pageData.tableParam.loading = true;
  273. $userApi
  274. .queryPage(query)
  275. .then((res: any) => {
  276. if (res.success) {
  277. pageData.tableParam.list = res.result.records;
  278. pageData.tableParam.pagination.total = Number(res.result.total);
  279. }
  280. })
  281. .finally(() => {
  282. pageData.tableParam.loading = false;
  283. });
  284. };
  285. const queryRoles = () => {
  286. roleQueryList({ enable: 1 }).then((res: any) => {
  287. if (res.success) {
  288. pageData.dataSource.roleList = res.result;
  289. }
  290. });
  291. };
  292. const handleEdit = (row: any) => {
  293. userEditRef.value!.open(row, pageData.dataSource, "edit");
  294. };
  295. const handleDel = (row: any) => {
  296. message.confirm("确认删除当前数据").then(() => {
  297. batchDel([row.id]);
  298. });
  299. };
  300. const batchDel = (ids: string[]) => {
  301. if (ids && ids.length > 0) {
  302. $userApi.del(ids).then((res: any) => {
  303. if (res.success) {
  304. message.success("删除成功");
  305. _loadData();
  306. } else {
  307. message.warning(res.message);
  308. }
  309. });
  310. }
  311. };
  312. const handleResetPasswd = (row: any) => {
  313. userResetPasswdRef.value!.open(row);
  314. };
  315. const handleDetail = (row: any) => {
  316. userEditRef.value!.open(row, pageData.dataSource, "detail");
  317. };
  318. watch(
  319. () => props.orgInfo,
  320. val => {
  321. if (val) {
  322. _loadData();
  323. }
  324. }
  325. );
  326. onBeforeMount(() => {
  327. queryRoles();
  328. });
  329. onMounted(() => {
  330. _loadData(1);
  331. });
  332. const emits = defineEmits(["switchMode"]);
  333. </script>
  334. <template>
  335. <div>
  336. <form-search
  337. :show="pageData.searchParam.searchState"
  338. :form-field="searchFormFields"
  339. :data-source="pageData.dataSource"
  340. @search-form="_updateSearchFormData"
  341. @search="_searchForm"
  342. @reset="_resetSearchForm"
  343. :query-permission="pageData.permission.query"
  344. />
  345. <!--operate-->
  346. <table-buttons
  347. :size="pageData.btnOpts.size"
  348. :left-btns="pageData.btnOpts.leftBtns"
  349. :right-btns="pageData.btnOpts.rightBtns"
  350. @click="btnClickHandle"
  351. />
  352. <!--table-->
  353. <pure-table
  354. :data="pageData.tableParam.list"
  355. :columns="pageData.tableParam.columns"
  356. row-key="id"
  357. border
  358. stripe
  359. :header-row-class-name="'table-header'"
  360. :loading="pageData.tableParam.loading"
  361. :pagination="pageData.tableParam.pagination"
  362. @page-current-change="handleChangeCurrentPage"
  363. @page-size-change="handleChangePageSize"
  364. >
  365. <template #ellipsis="{ row, column }">
  366. <el-tooltip placement="top-start" :content="row[column.property]">{{
  367. row[column.property]
  368. }}</el-tooltip>
  369. </template>
  370. <template #username="{ row }">
  371. <el-link type="primary" @click="handleDetail(row)">{{
  372. row.username
  373. }}</el-link>
  374. </template>
  375. <template #enableScope="scope">
  376. <el-tag v-if="scope.row.enable">启用</el-tag>
  377. <el-tag v-else type="info">禁用</el-tag>
  378. </template>
  379. <template #operation="{ row }">
  380. <div class="flex justify-center items-center">
  381. <el-link
  382. v-show="hasAuth(pageData.permission.update) && row.isManage !== 1"
  383. type="primary"
  384. @click="handleEdit(row)"
  385. >编辑</el-link
  386. >
  387. <el-divider
  388. v-show="hasAuth(pageData.permission.del) && row.isManage !== 1"
  389. direction="vertical"
  390. />
  391. <el-link
  392. v-show="hasAuth(pageData.permission.del) && row.isManage !== 1"
  393. type="primary"
  394. @click="handleDel(row)"
  395. >删除</el-link
  396. >
  397. <el-divider v-show="row.isManage !== 1" direction="vertical" />
  398. <el-dropdown v-show="row.isManage !== 1">
  399. <el-link type="primary"
  400. >更 多
  401. <el-icon class="el-icon--right">
  402. <component :is="useRenderIcon('ep:arrow-down')" />
  403. </el-icon>
  404. </el-link>
  405. <template #dropdown>
  406. <el-dropdown-menu>
  407. <el-dropdown-item @click="handleResetPasswd(row)"
  408. >重置密码</el-dropdown-item
  409. >
  410. </el-dropdown-menu>
  411. </template>
  412. </el-dropdown>
  413. </div>
  414. </template>
  415. </pure-table>
  416. <user-edit ref="userEditRef" @confirm="_loadData" />
  417. <user-reset-passwd ref="userResetPasswdRef" />
  418. </div>
  419. </template>