From ce1622d4aa4268c38b9efd1605db0cbc5fd96b1e Mon Sep 17 00:00:00 2001 From: "STW_TTTY\\stwtt" Date: Wed, 1 May 2024 18:11:11 +0700 Subject: [PATCH] =?UTF-8?q?=E0=B9=81=E0=B8=81=E0=B9=89=20=E0=B8=A3?= =?UTF-8?q?=E0=B8=B2=E0=B8=A2=E0=B8=81=E0=B8=B2=E0=B8=A3=E0=B8=A3=E0=B8=B1?= =?UTF-8?q?=E0=B8=9A=E0=B9=82=E0=B8=AD=E0=B8=99=20(=E0=B9=84=E0=B8=A1?= =?UTF-8?q?=E0=B9=88=E0=B9=80=E0=B8=AA=E0=B8=A3=E0=B9=87=E0=B8=88=E0=B8=94?= =?UTF-8?q?=E0=B8=B5)?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../components/Receive/receiveMain.vue | 11 +- .../components/Receive/receiveModal.vue | 451 ++++++++++++++++-- .../interface/response/Receive.ts | 199 +++++++- 3 files changed, 608 insertions(+), 53 deletions(-) diff --git a/src/modules/05_placement/components/Receive/receiveMain.vue b/src/modules/05_placement/components/Receive/receiveMain.vue index ef738b93e..d91061bce 100644 --- a/src/modules/05_placement/components/Receive/receiveMain.vue +++ b/src/modules/05_placement/components/Receive/receiveMain.vue @@ -18,6 +18,7 @@ import type { ResponseRow, } from "@/modules/05_placement/interface/response/Receive"; +const dataRows = ref([]); const $q = useQuasar(); const router = useRouter(); const rows2 = ref([]); @@ -203,6 +204,9 @@ const fecthlistRecevice = async () => { organizationShortName: e.organizationShortName, positionNumber: e.positionNumber, positionPath: e.positionPath, + positionLevelId: e.positionLevelId, + positionTypeId: e.positionTypeId, + positionId: e.positionId, birthday: e.dateOfBirth == null ? "-" @@ -254,10 +258,11 @@ const clickCloseUpload = () => { files.value = null; }; // ปิดโมเดลโครงสร้าง -const openModalTree = (id: string) => { +const openModalTree = (id: string,data:any) => { personalId.value = id; personal.value = listRecevice.value.filter((e: ResponseData) => e.id === id); modalTree.value = true; + dataRows.value = data }; // เปิดโมเดลไฟล์ const openUpload = (id: string) => { @@ -479,7 +484,7 @@ onMounted(() => { diff --git a/src/modules/05_placement/components/Receive/receiveModal.vue b/src/modules/05_placement/components/Receive/receiveModal.vue index 3cee75384..d98f39158 100644 --- a/src/modules/05_placement/components/Receive/receiveModal.vue +++ b/src/modules/05_placement/components/Receive/receiveModal.vue @@ -5,9 +5,22 @@ import { useCounterMixin } from "@/stores/mixin"; import DialogHeader from "@/modules/05_placement/components/PersonalList/DialogHeader.vue"; import DialogFooter from "@/modules/05_placement/components/PersonalList/DialogFooter.vue"; +import CardPosition from "@/modules/05_placement/components/PersonalList/CardPosition.vue"; + import http from "@/plugins/http"; import config from "@/app.config"; +import type { + DataActive, + OrgTree, + DataTree, + SumPosition, + PositionMaim, + PositionNo, + Positions, + DataPositionNo, + TreeMain, +} from "@/modules/05_placement/interface/response/Receive"; const $q = useQuasar(); const mixin = useCounterMixin(); //เรียกฟังก์ชันกลาง const { @@ -19,9 +32,15 @@ const { dialogConfirm, } = mixin; //ฟังก์ชันกลางที่เรียกใช้ +const nodeLevel = ref(0); + +const isAll = ref(false); +const isBlank = ref(false); +const positionNo = ref(); +const posMasterMain = ref([]); const notFound = ref("ไม่พบข้อมูลที่ค้นหา"); const noData = ref("ไม่พบข้อมูลผังโครงสร้าง"); - +const level = ref(); const id = ref(""); const search = ref(""); const selected = ref(""); @@ -35,27 +54,51 @@ const checkValidate = ref(false); const myFormPosition = ref(); const editDataStatus = ref(false); const placementPosition = ref([]); +const filter = ref(""); +const shortName = ref(""); +const nodes = ref>([]); +const lazy = ref(nodes); +const treeId = ref(); +const nodeTree = ref(); // ข้อมูล Tree +const nodeId = ref(""); // id ของ Tree +const itemTaps = ref(); +const selectedPos = ref([]); +const positionId = ref(""); +const datePos = ref(new Date()); +const seletcId = ref(""); +const sumPosition = reactive({ + total: 0, + use: 0, + vacant: 0, + totalRoot: 0, + useRoot: 0, + vacantRoot: 0, +}); // ตำแหน่งเลขที่ -const posNoOptions = ref([ { label: "", value: "" } ]); +const posNoOptions = ref([{ label: "", value: "" }]); // ตำแหน่ง -const positionOptions = ref([ { label: "", value: "" } ]); +const positionOptions = ref([{ label: "", value: "" }]); // ด้าน/สาขา -const positionPathSideOptions = ref([ { label: "", value: "" } ]); +const positionPathSideOptions = ref([{ label: "", value: "" }]); // ตำแหน่งประเภท -const positionTypeOptions = ref([ { label: "", value: "" } ]); +const positionTypeOptions = ref([{ label: "", value: "" }]); // สายงาน -const positionLineOptions = ref([ { label: "", value: "" } ]); +const positionLineOptions = ref([{ label: "", value: "" }]); // ระดับ -const positionLevelOptions = ref([ { label: "", value: "" } ]); +const positionLevelOptions = ref([{ label: "", value: "" }]); const props = defineProps({ personalId: String, + dataRows: { + type: Object, + require: true, + }, modal: Boolean, close: { type: Function, @@ -140,15 +183,18 @@ const myFilterMethod = (node: any, filter: string) => { (node.organizationName && node.organizationName.indexOf(filt) > -1) || (node.positionNum && node.positionNum.indexOf(filt) > -1) || (node.positionName && node.positionName.indexOf(filt) > -1) || - (node.governmentCode && node.governmentCode.toString().indexOf(filt) > -1) || + (node.governmentCode && + node.governmentCode.toString().indexOf(filt) > -1) || (node.agency && node.agency.indexOf(filt) > -1) || (node.government && node.government.indexOf(filt) > -1) || (node.department && node.department.indexOf(filt) > -1) || (node.pile && node.pile.indexOf(filt) > -1) || - (node.organizationShortName && node.organizationShortName.indexOf(filt) > -1) || + (node.organizationShortName && + node.organizationShortName.indexOf(filt) > -1) || (node.positionSideName && node.positionSideName.indexOf(filt) > -1) || (node.executivePosition && node.executivePosition.indexOf(filt) > -1) || - (node.executivePositionSide && node.executivePositionSide.indexOf(filt) > -1) || + (node.executivePositionSide && + node.executivePositionSide.indexOf(filt) > -1) || (node.positionLevel && node.positionLevel.indexOf(filt) > -1) ); }; @@ -197,21 +243,33 @@ const saveAppoint = async () => { }); }; -const closeModal = () => { - if (editDataStatus.value == true) { - dialogConfirm( - $q, - async () => { - editDataStatus.value = false; - await closeAndClear(); - }, - `ข้อมูลมีการแก้ไข`, - `ยืนยันที่จะปิดโดยไม่บันทึกใช่หรือไม่?` - ); - } else { - closeAndClear(); - } -}; +// const closeModal = () => { +// if (editDataStatus.value == true) { +// dialogConfirm( +// $q, +// async () => { +// editDataStatus.value = false; +// await closeAndClear(); +// }, +// `ข้อมูลมีการแก้ไข`, +// `ยืนยันที่จะปิดโดยไม่บันทึกใช่หรือไม่?` +// ); +// } else { +// closeAndClear(); +// } +// }; + +/** function closePopup*/ +async function closeModal() { + await props.close(); + clearData(); +} + +/** function clearData*/ +function clearData() { + nodeId.value = ""; + expanded.value = []; +} const closeAndClear = async () => { await props.close(); @@ -227,7 +285,6 @@ const closeAndClear = async () => { dataForm.positionTypeId = ""; }; - const selectedPosition = async (data: any) => { if (data.name == null && selected.value != data.keyId) { editDataStatus.value = true; @@ -362,6 +419,220 @@ function findByPerson(element: any): any { } return null; } +const activeId = ref(); +const draftId = ref(); + +const dataActive = ref(); +const isPublic = ref(false); +const orgPublishDate = ref(null); +/** function เรียกข้อมูลโครงสร้าง แบบปัจุบันและ แบบร่าง*/ +async function fetchOrganizationActive() { + showLoader(); + await http + .get(config.API.activeOrganization) + .then((res) => { + const data = res.data.result; + activeId.value = data.activeId; + draftId.value = data.draftId; + dataActive.value = data; + isPublic.value = data.isPublic; + orgPublishDate.value = data.orgPublishDate; + + fetchDataTree(data.activeId); + }) + .catch((err) => { + messageError($q, err); + }) + .finally(() => { + hideLoader(); + }); +} + +function getSumPosition(data: SumPosition) { + sumPosition.total = data.totalPosition; + sumPosition.totalRoot = data.totalRootPosition ? data.totalRootPosition : 0; + + sumPosition.use = data.totalPositionCurrentUse; + sumPosition.useRoot = data.totalRootPositionCurrentUse + ? data.totalRootPositionCurrentUse + : 0; + + sumPosition.vacant = data.totalPositionCurrentVacant; + sumPosition.vacantRoot = data.totalRootPositionCurrentVacant + ? data.totalRootPositionCurrentVacant + : 0; +} + +/** + * function fetch ข้อมูลของ Tree + * @param id id โครงสร้าง + */ +async function fetchDataTree(id: string) { + showLoader(); + await http + .get(config.API.orgByid(id.toString())) + .then((res) => { + const data = res.data.result; + nodes.value = data; + filterItemsTaps(data); + }) + .catch((err) => { + messageError($q, err); + }) + .finally(() => { + hideLoader(); + }); +} + +/** + * funtion เลือกข้อมูล Tree + * @param data ข่อมูล Tree + */ +function updateSelected(data: DataTree) { + // positionId.value = ""; + // seletcId.value = ""; + // selectedPos.value = []; + // datePos.value = new Date(); + + nodeId.value = data.orgTreeId ? data.orgTreeId : ""; + nodeLevel.value = data.orgLevel; + fetchDataTable(data.orgTreeId, data.orgLevel); +} + +async function fetchDataTable(id: string, level: number = 0) { + console.log(props.dataRows); + showLoader(); + const body = { + node: level, + nodeId: id, + position: props?.dataRows?.positionPath, + typeCommand: "MOVE", + posLevel: props.dataRows?.positionLevelId, + posType: props.dataRows?.positionTypeId, + isAll: isAll.value, + isBlank: isBlank.value, + }; + + await http + .post(config.API.orgPosPlacement, body) + .then((res) => { + const dataMain: PositionMaim[] = []; + posMasterMain.value = res.data.result.data; + + res.data.result.data.forEach((e: PositionNo) => { + const p = e.positions; + if (p.length !== 0) { + const a = p.find((el: Positions) => el.positionIsSelected === true); + const { id, ...rest } = a ? a : p[0]; + const data: any = { ...e, ...rest }; + dataMain.push(data); + } + }); + const listPosNo: DataPositionNo[] = dataMain.map((e: PositionMaim) => ({ + id: e.id, + isPosition: e.isPosition, + posMasterNo: + e.orgShortname + + (e.posMasterNoPrefix != null ? e.posMasterNoPrefix : "") + + e.posMasterNo + + (e.posMasterNoSuffix != null ? e.posMasterNoSuffix : ""), + positionName: e.positionName, + posTypeName: e.posTypeName, + posLevelName: e.posLevelName, + positionIsSelected: e.positionIsSelected + ? e.fullNameCurrentHolder + : "-", + isSit: e.isSit, + positions: e.positions, + node: e.node, + nodeId: e.nodeId, + })); + + positionNo.value = listPosNo; + }) + .catch((err) => { + messageError($q, err); + }) + .finally(() => { + setTimeout(() => { + hideLoader(); + }, 1000); + }); +} + +function filterItemsTaps(data: TreeMain[]) { + let orgTreeIds: string[] = []; + for (const child of data) { + orgTreeIds.push(child.orgTreeId); + if (child.children) { + orgTreeIds = orgTreeIds.concat(filterItemsTaps(child.children)); + } + } + itemTaps.value = orgTreeIds; + return orgTreeIds; +} + +/** + * function fetch ข้อมูล expanded tree + * @param level levelTree + * @param id treeId + */ +async function fetchPosFind(level: number, id: string) { + showLoader(); + const body = { + node: level, + nodeId: id, + }; + await http + .post(config.API.orgPosFind, body) + .then((res) => { + const data = res.data.result; + expanded.value = data; + nodeId.value = id; + positionId.value = props?.dataRows?.posmasterId; + seletcId.value = props?.dataRows?.positionId; + datePos.value = props?.dataRows?.reportingDateFullDate; + + fetchDataTable(nodeId.value, level); + }) + .catch((e) => { + messageError($q, e); + hideLoader(); + }); +} + +watch( + () => props.modal, + async () => { + if (props.modal) { + await fetchOrganizationActive(); + if (props?.dataRows?.node !== null && props?.dataRows?.nodeId !== null) { + await fetchPosFind(props?.dataRows?.node, props?.dataRows?.nodeId); + } else { + expanded.value = []; + } + } + } +); + +watch( + () => isAll.value, + (value, oldVal) => { + if (value !== oldVal) { + fetchDataTable(nodeId.value, nodeLevel.value); + } + } +); + +watch( + () => isBlank.value, + (value, oldVal) => { + if (value !== oldVal) { + fetchDataTable(nodeId.value, nodeLevel.value); + } + } +); + onMounted(async () => { await fetchPublishFile(); await loadTreeData(); @@ -370,12 +641,105 @@ onMounted(async () => { diff --git a/src/modules/05_placement/interface/response/Receive.ts b/src/modules/05_placement/interface/response/Receive.ts index e4910941c..ebfead083 100644 --- a/src/modules/05_placement/interface/response/Receive.ts +++ b/src/modules/05_placement/interface/response/Receive.ts @@ -19,13 +19,15 @@ interface ResponseRow { statusText: string; createdAt: Date | null; dateText: string | null; - educationOld: string - organizationPositionOld: string - positionTypeOld: string - positionLevelOld: string - positionNumberOld: string - amountOld: number - + educationOld: string; + organizationPositionOld: string; + positionTypeOld: string; + positionLevelOld: string; + positionNumberOld: string; + positionId: string; + positionTypeId: string; + positionLevelId: string; + amountOld: number; } interface ResponseData { @@ -62,7 +64,186 @@ interface ResponseData { recruitDate: Date; salary: number; status: string; - amountOld: number + amountOld: number; } -export type { ResponseTitle, ResponseData, ResponseRow }; +interface DataActive { + activeId: string; + activeName: string; + draftId: string; + draftName: string; + isPublic: boolean; + orgPublishDate: Date | null; +} + +interface OrgTree { + orgTreeId: string; + orgRootId: string; + orgLevel: number; + orgTreeName: string; + orgTreeShortName: string; + orgTreeCode: string; + orgCode: string; + orgTreeRank: string; + orgTreeOrder: number | null; + orgRootCode: string; + orgTreePhoneEx: string; + orgTreePhoneIn: string; + orgTreeFax: string; + orgRevisionId: string; + children: OrgTree[]; +} + +interface DataTree { + orgTreeId: string; + orgRootId?: string; + orgLevel: number; + orgName: string; + orgTreeName: string; + orgTreeShortName: string; + orgTreeCode: string; + orgCode: string; + orgTreeRank: string; + orgTreeOrder: number; + orgRootCode?: string; + orgTreePhoneEx: string; + orgTreePhoneIn: string; + orgTreeFax: string; + orgRevisionId: string; + orgRootName: string; + totalPosition: number; + totalPositionCurrentUse: number; + totalPositionCurrentVacant: number; + totalPositionNextUse: number; + totalPositionNextVacant: number; + totalRootPosition: number; + totalRootPositionCurrentUse: number; + totalRootPositionCurrentVacant: number; + totalRootPositionNextUse: number; + totalRootPositionNextVacant: number; + + children?: DataTree[]; +} +interface SumPosition { + totalPosition: number; + totalPositionCurrentUse: number; + totalPositionCurrentVacant: number; + totalPositionNextUse: number; + totalPositionNextVacant: number; + totalRootPosition: number; + totalRootPositionCurrentUse: number; + totalRootPositionCurrentVacant: number; + totalRootPositionNextUse: number; + totalRootPositionNextVacant: number; +} + +interface PositionMaim { + fullNameCurrentHolder: string | null; + fullNameNextHolder: string | null; + id: string; + isPosition: boolean; + isSit: boolean; + orgRootId: string; + orgShortname: string; + posMasterNo: number; + posMasterNoPrefix: string; + posMasterNoSuffix: string; + posExecutiveId: string; + posExecutiveName: string; + posLevelId: string; + posLevelName: string; + posTypeId: string; + posTypeName: string; + positionArea: string; + positionExecutiveField: string; + positionField: string; + positionIsSelected: boolean; + positionName: string; + positions: Positions[]; + node: number; + nodeId: string; +} + +interface PositionNo { + fullNameCurrentHolder: string | null; + fullNameNextHolder: string | null; + id: string; + isPosition: boolean; + isSit: boolean; + orgRootId: string; + orgShortname: string; + posMasterNo: number; + posMasterNoPrefix: string; + posMasterNoSuffix: string; + positions: Positions[]; +} + +interface Positions { + id: string; + posExecutiveId: string; + posExecutiveName: string; + posLevelId: string; + posLevelName: string; + posTypeId: string; + posTypeName: string; + positionArea: string; + positionExecutiveField: string; + positionField: string; + positionIsSelected: boolean; + positionName: string; +} + +interface DataPositionNo { + id: string; + isPosition: boolean; + posMasterNo: string; + positionName: string; + posTypeName: string; + posLevelName: string; + positionIsSelected: string | null; + isSit: boolean; + positions: Positions[]; +} + +interface TreeMain { + children: TreeMain[]; // ปรับเป็นชนิดข้อมูลที่ถูกต้องตามโครงสร้างของ children ถ้าเป็นไปได้ + orgCode: string; + orgLevel: number; + orgName: string; + orgRevisionId: string; + orgRootName: string; + orgTreeCode: string; + orgTreeFax: string; + orgTreeId: string; + orgTreeName: string; + orgTreeOrder: number; + orgTreePhoneEx: string; + orgTreePhoneIn: string; + orgTreeRank: string; + orgTreeShortName: string; + totalPosition: number; + totalPositionCurrentUse: number; + totalPositionCurrentVacant: number; + totalPositionNextUse: number; + totalPositionNextVacant: number; + totalRootPosition: number; + totalRootPositionCurrentUse: number; + totalRootPositionCurrentVacant: number; + totalRootPositionNextUse: number; + totalRootPositionNextVacant: number; +} + +export type { + ResponseTitle, + ResponseData, + ResponseRow, + DataActive, + OrgTree, + DataTree, + SumPosition, + PositionMaim, + PositionNo, + Positions, + DataPositionNo, + TreeMain, +};