summaryrefslogtreecommitdiff
path: root/lib/poa/service.ts
diff options
context:
space:
mode:
authorjoonhoekim <26rote@gmail.com>2025-03-27 18:50:59 +0900
committerjoonhoekim <26rote@gmail.com>2025-03-27 18:50:59 +0900
commit281a4060cff0396253192f4e852be6770ad97cbd (patch)
treedc7f7d6e01469982638be02889fa1bb95fe60d84 /lib/poa/service.ts
parent34bbeb86c1a8d24b5f526710889b5e54d699cfd0 (diff)
feat: POA 관련 파일 추가 및 contract 스키마 수정
Diffstat (limited to 'lib/poa/service.ts')
-rw-r--r--lib/poa/service.ts132
1 files changed, 132 insertions, 0 deletions
diff --git a/lib/poa/service.ts b/lib/poa/service.ts
new file mode 100644
index 00000000..a11cbdd8
--- /dev/null
+++ b/lib/poa/service.ts
@@ -0,0 +1,132 @@
+"use server";
+
+import db from "@/db/db";
+import { GetChangeOrderSchema } from "./validations";
+import { unstable_cache } from "@/lib/unstable-cache";
+import { filterColumns } from "@/lib/filter-columns";
+import {
+ asc,
+ desc,
+ ilike,
+ and,
+ or,
+ count,
+} from "drizzle-orm";
+
+import {
+ poaDetailView,
+} from "@/db/schema/contract";
+
+/**
+ * POA 목록 조회
+ */
+export async function getChangeOrders(input: GetChangeOrderSchema) {
+ return unstable_cache(
+ async () => {
+ try {
+ const offset = (input.page - 1) * input.perPage;
+
+ // 1. Build where clause
+ let advancedWhere;
+ try {
+ advancedWhere = filterColumns({
+ table: poaDetailView,
+ filters: input.filters,
+ joinOperator: input.joinOperator,
+ });
+ } catch (whereErr) {
+ console.error("Error building advanced where:", whereErr);
+ advancedWhere = undefined;
+ }
+
+ let globalWhere;
+ if (input.search) {
+ try {
+ const s = `%${input.search}%`;
+ globalWhere = or(
+ ilike(poaDetailView.contractNo, s),
+ ilike(poaDetailView.originalContractName, s),
+ ilike(poaDetailView.projectCode, s),
+ ilike(poaDetailView.projectName, s),
+ ilike(poaDetailView.vendorName, s)
+ );
+ } catch (searchErr) {
+ console.error("Error building search where:", searchErr);
+ globalWhere = undefined;
+ }
+ }
+
+ // 2. Combine where clauses
+ let finalWhere;
+ if (advancedWhere && globalWhere) {
+ finalWhere = and(advancedWhere, globalWhere);
+ } else {
+ finalWhere = advancedWhere || globalWhere;
+ }
+
+ // 3. Build order by
+ let orderBy;
+ try {
+ orderBy =
+ input.sort.length > 0
+ ? input.sort.map((item) =>
+ item.desc
+ ? desc(poaDetailView[item.id])
+ : asc(poaDetailView[item.id])
+ )
+ : [desc(poaDetailView.createdAt)];
+ } catch (orderErr) {
+ console.error("Error building order by:", orderErr);
+ orderBy = [desc(poaDetailView.createdAt)];
+ }
+
+ // 4. Execute queries
+ let data = [];
+ let total = 0;
+
+ try {
+ const queryBuilder = db.select().from(poaDetailView);
+
+ if (finalWhere) {
+ queryBuilder.where(finalWhere);
+ }
+
+ queryBuilder.orderBy(...orderBy);
+ queryBuilder.offset(offset).limit(input.perPage);
+
+ data = await queryBuilder;
+
+ const countBuilder = db
+ .select({ count: count() })
+ .from(poaDetailView);
+
+ if (finalWhere) {
+ countBuilder.where(finalWhere);
+ }
+
+ const countResult = await countBuilder;
+ total = countResult[0]?.count || 0;
+ } catch (queryErr) {
+ console.error("Query execution failed:", queryErr);
+ throw queryErr;
+ }
+
+ const pageCount = Math.ceil(total / input.perPage);
+
+ return { data, pageCount };
+ } catch (err) {
+ console.error("Error in getChangeOrders:", err);
+ if (err instanceof Error) {
+ console.error("Error message:", err.message);
+ console.error("Error stack:", err.stack);
+ }
+ return { data: [], pageCount: 0 };
+ }
+ },
+ [JSON.stringify(input)],
+ {
+ revalidate: 3600,
+ tags: [`poa`],
+ }
+ )();
+} \ No newline at end of file