index.vue 12 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357
  1. <script setup>
  2. import { CirclePlus } from '@element-plus/icons-vue'
  3. import { ElMessageBox } from 'element-plus'
  4. import { getOrganizationList, postOrganization, putOrganization, delOrganization, getRegion } from '@/api/client/manage'
  5. const { proxy } = getCurrentInstance();
  6. const loading = ref(false);
  7. const tableLoading = ref(false);
  8. const tableData = ref([]);
  9. const queryParams = ref({
  10. pageNum: 1,
  11. pageSize: 1000,
  12. name: '',
  13. provinceCode: '',
  14. type: 0,
  15. status: '',
  16. regionList: []
  17. });
  18. const typeEmun = {
  19. 0: '集团',
  20. 1: '水厂'
  21. }
  22. const formData = ref({});
  23. const formRef = ref(null);
  24. const dialogVisible = ref(false);
  25. const rules = {
  26. name: [
  27. { required: true, message: '请输入机构名称', trigger: 'blur' },
  28. ],
  29. regionList: [
  30. { type: 'array', required: true, message: '请选择省市区', trigger: 'change' }
  31. ]
  32. }
  33. const regionOptions = ref([]);
  34. const typeOptions = [
  35. { value: 0, label: '集团'},
  36. { value: 1, label: '水厂'},
  37. ]
  38. const statusOptions = [
  39. { value: '', label: '全部'},
  40. { value: 0, label: '正常'},
  41. { value: 1, label: '停用'},
  42. ]
  43. const cascaderProps = {
  44. lazy: true,
  45. lazyLoad(node, resolve) {
  46. const { level } = node
  47. getRegion({ regionLevel: level + 1, parentId: node.data.regionId, pageSize: 100 }).then(({ rows }) => {
  48. console.log( "rows", rows );
  49. const nodes = rows.map(item => {
  50. return {
  51. value: item.regionCod,
  52. label: item.regionName,
  53. regionId: item.regionId,
  54. leaf: level >= 2,
  55. }
  56. })
  57. resolve(nodes)
  58. })
  59. },
  60. }
  61. // 新增机构
  62. const handleAddOrganization = () => {
  63. formData.value = { ...formData.value, type: 0, title: "新增机构", isAdd: true }
  64. dialogVisible.value = true;
  65. }
  66. // 添加水厂
  67. const handleAddWaterFactory = (row) => {
  68. formData.value = { ...formData.value, parentId: row.id, parentName: row.name, type: 1, title: "添加水厂", isAdd: true };
  69. dialogVisible.value = true;
  70. }
  71. // 编辑水厂
  72. const handleEditOrganizationOrFactory = (row) => {
  73. const { parentId, name: parentName, type, provinceCode, cityCode, countryCode } = row;
  74. formData.value = {
  75. ...row,
  76. parentId: type == 0 ? 0 : parentId,
  77. parentName,
  78. type,
  79. title: type == 0 ? "编辑机构" : "编辑水厂",
  80. regionList: [provinceCode, cityCode, countryCode]
  81. };
  82. dialogVisible.value = true;
  83. }
  84. // 删除机构or水厂
  85. const handleDelete = async ({ id }) => {
  86. await delOrganization(id);
  87. proxy.$modal.msgSuccess("删除成功");
  88. initPageData();
  89. }
  90. const initPageData = async () => {
  91. tableLoading.value = true;
  92. const { rows } = await getOrganizationList(queryParams.value);
  93. tableData.value = rows.map(item => ({
  94. ...item,
  95. typeText: typeEmun[item.type],
  96. children: item.children ? item.children.map(child => ({
  97. ...child,
  98. typeText: typeEmun[child.type],
  99. parentId: item.id
  100. })) : [],
  101. }));
  102. tableLoading.value = false;
  103. }
  104. // 查询
  105. const handleQuery = async() => {
  106. initPageData();
  107. }
  108. // 重置
  109. const handleReset = () => {
  110. queryParams.value = {
  111. pageNum: 1,
  112. pageSize: 10000,
  113. name: '',
  114. provinceCode: '',
  115. type: 0,
  116. status: '',
  117. regionList: []
  118. }
  119. initPageData();
  120. }
  121. // 重置dialog表单
  122. const handleDialogReset = () => {
  123. formRef.value.resetFields();
  124. formData.value = {};
  125. }
  126. // 切换table - 状态
  127. const onChangeTag= (row) => {
  128. const content = `请确认,是否要${row.status == 0 ? '停用' : '启用'}该${row.type == 0 ? '机构' : '水厂'}?`
  129. ElMessageBox.confirm(
  130. content,
  131. '状态变更提醒',
  132. {
  133. confirmButtonText: '确认',
  134. cancelButtonText: '取消',
  135. type: 'warning',
  136. }
  137. ).then(async () => {
  138. const params = {
  139. id: row.id,
  140. status: row.status == 0 ? 1 : 0
  141. }
  142. await putOrganization(params);
  143. initPageData();
  144. proxy.$modal.msgSuccess("状态变更成功");
  145. }).catch(() => {})
  146. }
  147. // 新增机构 - 保存
  148. const handleDialogConfirm = async () => {
  149. if (!formRef.value) return
  150. await formRef.value.validate(async (valid, fields) => {
  151. if (valid) {
  152. const [provinceCode, cityCode, countryCode] = formData.value.regionList || [];
  153. const params = {
  154. ...formData.value,
  155. provinceCode,
  156. cityCode,
  157. countryCode
  158. }
  159. params.isAdd ? await postOrganization(params) : await putOrganization(params);
  160. initPageData();
  161. formRef.value.resetFields();
  162. dialogVisible.value = false;
  163. proxy.$modal.msgSuccess("操作成功");
  164. } else {
  165. console.log('error submit!', fields)
  166. }
  167. })
  168. }
  169. onMounted(() => {
  170. getRegion({ regionLevel: 1 }).then(({ rows }) => {
  171. regionOptions.value = rows.map(item => ({ value: item.regionCod, label: item.regionName}));
  172. })
  173. initPageData();
  174. })
  175. </script>
  176. <template>
  177. <div>
  178. <el-card shadow="never" :body-style="{ border: '0px' }" style="margin-bottom: 10px;">
  179. <template #header>
  180. <p class="space-x-[10px]">
  181. <span class="font-bold">数据筛选</span>
  182. </p>
  183. </template>
  184. <el-row class="pt-[5px]" justify="space-between" :gutter="20">
  185. <el-col :span="6">
  186. <el-form-item label="机构名称">
  187. <el-input placeholder="请输入机构名称" v-model.trim="queryParams.name"></el-input>
  188. </el-form-item>
  189. </el-col>
  190. <el-col :span="6">
  191. <el-form-item label="所属省份">
  192. <el-select v-model="queryParams.provinceCode" placeholder="请选择所属省份" filterable clearable>
  193. <el-option v-for="item in regionOptions" :key="item.value" :label="item.label" :value="item.value" />
  194. </el-select>
  195. </el-form-item>
  196. </el-col>
  197. <el-col :span="6">
  198. <el-form-item label="机构类型">
  199. <el-select v-model="queryParams.type" placeholder="请选择类型" filterable clearable>
  200. <el-option v-for="item in typeOptions" :key="item.label" :label="item.label" :value="item.value" />
  201. </el-select>
  202. </el-form-item>
  203. </el-col>
  204. <el-col :span="6">
  205. <el-form-item label="状态">
  206. <el-select v-model="queryParams.status" placeholder="请选择状态" filterable clearable>
  207. <el-option v-for="item in statusOptions" :key="item.label" :label="item.label" :value="item.value" />
  208. </el-select>
  209. </el-form-item>
  210. </el-col>
  211. <el-col :span="6" :offset="18">
  212. <div class="flex justify-end">
  213. <el-button type="primary" @click="handleQuery" :loading="loading">查询</el-button>
  214. <el-button @click="handleReset" :loading="loading">重置</el-button>
  215. </div>
  216. </el-col>
  217. </el-row>
  218. </el-card>
  219. <el-card shadow="never" :body-style="{ padding: '20px' }">
  220. <div class="flex justify-between items-center mb-[10px]">
  221. <el-button type="primary" @click="handleAddOrganization" :loading="loading" :icon="CirclePlus">新增机构</el-button>
  222. </div>
  223. <el-table :data="tableData" style="width: 100%" v-loading="tableLoading" row-key="id" border>
  224. <el-table-column prop="name" label="机构名称" width="280" fixed/>
  225. <el-table-column prop="code" label="机构编号" width="180" />
  226. <el-table-column prop="typeText" label="机构类型" width="180"/>
  227. <el-table-column prop="provinceName" label="省份" width="180"/>
  228. <el-table-column prop="lxjcCounts" label="连续检测设备总数" width="180"/>
  229. <el-table-column prop="robotCounts" label="实验室设备总数" width="180"/>
  230. <el-table-column prop="concat" label="联系人" width="180"/>
  231. <el-table-column prop="phone" label="联系电话" width="180"/>
  232. <el-table-column prop="status" label="状态" width="180">
  233. <template #default="{ row }">
  234. <el-check-tag :checked="row.status == 0" type="success" @change="onChangeTag(row)">
  235. {{ row.status == 0 ? '正常' : '停用' }}
  236. </el-check-tag>
  237. </template>
  238. </el-table-column>
  239. <el-table-column prop="createUser.nickName" label="创建人" width="180"/>
  240. <el-table-column prop="createTime" label="创建时间" width="180"/>
  241. <el-table-column prop="address" label="操作" fixed="right" width="220">
  242. <template #default="{ row }">
  243. <el-button text type="primary" size="small" @click="handleAddWaterFactory(row)" :disabled="row.type == 1">添加水厂</el-button>
  244. <el-button text type="primary" size="small" @click="handleEditOrganizationOrFactory(row)">编辑</el-button>
  245. <el-popconfirm title="请确认是否删除?" @confirm="handleDelete(row)" width="200">
  246. <template #reference>
  247. <el-button text type="primary" size="small">删除</el-button>
  248. </template>
  249. </el-popconfirm>
  250. </template>
  251. </el-table-column>
  252. </el-table>
  253. </el-card>
  254. <el-dialog v-model="dialogVisible" :title="formData.title" width="900" @closed="handleDialogReset">
  255. <el-form :model="formData" :rules="rules" ref="formRef" label-width="80px" label-position="left" require-asterisk-position="right">
  256. <el-row justify="space-between">
  257. <el-col :span="11">
  258. <el-form-item label="名称" prop="name">
  259. <el-input v-model="formData.name" placeholder="请输入名称" clearable />
  260. </el-form-item>
  261. </el-col>
  262. <el-col :span="11">
  263. <el-form-item label="排序" prop="sort">
  264. <el-input-number v-model="formData.sort" :min="1" :step="1" step-strictly placeholder="请输入排序序号" style="width: 100%;" />
  265. </el-form-item>
  266. </el-col>
  267. <el-col :span="11">
  268. <el-form-item label="编号" prop="code">
  269. <el-input v-model="formData.code" placeholder="请输入编号" clearable />
  270. </el-form-item>
  271. </el-col>
  272. <el-col :span="11" v-if="formData.type == 1" prop="parentId">
  273. <el-form-item label="上级机构" prop="parentName">
  274. <span>{{ formData.parentName }}</span>
  275. </el-form-item>
  276. </el-col>
  277. <el-col :span="11" prop="regionList">
  278. <el-form-item label="省市区" prop="regionList">
  279. <el-cascader
  280. v-model="formData.regionList"
  281. :props="cascaderProps"
  282. placeholder="请选择省市区"
  283. class="w-full"
  284. />
  285. </el-form-item>
  286. </el-col>
  287. <el-col :span="11">
  288. <el-form-item label="详细地址" prop="address">
  289. <el-input v-model="formData.address" placeholder="请输入详细地址" clearable />
  290. </el-form-item>
  291. </el-col>
  292. <el-col :span="11">
  293. <el-form-item label="经度" prop="longitude">
  294. <el-input v-model="formData.longitude" placeholder="请输入经度" clearable />
  295. </el-form-item>
  296. </el-col>
  297. <el-col :span="11">
  298. <el-form-item label="纬度" prop="latitude">
  299. <el-input v-model="formData.latitude" placeholder="请输入纬度" clearable />
  300. </el-form-item>
  301. </el-col>
  302. <el-col :span="11">
  303. <el-form-item label="状态" prop="status">
  304. <el-select v-model="formData.status" placeholder="请选择状态" clearable>
  305. <el-option label="正常" :value="0" />
  306. <el-option label="停用" :value="1" />
  307. </el-select>
  308. </el-form-item>
  309. </el-col>
  310. <el-col :span="11">
  311. <el-form-item label="联系人" prop="concat">
  312. <el-input v-model="formData.concat" placeholder="请输入联系人" clearable />
  313. </el-form-item>
  314. </el-col>
  315. <el-col :span="11">
  316. <el-form-item label="联系电话" prop="phone">
  317. <el-input v-model="formData.phone" placeholder="请输入联系电话" clearable />
  318. </el-form-item>
  319. </el-col>
  320. </el-row>
  321. </el-form>
  322. <template #footer>
  323. <div class="dialog-footer">
  324. <el-button @click="dialogVisible = false" >取 消</el-button>
  325. <el-button @click="handleDialogConfirm" type="primary">确 定</el-button>
  326. </div>
  327. </template>
  328. </el-dialog>
  329. </div>
  330. </template>