import { sql } from "drizzle-orm";
import { date, datetime, decimal, float, foreignKey, index, int, json, mysqlTable, primaryKey, text, timestamp, tinyint, unique, varchar } from "drizzle-orm/mysql-core";
//* 별도 import 행으로 둔다 — 위 행은 introspect 산출물이라 손대면 재생성 diff 가 커진다(M3 §D1).
import { bigint } from "drizzle-orm/mysql-core";

export const logFailMailer = mysqlTable("log_fail_mailer", {
	lfmId: int("lfm_id", { unsigned: true }).autoincrement().primaryKey().notNull(),
	sagId: int("sag_id").notNull(),
	sagCode: varchar("sag_code", { length: 20 }),
	sagEmail: varchar("sag_email", { length: 128 }).notNull(),
	lfmFailReason: text("lfm_fail_reason").notNull(),
	lfmUpdatedAt: datetime("lfm_updated_at", { mode: 'string'}),
	lfmCreatedAt: datetime("lfm_created_at", { mode: 'string'}).default(sql`(CURRENT_TIMESTAMP)`).notNull(),
},
(table) => {
	return {
		logFailMailerLfmId: primaryKey({ columns: [table.lfmId], name: "log_fail_mailer_lfm_id"}),
	}
});

export const logTreat = mysqlTable("log_treat", {
	ltrId: int("ltr_id", { unsigned: true }).autoincrement().primaryKey().notNull(),
	memType: varchar("mem_type", { length: 15 }).notNull(),
	memLoginId: varchar("mem_login_id", { length: 20 }).notNull(),
	usrName: varchar("usr_name", { length: 128 }).notNull(),
	usrPhone: varchar("usr_phone", { length: 128 }).notNull(),
	usrBirth: varchar("usr_birth", { length: 128 }).notNull(),
	agcId: int("agc_id"),
	agcCorporateName: varchar("agc_corporate_name", { length: 30 }),
	altCode: varchar("alt_code", { length: 30 }).notNull(),
	oddTransactionId: varchar("odd_transaction_id", { length: 30 }).notNull(),
	codefRequestType: varchar("codef_request_type", { length: 10 }).notNull(),
	codefInitiatedBy: varchar("codef_initiated_by", { length: 10 }).notNull(),
	codefProvider: varchar("codef_provider", { length: 16 }),
	codefRequestStage: varchar("codef_request_stage", { length: 10 }).notNull(),
	codefCertType: varchar("codef_cert_type", { length: 10 }).notNull(),
	codefResultStatus: varchar("codef_result_status", { length: 10 }).notNull(),
	codefResultCode: varchar("codef_result_code", { length: 10 }).notNull(),
	codefResultMessage: text("codef_result_message").notNull(),
	codefElapsedMs: int("codef_elapsed_ms"), //* 2차 수집 호출 소요 ms (측정 벤더만, null=미측정)
	codefTimeout: tinyint("codef_timeout").default(0).notNull(), //* 조회 타임아웃 실패 여부
	ltrCreatedAt: datetime("ltr_created_at", { mode: 'string'}).default(sql`(CURRENT_TIMESTAMP)`).notNull(),
},
(table) => {
	return {
		logTreatLtrId: primaryKey({ columns: [table.ltrId], name: "log_treat_ltr_id"}),
	}
});

export const tcClinicalResultMajor = mysqlTable("tc_clinical_result_major", {
	crmId: int("crm_id").autoincrement().primaryKey().notNull(),
	crmDisplayName: varchar("crm_display_name", { length: 255 }).notNull(),
	crmRegDate: datetime("crm_reg_date", { mode: 'string'}).default(sql`(CURRENT_TIMESTAMP)`),
	crmUpdDate: datetime("crm_upd_date", { mode: 'string'}).default(sql`(CURRENT_TIMESTAMP)`),
},
(table) => {
	return {
		tcClinicalResultMajorCrmId: primaryKey({ columns: [table.crmId], name: "tc_clinical_result_major_crm_id"}),
	}
});

export const tcClinicalResultMiddle = mysqlTable("tc_clinical_result_middle", {
	crmiId: int("crmi_id").autoincrement().primaryKey().notNull(),
	crmId: int("crm_id").notNull().references(() => tcClinicalResultMajor.crmId),
	crmiDisplayName: varchar("crmi_display_name", { length: 500 }).notNull(),
	crmiRegDate: datetime("crmi_reg_date", { mode: 'string'}).default(sql`(CURRENT_TIMESTAMP)`),
	crmiUpdDate: datetime("crmi_upd_date", { mode: 'string'}).default(sql`(CURRENT_TIMESTAMP)`),
},
(table) => {
	return {
		tcClinicalResultMiddleCrmiId: primaryKey({ columns: [table.crmiId], name: "tc_clinical_result_middle_crmi_id"}),
	}
});

export const ttClinicalResultMajor = mysqlTable("tt_clinical_result_major", {
	crmId: int("crm_id").notNull(),
	crmDisplayName: varchar("crm_display_name", { length: 255 }).notNull(),
	crmRegDate: datetime("crm_reg_date", { mode: 'string'}),
	crmUpdDate: datetime("crm_upd_date", { mode: 'string'}),
},
(table) => {
	return {
		ttClinicalResultMajorCrmId: primaryKey({ columns: [table.crmId], name: "tt_clinical_result_major_crm_id"}),
	}
});

export const ttClinicalResultMiddle = mysqlTable("tt_clinical_result_middle", {
	crmiId: int("crmi_id").notNull(),
	crmId: int("crm_id").notNull(),
	crmiDisplayName: varchar("crmi_display_name", { length: 500 }).notNull(),
	crmiRegDate: datetime("crmi_reg_date", { mode: 'string'}),
	crmiUpdDate: datetime("crmi_upd_date", { mode: 'string'}),
},
(table) => {
	return {
		ttClinicalResultMiddleCrmiId: primaryKey({ columns: [table.crmiId], name: "tt_clinical_result_middle_crmi_id"}),
	}
});

export const tcCommon = mysqlTable("tc_common", {
	cmnId: varchar("cmn_id", { length: 10 }).notNull(),
	cmnParentId: varchar("cmn_parent_id", { length: 10 }),
	cmnName: varchar("cmn_name", { length: 30 }),
},
(table) => {
	return {
		tcCommonCmnId: primaryKey({ columns: [table.cmnId], name: "tc_common_cmn_id"}),
	}
});

export const tcCompareBasic = mysqlTable("tc_compare_basic", {
	cpbId: int("cpb_id", { unsigned: true }).autoincrement().primaryKey().notNull(),
	cpbType: varchar("cpb_type", { length: 10 }).notNull(),
	cpbDiseaseCode: varchar("cpb_disease_code", { length: 10 }).notNull(),
	cpbName: varchar("cpb_name", { length: 255 }).notNull(),
	cpbViewName: text("cpb_view_name"),
	cpbIsSicked: tinyint("cpb_is_sicked").default(0).notNull(),
	cpbUpdatedAt: datetime("cpb_updated_at", { mode: 'string'}),
	cpbCreatedAt: datetime("cpb_created_at", { mode: 'string'}).default(sql`(CURRENT_TIMESTAMP)`).notNull(),
},
(table) => {
	return {
		tcCompareBasicCpbId: primaryKey({ columns: [table.cpbId], name: "tc_compare_basic_cpb_id"}),
		tcCompareBasicCpbTypeIdx: unique("tc_compare_basic_cpb_type_IDX").on(table.cpbType, table.cpbDiseaseCode),
	}
});

export const tcCompareDetail = mysqlTable("tc_compare_detail", {
	cpdId: int("cpd_id", { unsigned: true }).autoincrement().primaryKey().notNull(),
	cpdType: varchar("cpd_type", { length: 10 }).notNull(),
	cpdName: varchar("cpd_name", { length: 255 }).notNull(),
	cpdViewName: text("cpd_view_name"),
	cpdUpdatedAt: datetime("cpd_updated_at", { mode: 'string'}),
	cpdCreatedAt: datetime("cpd_created_at", { mode: 'string'}).default(sql`(CURRENT_TIMESTAMP)`).notNull(),
},
(table) => {
	return {
		cpdNameIdx: index("tc_compare_detail_cpd_name_IDX").on(table.cpdName),
		cpdTypeIdx: index("tc_compare_detail_cpd_type_IDX").on(table.cpdType),
		tcCompareDetailCpdId: primaryKey({ columns: [table.cpdId], name: "tc_compare_detail_cpd_id"}),
	}
});

export const tcDiseaseDetail = mysqlTable("tc_disease_detail", {
	ddtMajorCode: varchar("ddt_major_code", { length: 10 }).notNull(),
	ddtMiddleCode: varchar("ddt_middle_code", { length: 10 }).notNull(),
	ddtMinorCode: varchar("ddt_minor_code", { length: 10 }).notNull(),
	ddtDetailCode: varchar("ddt_detail_code", { length: 10 }).notNull(),
	ddtDetailName: varchar("ddt_detail_name", { length: 200 }).notNull(),
	ddtInsuranceComment: varchar("ddt_insurance_comment", { length: 200 }),
	ddtRegDate: timestamp("ddt_reg_date", { mode: 'string' }).defaultNow(),
	ddtUpdDate: timestamp("ddt_upd_date", { mode: 'string' }).defaultNow().onUpdateNow(),
},
(table) => {
	return {
		idxDdtDetailName: index("idx_ddt_detail_name").on(table.ddtDetailName),
		idxDdtMinor: index("idx_ddt_minor").on(table.ddtMajorCode, table.ddtMiddleCode, table.ddtMinorCode),
		fkDdtMinor: foreignKey({
			columns: [table.ddtMajorCode, table.ddtMiddleCode, table.ddtMinorCode],
			foreignColumns: [tcDiseaseMinor.dsnMajorCode, tcDiseaseMinor.dsnMiddleCode, tcDiseaseMinor.dsnMinorCode],
			name: "fk_ddt_minor"
		}).onUpdate("cascade").onDelete("cascade"),
		tcDiseaseDetailDdtMajorCodeDdtMiddleCodeDdtMinorCodeDdtDetailCode: primaryKey({ columns: [table.ddtMajorCode, table.ddtMiddleCode, table.ddtMinorCode, table.ddtDetailCode], name: "tc_disease_detail_ddt_major_code_ddt_middle_code_ddt_minor_code_ddt_detail_code"}),
	}
});

export const tcDiseaseMajor = mysqlTable("tc_disease_major", {
	dsmMajorCode: varchar("dsm_major_code", { length: 10 }).notNull(),
	dsmMajorName: varchar("dsm_major_name", { length: 200 }).notNull(),
	dsmInsuranceComment: varchar("dsm_insurance_comment", { length: 200 }),
	dsmRegDate: timestamp("dsm_reg_date", { mode: 'string' }).defaultNow(),
	dsmUpdDate: timestamp("dsm_upd_date", { mode: 'string' }).defaultNow().onUpdateNow(),
},
(table) => {
	return {
		idxDsmMajorName: index("idx_dsm_major_name").on(table.dsmMajorName),
		tcDiseaseMajorDsmMajorCode: primaryKey({ columns: [table.dsmMajorCode], name: "tc_disease_major_dsm_major_code"}),
	}
});

export const tcDiseaseMiddle = mysqlTable("tc_disease_middle", {
	dsdMajorCode: varchar("dsd_major_code", { length: 10 }).notNull().references(() => tcDiseaseMajor.dsmMajorCode, { onDelete: "cascade", onUpdate: "cascade" } ),
	dsdMiddleCode: varchar("dsd_middle_code", { length: 10 }).notNull(),
	dsdMiddleName: varchar("dsd_middle_name", { length: 200 }).notNull(),
	dsdInsuranceComment: varchar("dsd_insurance_comment", { length: 200 }),
	dsdRegDate: timestamp("dsd_reg_date", { mode: 'string' }).defaultNow(),
	dsdUpdDate: timestamp("dsd_upd_date", { mode: 'string' }).defaultNow().onUpdateNow(),
},
(table) => {
	return {
		idxDsdMajor: index("idx_dsd_major").on(table.dsdMajorCode),
		idxDsdMiddleName: index("idx_dsd_middle_name").on(table.dsdMiddleName),
		tcDiseaseMiddleDsdMajorCodeDsdMiddleCode: primaryKey({ columns: [table.dsdMajorCode, table.dsdMiddleCode], name: "tc_disease_middle_dsd_major_code_dsd_middle_code"}),
	}
});

export const tcDiseaseMinor = mysqlTable("tc_disease_minor", {
	dsnMajorCode: varchar("dsn_major_code", { length: 10 }).notNull(),
	dsnMiddleCode: varchar("dsn_middle_code", { length: 10 }).notNull(),
	dsnMinorCode: varchar("dsn_minor_code", { length: 10 }).notNull(),
	dsnMinorName: varchar("dsn_minor_name", { length: 200 }).notNull(),
	dsnInsuranceComment: varchar("dsn_insurance_comment", { length: 200 }),
	dsnRegDate: timestamp("dsn_reg_date", { mode: 'string' }).defaultNow(),
	dsnUpdDate: timestamp("dsn_upd_date", { mode: 'string' }).defaultNow().onUpdateNow(),
},
(table) => {
	return {
		idxDsnMiddle: index("idx_dsn_middle").on(table.dsnMajorCode, table.dsnMiddleCode),
		idxDsnMinorName: index("idx_dsn_minor_name").on(table.dsnMinorName),
		fkDsnMiddle: foreignKey({
			columns: [table.dsnMajorCode, table.dsnMiddleCode],
			foreignColumns: [tcDiseaseMiddle.dsdMajorCode, tcDiseaseMiddle.dsdMiddleCode],
			name: "fk_dsn_middle"
		}).onUpdate("cascade").onDelete("cascade"),
		tcDiseaseMinorDsnMajorCodeDsnMiddleCodeDsnMinorCode: primaryKey({ columns: [table.dsnMajorCode, table.dsnMiddleCode, table.dsnMinorCode], name: "tc_disease_minor_dsn_major_code_dsn_middle_code_dsn_minor_code"}),
	}
});

export const tcDiseaseFineClassification = mysqlTable("tc_disease_fine_classification", {
	dfcMajorCode: varchar("dfc_major_code", { length: 10 }).notNull(),
	dfcMiddleCode: varchar("dfc_middle_code", { length: 10 }).notNull(),
	dfcMinorCode: varchar("dfc_minor_code", { length: 10 }).notNull(),
	dfcDetailCode: varchar("dfc_detail_code", { length: 10 }).notNull(),
	dfcFineCode: varchar("dfc_fine_code", { length: 10 }).notNull(),
	dfcFineName: varchar("dfc_fine_name", { length: 200 }).notNull(),
	dfcInsuranceComment: varchar("dfc_insurance_comment", { length: 200 }),
	dfcRegDate: timestamp("dfc_reg_date", { mode: 'string' }).defaultNow(),
	dfcUpdDate: timestamp("dfc_upd_date", { mode: 'string' }).defaultNow().onUpdateNow(),
},
(table) => {
	return {
		idxDfcFineName: index("idx_dfc_fine_name").on(table.dfcFineName),
		idxDfcDetail: index("idx_dfc_detail").on(table.dfcMajorCode, table.dfcMiddleCode, table.dfcMinorCode, table.dfcDetailCode),
		fkDfcDetail: foreignKey({
			columns: [table.dfcMajorCode, table.dfcMiddleCode, table.dfcMinorCode, table.dfcDetailCode],
			foreignColumns: [tcDiseaseDetail.ddtMajorCode, tcDiseaseDetail.ddtMiddleCode, tcDiseaseDetail.ddtMinorCode, tcDiseaseDetail.ddtDetailCode],
			name: "fk_dfc_detail"
		}).onUpdate("cascade").onDelete("cascade"),
		tcDiseaseFineClassificationPk: primaryKey({ columns: [table.dfcMajorCode, table.dfcMiddleCode, table.dfcMinorCode, table.dfcDetailCode, table.dfcFineCode], name: "tc_disease_fine_classification_pk"}),
	}
});

export const tcDiseaseSubFineClassification = mysqlTable("tc_disease_sub_fine_classification", {
	dsfMajorCode: varchar("dsf_major_code", { length: 10 }).notNull(),
	dsfMiddleCode: varchar("dsf_middle_code", { length: 10 }).notNull(),
	dsfMinorCode: varchar("dsf_minor_code", { length: 10 }).notNull(),
	dsfDetailCode: varchar("dsf_detail_code", { length: 10 }).notNull(),
	dsfFineCode: varchar("dsf_fine_code", { length: 10 }).notNull(),
	dsfSubFineCode: varchar("dsf_sub_fine_code", { length: 10 }).notNull(),
	dsfSubFineName: varchar("dsf_sub_fine_name", { length: 200 }).notNull(),
	dsfInsuranceComment: varchar("dsf_insurance_comment", { length: 200 }),
	dsfRegDate: timestamp("dsf_reg_date", { mode: 'string' }).defaultNow(),
	dsfUpdDate: timestamp("dsf_upd_date", { mode: 'string' }).defaultNow().onUpdateNow(),
},
(table) => {
	return {
		idxDsfSubFineName: index("idx_dsf_sub_fine_name").on(table.dsfSubFineName),
		idxDsfFine: index("idx_dsf_fine").on(table.dsfMajorCode, table.dsfMiddleCode, table.dsfMinorCode, table.dsfDetailCode, table.dsfFineCode),
		fkDsfFine: foreignKey({
			columns: [table.dsfMajorCode, table.dsfMiddleCode, table.dsfMinorCode, table.dsfDetailCode, table.dsfFineCode],
			foreignColumns: [tcDiseaseFineClassification.dfcMajorCode, tcDiseaseFineClassification.dfcMiddleCode, tcDiseaseFineClassification.dfcMinorCode, tcDiseaseFineClassification.dfcDetailCode, tcDiseaseFineClassification.dfcFineCode],
			name: "fk_dsf_fine"
		}).onUpdate("cascade").onDelete("cascade"),
		tcDiseaseSubFineClassificationPk: primaryKey({ columns: [table.dsfMajorCode, table.dsfMiddleCode, table.dsfMinorCode, table.dsfDetailCode, table.dsfFineCode, table.dsfSubFineCode], name: "tc_disease_sub_fine_classification_pk"}),
	}
});

export const tcSearchDisease = mysqlTable("tc_search_disease", {
	sdsCode: varchar("sds_code", { length: 10 }).notNull(),
	sdsName: varchar("sds_name", { length: 100 }).notNull(),
	sdsContent: text("sds_content"),
	sdsCreatedAt: datetime("sds_created_at", { mode: 'string'}).default(sql`(CURRENT_TIMESTAMP)`).notNull(),
	sdsUpdatedAt: datetime("sds_updated_at", { mode: 'string'}),
},
(table) => {
	return {
		tcSearchDiseaseSdsCode: primaryKey({ columns: [table.sdsCode], name: "tc_search_disease_sds_code"}),
		sdsCode: unique("sds_code").on(table.sdsCode),
	}
});

export const thClientInvoice = mysqlTable("th_client_invoice", {
	civhId: int("civh_id", { unsigned: true }).autoincrement().primaryKey().notNull(),
	cluId: int("clu_id", { unsigned: true }).notNull().references(() => tnClientUser.cluId, { onDelete: "restrict", onUpdate: "restrict" } ),
	civhInsurers: json("civh_insurers").notNull(),
	civhCreatedAt: datetime("civh_created_at", { mode: 'string'}).default(sql`(CURRENT_TIMESTAMP)`).notNull(),
},
(table) => {
	return {
		thInvoiceMemIdTnMemberMemIdFk: index("th_invoice_mem_id_tn_member_mem_id_fk").on(table.cluId),
		thClientInvoiceCivhId: primaryKey({ columns: [table.civhId], name: "th_client_invoice_civh_id"}),
	}
});

export const thInvoice = mysqlTable("th_invoice", {
	ivhId: int("ivh_id", { unsigned: true }).autoincrement().primaryKey().notNull(),
	memId: int("mem_id", { unsigned: true }).notNull().references(() => tnMember.memId),
	ordId: int("ord_id", { unsigned: true }).notNull(),
	ivhName: varchar("ivh_name", { length: 64 }).notNull(),
	ivhPhone: varchar("ivh_phone", { length: 64 }).notNull(),
	ivhInsurers: json("ivh_insurers").notNull(),
	ivhS3Key: json("ivh_s3_key"), // [{s3Key: string, originalName: string}]
	ivhAttachmentS3Keys: json("ivh_attachment_s3_keys"), // [{s3Key: string, originalName: string}]
	ivhCreatedAt: datetime("ivh_created_at", { mode: 'string'}).default(sql`(CURRENT_TIMESTAMP)`).notNull(),
},
(table) => {
	return {
		thInvoiceIvhId: primaryKey({ columns: [table.ivhId], name: "th_invoice_ivh_id"}),
	}
});

export const tnAdmin = mysqlTable("tn_admin", {
	admId: int("adm_id", { unsigned: true }).autoincrement().primaryKey().notNull(),
	athId: int("ath_id", { unsigned: true }).references(() => tnAuth.athId, { onDelete: "restrict", onUpdate: "cascade" } ),
	admName: varchar("adm_name", { length: 128 }).notNull(),
	admLoginId: varchar("adm_login_id", { length: 20 }).notNull(),
	admPassword: varchar("adm_password", { length: 100 }).notNull(),
	admEmail: varchar("adm_email", { length: 128 }),
	admPhone: varchar("adm_phone", { length: 128 }).notNull(),
	admLastLoginAt: datetime("adm_last_login_at", { mode: 'string'}),
	admUpdatedAt: datetime("adm_updated_at", { mode: 'string'}),
	admCreatedAt: datetime("adm_created_at", { mode: 'string'}).default(sql`(CURRENT_TIMESTAMP)`).notNull(),
},
(table) => {
	return {
		tnAdminAdmId: primaryKey({ columns: [table.admId], name: "tn_admin_adm_id"}),
		admLoginId: unique("adm_login_id").on(table.admLoginId),
	}
});

export const tnAdminAlarm = mysqlTable("tn_admin_alarm", {
	aadId: int("aad_id", { unsigned: true }).autoincrement().primaryKey().notNull(),
	admId: int("adm_id", { unsigned: true }).notNull().references(() => tnAdmin.admId, { onDelete: "cascade", onUpdate: "cascade" } ),
	aadType: varchar("aad_type", { length: 10 }).notNull(),
	aadResultType: varchar("aad_result_type", { length: 10 }).notNull(),
	aadMessage: varchar("aad_message", { length: 255 }).notNull(),
	aadChecked: tinyint("aad_checked").default(0).notNull(),
	aadRedirectPage: varchar("aad_redirect_page", { length: 255 }),
	aadDetail: json("aad_detail").$type<Record<string, unknown>>(),
	aadCreatedAt: datetime("aad_created_at", { mode: 'string'}).default(sql`(CURRENT_TIMESTAMP)`).notNull(),
	aadUpdatedAt: datetime("aad_updated_at", { mode: 'string'}),
},
(table) => {
	return {
		tnAdminAlarmAadId: primaryKey({ columns: [table.aadId], name: "tn_admin_alarm_aad_id"}),
	}
});

export const tnAdvertisement = mysqlTable("tn_advertisement", {
	adsId: int("ads_id", { unsigned: true }).autoincrement().primaryKey().notNull(),
	agcId: int("agc_id"),
	adsName: varchar("ads_name", { length: 50 }).notNull(),
	adsLocation: varchar("ads_location", { length: 10 }).notNull(),
	adsType: varchar("ads_type", { length: 10 }).notNull(),
	adsVideoUrl: varchar("ads_video_url", { length: 255 }),
	adsImg: varchar("ads_img", { length: 255 }),
	adsRandom: tinyint("ads_random").notNull(),
	adsSort: int("ads_sort"),
	adsShow: int("ads_show").notNull(),
	adsOpenedAt: datetime("ads_opened_at", { mode: 'string'}).notNull(),
	adsClosedAt: datetime("ads_closed_at", { mode: 'string'}).notNull(),
	adsLinked: tinyint("ads_linked"),
	adsLink: varchar("ads_link", { length: 100 }),
	adsPlaybackType: varchar("ads_playback_type", { length: 10 }),
	adsPlaybackTime: int("ads_playback_time"),
	adsTotalImpressionCount: int("ads_total_impression_count").default(0),
	adsTotalClickCount: int("ads_total_click_count").default(0),
	adsTotalPlayCount: int("ads_total_play_count").default(0),
	adsUpdatedAt: datetime("ads_updated_at", { mode: 'string'}),
	adsCreatedAt: datetime("ads_created_at", { mode: 'string'}).default(sql`(CURRENT_TIMESTAMP)`).notNull(),
},
(table) => {
	return {
		tnAdvertisementAdsId: primaryKey({ columns: [table.adsId], name: "tn_advertisement_ads_id"}),
	}
});

export const tnAdvertisementStatistics = mysqlTable("tn_advertisement_statistics", {
	adtId: int("adt_id", { unsigned: true }).autoincrement().primaryKey().notNull(),
	adsId: int("ads_id", { unsigned: true }).notNull().references(() => tnAdvertisement.adsId, { onDelete: "cascade", onUpdate: "cascade" } ),
	// you can use { mode: 'date' }, if you want to have Date as type for this column
	adtDate: date("adt_date", { mode: 'string' }).notNull(),
	adtImpressions: int("adt_impressions").default(0),
	adtClicks: int("adt_clicks").default(0),
	adtPlays: int("adt_plays").default(0),
	adtUpdatedAt: datetime("adt_updated_at", { mode: 'string'}),
	adtCreatedAt: datetime("adt_created_at", { mode: 'string'}).default(sql`(CURRENT_TIMESTAMP)`).notNull(),
},
(table) => {
	return {
		tnAdvertisementStatisticsAdtIdAdsId: primaryKey({ columns: [table.adtId, table.adsId], name: "tn_advertisement_statistics_adt_id_ads_id"}),
		uniqueAdsIdAdtDate: unique("unique_ads_id_adt_date").on(table.adsId, table.adtDate),
	}
});

export const tnAgency = mysqlTable("tn_agency", {
	agcId: int("agc_id", { unsigned: true }).autoincrement().primaryKey().notNull(),
	sagId: int("sag_id"),
	sagCode: varchar("sag_code", { length: 20 }),
	sacCode: varchar("sac_code", { length: 20 }),
	agcRegistrationNumber: varchar("agc_registration_number", { length: 12 }).notNull(),
	agcCorporateName: varchar("agc_corporate_name", { length: 30 }).notNull(),
	agcCorporateCode: varchar("agc_corporate_code", { length: 20 }).notNull(),
	agcRepresentativeName: varchar("agc_representative_name", { length: 20 }),
	agcMoney: int("agc_money", { unsigned: true }).default(0).notNull(),
	agcDeliquent: tinyint("agc_deliquent").default(0).notNull(),
	// 분석관리 화면 노출여부 (0: 미노출 | 1: 분석목록만 | 2: 분석목록+상세팝업)
	agcAnalysisView: tinyint("agc_analysis_view").default(0).notNull(),
	agcLoginId: varchar("agc_login_id", { length: 50 }),
	agcPassword: varchar("agc_password", { length: 255 }),
	agcCreatedAt: datetime("agc_created_at", { mode: 'string'}).default(sql`(CURRENT_TIMESTAMP)`).notNull(),
	agcUpdatedAt: datetime("agc_updated_at", { mode: 'string'}),
},
(table) => {
	return {
		tnAgencyAgcId: primaryKey({ columns: [table.agcId], name: "tn_agency_agc_id"}),
		agcCorporateCode: unique("agc_corporate_code").on(table.agcCorporateCode),
		agcLoginId: unique("agc_login_id").on(table.agcLoginId),
		agcRegistrationNumber: unique("agc_registration_number").on(table.agcRegistrationNumber),
	}
});

//* 기업조직(task-688): 기업↔기업상품 1:N 관계 도입을 위한 조직 단위 식별자.
//*   orgName은 agcId 내 UNIQUE, orgCode는 NULL 허용·NOT NULL일 때만 agcId 내 UNIQUE.
export const tnAgencyOrganization = mysqlTable("tn_agency_organization", {
	orgId: varchar("org_id", { length: 26 }).notNull(),
	agcId: int("agc_id", { unsigned: true }).notNull().references(() => tnAgency.agcId, { onDelete: "restrict", onUpdate: "cascade" } ),
	orgName: varchar("org_name", { length: 100 }).notNull(),
	orgCode: varchar("org_code", { length: 50 }),
	//* 조직트리(corp 권한위임): materialized path. 루트=parent NULL, path '/{orgId}/'. FK는 DDL(0014)에서 self-ref.
	orgParentId: varchar("org_parent_id", { length: 26 }),
	orgDepth: int("org_depth").default(0).notNull(),
	orgPath: varchar("org_path", { length: 1024 }),
	orgDescription: varchar("org_description", { length: 500 }),
	orgUseYn: varchar("org_use_yn", { length: 1 }).default('Y').notNull(),
	orgCreatedAt: datetime("org_created_at", { mode: 'string'}).default(sql`(CURRENT_TIMESTAMP)`).notNull(),
	orgUpdatedAt: datetime("org_updated_at", { mode: 'string'}),
},
(table) => {
	return {
		tnAgencyOrganizationOrgId: primaryKey({ columns: [table.orgId], name: "tn_agency_organization_org_id"}),
		agcId: index("agc_id").on(table.agcId),
		orgPathIdx: index("idx_org_path").on(table.orgPath),
		orgParentIdx: index("idx_org_parent").on(table.orgParentId),
		orgNamePerAgency: unique("org_name_per_agency").on(table.agcId, table.orgName),
		orgCodePerAgency: unique("org_code_per_agency").on(table.agcId, table.orgCode),
	}
});

export const tnAgencyContract = mysqlTable("tn_agency_contract", {
	actId: int("act_id", { unsigned: true }).autoincrement().primaryKey().notNull(),
	agcId: int("agc_id", { unsigned: true }).notNull().references(() => tnAgency.agcId, { onDelete: "restrict", onUpdate: "cascade" } ),
	//* 기업조직(task-688): 마이그레이션 후 NOT NULL ALTER 예정. 신규 등록은 항상 지정.
	orgId: varchar("org_id", { length: 26 }).references(() => tnAgencyOrganization.orgId, { onDelete: "restrict", onUpdate: "cascade" } ),
	prdId: int("prd_id", { unsigned: true }).notNull().references(() => tnProduct.prdId, { onDelete: "restrict", onUpdate: "cascade" } ),
	actInitialMidPrdId: int("act_initial_mid_prd_id", { unsigned: true }).references(() => tnProduct.prdId, { onDelete: "restrict", onUpdate: "cascade" } ),
	actInitialLatePrdId: int("act_initial_late_prd_id", { unsigned: true }).references(() => tnProduct.prdId, { onDelete: "restrict", onUpdate: "cascade" } ),
	actInitialMidStartedDay: tinyint("act_initial_mid_started_day", { unsigned: true }).default(11).notNull(),
	actInitialMidEndedDay: tinyint("act_initial_mid_ended_day", { unsigned: true }).default(20).notNull(),
	actInitialLateStartedDay: tinyint("act_initial_late_started_day", { unsigned: true }).default(21).notNull(),
	actInitialLateEndedDay: tinyint("act_initial_late_ended_day", { unsigned: true }).default(31).notNull(),
	actCode: varchar("act_code", { length: 20 }).notNull(),
	//* 계약 상태(task-688): ACTIVE/EXPIRED/TERMINATED. 마이그레이션으로 기본 'ACTIVE'.
	actStatus: varchar("act_status", { length: 15 }).default('ACTIVE').notNull(),
	//* 정산 수수료율(task-688): 0~100, NULL 허용. 소수점 2자리.
	actFeeRate: decimal("act_fee_rate", { precision: 5, scale: 2 }),
	//* 계약 메모(task-688)
	actMemo: text("act_memo"),
	//* 과금방식(후불정산 변경안): PREPAID/POSTPAID/FREE. PREPAID는 추후 지원.
	actBillingType: varchar("act_billing_type", { length: 16 }).default('POSTPAID').notNull(),
	//* 계약 구독계정수 하한(후불정산 변경안). NULL이면 하한 판정 skip.
	actSubscriptionSeat: int("act_subscription_seat"),
	//* 회계팀 이메일(후불정산 변경안). FREE 계약은 선택.
	actAccountingEmail: varchar("act_accounting_email", { length: 255 }),
	actSubscriptionCycle: int("act_subscription_cycle").notNull(),
	actContractStartedAt: datetime("act_contract_started_at", { mode: 'string'}).notNull(),
	actContractEndedAt: datetime("act_contract_ended_at", { mode: 'string'}).notNull(),
	actCreatedAt: datetime("act_created_at", { mode: 'string'}).default(sql`(CURRENT_TIMESTAMP)`).notNull(),
	actUpdatedAt: datetime("act_updated_at", { mode: 'string'}),
},
(table) => {
	return {
		tnAgencyContractActId: primaryKey({ columns: [table.actId], name: "tn_agency_contract_act_id"}),
		orgId: index("org_id").on(table.orgId),
		actInitialMidPrdId: index("act_initial_mid_prd_id").on(table.actInitialMidPrdId),
		actInitialLatePrdId: index("act_initial_late_prd_id").on(table.actInitialLatePrdId),
	}
});

export const tnAgencyContractInitialPlan = mysqlTable("tn_agency_contract_initial_plan", {
	aipId: int("aip_id", { unsigned: true }).autoincrement().primaryKey().notNull(),
	actId: int("act_id", { unsigned: true }).notNull().references(() => tnAgencyContract.actId, { onDelete: "cascade", onUpdate: "cascade" } ),
	prdId: int("prd_id", { unsigned: true }).references(() => tnProduct.prdId, { onDelete: "restrict", onUpdate: "cascade" } ),
	aipStartedDay: tinyint("aip_started_day", { unsigned: true }).notNull(),
	aipEndedDay: tinyint("aip_ended_day", { unsigned: true }),
	aipCreatedAt: datetime("aip_created_at", { mode: 'string'}).default(sql`(CURRENT_TIMESTAMP)`).notNull(),
	aipUpdatedAt: datetime("aip_updated_at", { mode: 'string'}),
},
(table) => {
	return {
		tnAgencyContractInitialPlanAipId: primaryKey({ columns: [table.aipId], name: "tn_agency_contract_initial_plan_aip_id"}),
		actId: index("act_id").on(table.actId),
		prdId: index("prd_id").on(table.prdId),
	}
});

//* 기업 정책 버전(agency-billing-policy M1). 기업 단위로 적용 시작일(날짜)부터 유효하다 — 적용이 시작된 버전은 서버가 고치지 않는다.
export const tnAgencyPolicy = mysqlTable("tn_agency_policy", {
	aplId: int("apl_id", { unsigned: true }).autoincrement().primaryKey().notNull(),
	agcId: int("agc_id", { unsigned: true }).notNull().references(() => tnAgency.agcId, { onDelete: "restrict", onUpdate: "cascade" } ),
	aplVersion: int("apl_version", { unsigned: true }).notNull(),
	aplStartedAt: date("apl_started_at", { mode: 'string' }).notNull(),
	//* CONTRACT_PRODUCT(가입일과 무관하게 계약 상품) / DAY_RANGE(가입일 구간별 상품)
	aplProration: varchar("apl_proration", { length: 20 }).notNull(),
	//* ORDER(주문 기준) / ACTIVE_MEMBER(사용 FC 기준 — 청구 명세 대상)
	aplBillingBasis: varchar("apl_billing_basis", { length: 20 }).notNull(),
	aplMemo: varchar("apl_memo", { length: 255 }),
	admId: int("adm_id", { unsigned: true }),
	aplCreatedAt: datetime("apl_created_at", { mode: 'string'}).default(sql`(CURRENT_TIMESTAMP)`).notNull(),
	aplUpdatedAt: datetime("apl_updated_at", { mode: 'string'}),
},
(table) => {
	return {
		tnAgencyPolicyAplId: primaryKey({ columns: [table.aplId], name: "tn_agency_policy_apl_id"}),
		agcVersion: unique("agc_version").on(table.agcId, table.aplVersion),
		agcStartedAt: unique("agc_started_at").on(table.agcId, table.aplStartedAt),
	}
});

export const tnAgencyPolicyRange = mysqlTable("tn_agency_policy_range", {
	aprId: int("apr_id", { unsigned: true }).autoincrement().primaryKey().notNull(),
	aplId: int("apl_id", { unsigned: true }).notNull().references(() => tnAgencyPolicy.aplId, { onDelete: "cascade", onUpdate: "cascade" } ),
	//* null 이면 그 구간 신규구독 차단
	prdId: int("prd_id", { unsigned: true }).references(() => tnProduct.prdId, { onDelete: "restrict", onUpdate: "cascade" } ),
	aprStartedDay: tinyint("apr_started_day", { unsigned: true }).notNull(),
	aprEndedDay: tinyint("apr_ended_day", { unsigned: true }),
	aprCreatedAt: datetime("apr_created_at", { mode: 'string'}).default(sql`(CURRENT_TIMESTAMP)`).notNull(),
	aprUpdatedAt: datetime("apr_updated_at", { mode: 'string'}),
},
(table) => {
	return {
		tnAgencyPolicyRangeAprId: primaryKey({ columns: [table.aprId], name: "tn_agency_policy_range_apr_id"}),
		aplId: index("apl_id").on(table.aplId),
		prdId: index("prd_id").on(table.prdId),
	}
});

export const tnAgencySettlement = mysqlTable("tn_agency_settlement", {
	astId: int("ast_id", { unsigned: true }).autoincrement().primaryKey().notNull(),
	agcId: int("agc_id", { unsigned: true }).notNull().references(() => tnAgency.agcId, { onDelete: "cascade", onUpdate: "cascade" } ),
	astCode: varchar("ast_code", { length: 20 }).notNull(),
	// you can use { mode: 'date' }, if you want to have Date as type for this column
	astDate: date("ast_date", { mode: 'string' }).notNull(),
	astOrderCount: int("ast_order_count").notNull(),
	astOrderTotalLimitedQty: int("ast_order_total_limited_qty").notNull(),
	astOrderTotalUsedQty: int("ast_order_total_used_qty").notNull(),
	astSettlementPrice: int("ast_settlement_price").notNull(),
	//* 회차를 담은 기준: ORDER(주문)/ACTIVE_MEMBER(사용 FC — 명세 규칙). 0034_settlement_active_member.sql
	astBillingBasis: varchar("ast_billing_basis", { length: 16 }).default('ORDER').notNull(),
	astPaid: tinyint("ast_paid").default(0).notNull(),
	astPaidAt: datetime("ast_paid_at", { mode: 'string'}),
	//* 정산상태(후불정산 변경안): PENDING(미정산)/CONFIRMED(정산확정)
	astSettleStatus: varchar("ast_settle_status", { length: 16 }).default('PENDING').notNull(),
	astConfirmedAt: datetime("ast_confirmed_at", { mode: 'string'}),
	//* 확정 처리 관리자 id(후불정산 변경안)
	astConfirmedBy: int("ast_confirmed_by", { unsigned: true }),
	//* 정산확정금액 스냅샷(후불정산 변경안): 확정 시 INCLUDE 합
	astConfirmedPrice: int("ast_confirmed_price"),
	//* 세금계산서 발행여부·발행일(후불정산 변경안, 수기 기록)
	astTaxInvoice: tinyint("ast_tax_invoice").default(0).notNull(),
	astTaxInvoiceAt: datetime("ast_tax_invoice_at", { mode: 'string'}),
	astCreatedAt: datetime("ast_created_at", { mode: 'string'}).default(sql`(CURRENT_TIMESTAMP)`).notNull(),
	astUpdatedAt: datetime("ast_updated_at", { mode: 'string'}),
},
(table) => {
	return {
		tnAgencySettlementAstId: primaryKey({ columns: [table.astId], name: "tn_agency_settlement_ast_id"}),
		//* 회차 유일 제약(M2) — (agc_id, ast_date) 정확히 두 열. ast_code 를 끼운 더 넓은 유일키가
		//*  아니다: ast_code 는 agc_corporate_code + YYYYMM 파생이라 기업 코드가 바뀌면 같은 회차가
		//*  다른 코드로 두 번 선다. 이름이 계약이다 — create() 가 이 이름이 든 1062 만 건너뛴다.
		uqAgencySettlementAgcDate: unique("uq_agency_settlement_agc_date").on(table.agcId, table.astDate),
	}
});

export const tnAgencySettlementOrderMap = mysqlTable("tn_agency_settlement_order_map", {
	astId: int("ast_id", { unsigned: true }).notNull().references(() => tnAgencySettlement.astId, { onDelete: "cascade", onUpdate: "cascade" } ),
	ordId: int("ord_id", { unsigned: true }).notNull().references(() => tnOrder.ordId, { onDelete: "cascade", onUpdate: "cascade" } ),
	//* 정산반영(후불정산 변경안): INCLUDE(반영)/EXCLUDE(미반영)/CARRYOVER(이월)
	somSettleAction: varchar("som_settle_action", { length: 16 }).default('INCLUDE').notNull(),
	//* 이월 편입 시 원 정산 id(후불정산 변경안, 중복 청구 추적)
	somCarryoverFromAstId: int("som_carryover_from_ast_id", { unsigned: true }),
	//* 담긴 까닭(사용 FC 기준 회차): INCLUDE 면 리포트 제외 사유(리포트에 들면 NULL), EXCLUDE 면 미사용·중복 주문
	somReason: varchar("som_reason", { length: 32 }),
	//* 이 회차에서 반영할 때의 단가(사용 FC 기준 회차 = 계약가). NULL 이면 ord_settlement_price
	somSettlementPrice: int("som_settlement_price"),
	somCreatedAt: datetime("som_created_at", { mode: 'string'}).default(sql`(CURRENT_TIMESTAMP)`).notNull(),
},
(table) => {
	return {
		ordId: index("ord_id").on(table.ordId),
		tnAgencySettlementOrderMapAstIdOrdId: primaryKey({ columns: [table.astId, table.ordId], name: "tn_agency_settlement_order_map_ast_id_ord_id"}),
	}
});

//* 후불정산 변경안: 정산 메일 발송 이력
export const tnAgencySettlementMailLog = mysqlTable("tn_agency_settlement_mail_log", {
	smlId: int("sml_id", { unsigned: true }).autoincrement().primaryKey().notNull(),
	astId: int("ast_id", { unsigned: true }).notNull().references(() => tnAgencySettlement.astId, { onDelete: "cascade", onUpdate: "cascade" } ),
	//* 수신자(콤마구분)
	smlTo: varchar("sml_to", { length: 500 }).notNull(),
	smlSubject: varchar("sml_subject", { length: 255 }).notNull(),
	smlSentAt: datetime("sml_sent_at", { mode: 'string'}).default(sql`(CURRENT_TIMESTAMP)`).notNull(),
	//* 발송 관리자 id
	smlSentBy: int("sml_sent_by", { unsigned: true }),
},
(table) => {
	return {
		tnAgencySettlementMailLogSmlId: primaryKey({ columns: [table.smlId], name: "tn_agency_settlement_mail_log_sml_id"}),
		astId: index("ast_id").on(table.astId),
	}
});

//* 리포트 발송 이력(M2) — 정산 회차 행과 FK 로 묶이지 않는다. 리포트는 정산 행이 생기기 전에
//*  날마다 나가므로 걸 ast_id 가 없다(tnAgencySettlementMailLog 는 ast_id 가 NOT NULL 이다).
//*  preview·final 두 모드 모두 실제로 발송하므로 둘 다 남긴다.
export const tnAgencyReportSendLog = mysqlTable("tn_agency_report_send_log", {
	rslId: int("rsl_id", { unsigned: true }).autoincrement().primaryKey().notNull(),
	agcId: int("agc_id", { unsigned: true }).notNull().references(() => tnAgency.agcId, { onDelete: "restrict", onUpdate: "cascade" } ),
	//* 'preview' | 'final' | 'statement'(preview 에 붙는 청구 명세 — 리포트와 다른 S3 객체라 행을 따로 둔다)
	//*  | 'usage'(콘솔 거래명세서 메일 — S3 객체 없음, rsl_s3_key 에 `usage:{PDF 파일 이름}`, rsl_sent_by 에 보낸 관리자)
	rslMode: varchar("rsl_mode", { length: 10 }).notNull(),
	//* 귀속 월(월초 정규화). 발송일의 달이 아니라 보고 기간 끝의 달이다 — 1일 발송은 전월이 귀속이다.
	rslPeriodMonth: date("rsl_period_month", { mode: 'string' }).notNull(),
	rslS3Key: varchar("rsl_s3_key", { length: 500 }).notNull(),
	//* 수신자(콤마구분)
	rslTo: varchar("rsl_to", { length: 500 }).notNull(),
	//* 보낸 관리자 id — 콘솔 메일(usage)만. 예약 리포트는 NULL. 0035_report_send_log_sent_by.sql
	rslSentBy: int("rsl_sent_by", { unsigned: true }),
	//* NULL 이면 «행은 썼는데 발송 확인을 못 받았다». 행은 발송 전에 쓰고 발송 뒤에 스탬프한다.
	rslSentAt: datetime("rsl_sent_at", { mode: 'string'}),
	rslCreatedAt: datetime("rsl_created_at", { mode: 'string'}).default(sql`(CURRENT_TIMESTAMP)`).notNull(),
},
(table) => {
	return {
		tnAgencyReportSendLogRslId: primaryKey({ columns: [table.rslId], name: "tn_agency_report_send_log_rsl_id"}),
		agcIdPeriod: index("agc_id_period").on(table.agcId, table.rslPeriodMonth),
	}
});

export const tnAlarm = mysqlTable("tn_alarm", {
	almId: int("alm_id", { unsigned: true }).autoincrement().primaryKey().notNull(),
	memId: int("mem_id", { unsigned: true }).notNull().references(() => tnMember.memId, { onDelete: "cascade", onUpdate: "cascade" } ),
	almUserName: varchar("alm_user_name", { length: 128 }),
	almType: varchar("alm_type", { length: 10 }).notNull(),
	almTitle: varchar("alm_title", { length: 100 }),
	almContent: text("alm_content"),
	almMessage: varchar("alm_message", { length: 100 }),
	almChecked: tinyint("alm_checked").default(0).notNull(),
	almRedirectId: int("alm_redirect_id"),
	almCreatedAt: datetime("alm_created_at", { mode: 'string'}).default(sql`(CURRENT_TIMESTAMP)`).notNull(),
	almUpdatedAt: datetime("alm_updated_at", { mode: 'string'}),
},
(table) => {
	return {
		memId: index("mem_id").on(table.memId),
		tnAlarmAlmId: primaryKey({ columns: [table.almId], name: "tn_alarm_alm_id"}),
	}
});

export const tnAlimtalk = mysqlTable("tn_alimtalk", {
	altId: int("alt_id", { unsigned: true }).autoincrement().primaryKey().notNull(),
	ordId: int("ord_id"),
	altType: varchar("alt_type", { length: 10 }).notNull(),
	altTemplateCode: varchar("alt_template_code", { length: 10 }),
	altRequestState: varchar("alt_request_state", { length: 10 }).notNull(),
	altCompletionState: varchar("alt_completion_state", { length: 10 }),
	altSmsCompletionState: varchar("alt_sms_completion_state", { length: 10 }),
	altCode: varchar("alt_code", { length: 30 }),
	altName: varchar("alt_name", { length: 128 }).notNull(),
	altPhone: varchar("alt_phone", { length: 128 }).notNull(),
	altMid: int("alt_mid"),
	altSmid: int("alt_smid"),
	altUsed: tinyint("alt_used").default(0).notNull(),
	altRequestMessage: varchar("alt_request_message", { length: 100 }),
	altCompletionMessage: varchar("alt_completion_message", { length: 100 }),
	altSmsCompletionMessage: varchar("alt_sms_completion_message", { length: 100 }),
	altCurrent: float("alt_current"),
	altScnt: int("alt_scnt"),
	altFcnt: int("alt_fcnt"),
	altSendCompletedAt: datetime("alt_send_completed_at", { mode: 'string'}),
	altUpdatedAt: datetime("alt_updated_at", { mode: 'string'}),
	altCreatedAt: datetime("alt_created_at", { mode: 'string'}).default(sql`(CURRENT_TIMESTAMP)`).notNull(),
},
(table) => {
	return {
		altRequestState: index("alt_request_state").on(table.altRequestState),
		tnAlimtalkAltId: primaryKey({ columns: [table.altId], name: "tn_alimtalk_alt_id"}),
		altCode: unique("alt_code").on(table.altCode),
	}
});

export const tnAllowIp = mysqlTable("tn_allow_ip", {
	alpId: int("alp_id", { unsigned: true }).autoincrement().primaryKey().notNull(),
	alpName: varchar("alp_name", { length: 10 }),
	alpIp: varchar("alp_ip", { length: 20 }).notNull(),
	alpUsePlace: varchar("alp_use_place", { length: 20 }),
	alpUpdatedAt: datetime("alp_updated_at", { mode: 'string'}),
	alpCreatedAt: datetime("alp_created_at", { mode: 'string'}).default(sql`(CURRENT_TIMESTAMP)`).notNull(),
},
(table) => {
	return {
		tnAllowIpAlpId: primaryKey({ columns: [table.alpId], name: "tn_allow_ip_alp_id"}),
		alpIp: unique("alp_ip").on(table.alpIp),
	}
});

export const tnAnalysisBasic = mysqlTable("tn_analysis_basic", {
	asbId: int("asb_id", { unsigned: true }).autoincrement().primaryKey().notNull(),
	oddId: int("odd_id", { unsigned: true }).notNull().references(() => tnOrderDetail.oddId, { onDelete: "restrict", onUpdate: "restrict" } ),
	// you can use { mode: 'date' }, if you want to have Date as type for this column
	asbTreatStartDate: date("asb_treat_start_date", { mode: 'string' }).notNull(),
	asbHospitalName: varchar("asb_hospital_name", { length: 50 }).notNull(),
	asbDepartment: varchar("asb_department", { length: 20 }),
	asbTreatType: varchar("asb_treat_type", { length: 15 }).notNull(),
	asbDiseaseCode: varchar("asb_disease_code", { length: 10 }),
	asbDiseaseName: varchar("asb_disease_name", { length: 255 }),
	asbVisitDays: int("asb_visit_days").default(0).notNull(),
	asbDisease: varchar("asb_disease", { length: 255 }),
	asbInDisease: text("asb_in_disease"),
	asbNotice: text("asb_notice"),
	asbDentures: varchar("asb_dentures", { length: 255 }),
	asbToothOne: varchar("asb_tooth_one", { length: 255 }),
	asbToothFive: varchar("asb_tooth_five", { length: 255 }),
	asbEtc: varchar("asb_etc", { length: 255 }),
	asbDrugNotice: varchar("asb_drug_notice", { length: 255 }),
	asbDosingDays: int("asb_dosing_days").default(0).notNull(),
	asbInTooth: tinyint("asb_in_tooth").default(0).notNull(),
	asbDuplicated: tinyint("asb_duplicated").default(0).notNull(),
	asbSicked: tinyint("asb_sicked").default(0).notNull(),
	asbDosingId: int("asb_dosing_id").default(0).notNull(),
	asbUpdatedAt: datetime("asb_updated_at", { mode: 'string'}),
	asbCreatedAt: datetime("asb_created_at", { mode: 'string'}).default(sql`(CURRENT_TIMESTAMP)`).notNull(),
},
(table) => {
	return {
		asbId: index("asb_id").on(table.asbId),
		tnAnalysisBasicAsbIdOddId: primaryKey({ columns: [table.asbId, table.oddId], name: "tn_analysis_basic_asb_id_odd_id"}),
	}
});

export const tnAnalysisCarBasic = mysqlTable("tn_analysis_car_basic", {
	acbId: int("acb_id", { unsigned: true }).autoincrement().primaryKey().notNull(),
	oddId: int("odd_id", { unsigned: true }).notNull().references(() => tnOrderDetail.oddId, { onDelete: "restrict", onUpdate: "restrict" } ),
	// you can use { mode: 'date' }, if you want to have Date as type for this column
	acbTreatStartDate: date("acb_treat_start_date", { mode: 'string' }).notNull(),
	// you can use { mode: 'date' }, if you want to have Date as type for this column
	acbTreatEndDate: date("acb_treat_end_date", { mode: 'string' }).notNull(),
	acbTotalTreatDate: int("acb_total_treat_date").notNull(),
	acbTotalAmount: int("acb_total_amount").notNull(),
	acbTotalMedicalFee: int("acb_total_medical_fee"),
	acbOutpatientTotalAmount: int("acb_outpatient_total_amount").notNull(),
	acbInpatientTotalAmount: int("acb_inpatient_total_amount").notNull(),
	acbOutpatientMedicalFee: int("acb_outpatient_medical_fee").notNull(),
	acbInpatientMedicalFee: int("acb_inpatient_medical_fee").notNull(),
	acbOutpatientTreatDate: int("acb_outpatient_treat_date").notNull(),
	acbInpatientTreatDate: int("acb_inpatient_treat_date").notNull(),
	acbUpdatedAt: datetime("acb_updated_at", { mode: 'string'}),
	acbCreatedAt: datetime("acb_created_at", { mode: 'string'}).default(sql`(CURRENT_TIMESTAMP)`).notNull(),
},
(table) => {
	return {
		acbId: index("acb_id").on(table.acbId),
		tnAnalysisCarBasicAcbIdOddId: primaryKey({ columns: [table.acbId, table.oddId], name: "tn_analysis_car_basic_acb_id_odd_id"}),
	}
});

export const tnAnalysisCarDetail = mysqlTable("tn_analysis_car_detail", {
	acdId: int("acd_id", { unsigned: true }).autoincrement().primaryKey().notNull(),
	acbId: int("acb_id", { unsigned: true }).notNull().references(() => tnAnalysisCarBasic.acbId, { onDelete: "restrict", onUpdate: "cascade" } ),
	oddId: int("odd_id", { unsigned: true }).notNull().references(() => tnOrderDetail.oddId, { onDelete: "restrict", onUpdate: "cascade" } ),
	// you can use { mode: 'date' }, if you want to have Date as type for this column
	acdTreatStartDate: date("acd_treat_start_date", { mode: 'string' }).notNull(),
	acdHospitalName: varchar("acd_hospital_name", { length: 50 }).notNull(),
	acdDepartment: varchar("acd_department", { length: 20 }),
	acdTreatType: varchar("acd_treat_type", { length: 15 }).notNull(),
	acdDiseaseCode: varchar("acd_disease_code", { length: 10 }),
	acdDiseaseName: varchar("acd_disease_name", { length: 255 }),
	acdTreatDate: int("acd_treat_date").notNull(),
	acdTotalAmount: int("acd_total_amount").notNull(),
	acdMedicalFee: int("acd_medical_fee").notNull(),
	acdUpdatedAt: datetime("acd_updated_at", { mode: 'string'}),
	acdCreatedAt: datetime("acd_created_at", { mode: 'string'}).default(sql`(CURRENT_TIMESTAMP)`).notNull(),
},
(table) => {
	return {
		acdId: index("acd_id").on(table.acdId),
		tnAnalysisCarDetailAcdIdAcbIdOddId: primaryKey({ columns: [table.acdId, table.acbId, table.oddId], name: "tn_analysis_car_detail_acd_id_acb_id_odd_id"}),
	}
});

export const tnAnalysisDetail = mysqlTable("tn_analysis_detail", {
	asdId: int("asd_id", { unsigned: true }).autoincrement().primaryKey().notNull(),
	asbId: int("asb_id", { unsigned: true }).notNull().references(() => tnAnalysisBasic.asbId, { onDelete: "restrict", onUpdate: "cascade" } ),
	oddId: int("odd_id", { unsigned: true }).notNull().references(() => tnOrderDetail.oddId, { onDelete: "restrict", onUpdate: "cascade" } ),
	// you can use { mode: 'date' }, if you want to have Date as type for this column
	asdTreatStartDate: date("asd_treat_start_date", { mode: 'string' }).notNull(),
	asdHospitalName: varchar("asd_hospital_name", { length: 50 }).notNull(),
	asdCodeName: varchar("asd_code_name", { length: 255 }),
	asdOperation: varchar("asd_operation", { length: 255 }),
	asdDrug: varchar("asd_drug", { length: 255 }),
	asdDrugNotice: varchar("asd_drug_notice", { length: 255 }),
	asdExamination: varchar("asd_examination", { length: 255 }),
	asdVisitDays: int("asd_visit_days").default(0).notNull(),
	asdDosingDays: int("asd_dosing_days").default(0).notNull(),
	asdDosingId: int("asd_dosing_id").default(0).notNull(),
	asdInTooth: text("asd_in_tooth"),
	asdInOperation: text("asd_in_operation"),
	asdInEtc: text("asd_in_etc"),
	asdDentures: varchar("asd_dentures", { length: 255 }),
	asdToothOne: varchar("asd_tooth_one", { length: 255 }),
	asdToothFive: varchar("asd_tooth_five", { length: 255 }),
	asdUpdaedAt: datetime("asd_updaed_at", { mode: 'string'}),
	asdCreatedAt: datetime("asd_created_at", { mode: 'string'}).default(sql`(CURRENT_TIMESTAMP)`).notNull(),
},
(table) => {
	return {
		asbId: index("asb_id").on(table.asbId),
		v1Ibfk2: index("tn_analysis_detail_v1_ibfk_2").on(table.oddId),
		tnAnalysisDetailAsdIdAsbIdOddId: primaryKey({ columns: [table.asdId, table.asbId, table.oddId], name: "tn_analysis_detail_asd_id_asb_id_odd_id"}),
	}
});

export const tnAnalysisPrescibe = mysqlTable("tn_analysis_prescibe", {
	aspId: int("asp_id", { unsigned: true }).autoincrement().primaryKey().notNull(),
	asbId: int("asb_id", { unsigned: true }).notNull(),
	oddId: int("odd_id", { unsigned: true }).notNull(),
	// you can use { mode: 'date' }, if you want to have Date as type for this column
	aspTreatStartDate: date("asp_treat_start_date", { mode: 'string' }).notNull(),
	aspHospitalName: varchar("asp_hospital_name", { length: 50 }).notNull(),
	aspTreatType: varchar("asp_treat_type", { length: 10 }).notNull(),
	aspDrugName: varchar("asp_drug_name", { length: 255 }),
	aspIngredients: varchar("asp_ingredients", { length: 255 }),
	aspOneDose: int("asp_one_dose").default(0).notNull(),
	aspDailyDosesNumber: int("asp_daily_doses_number").default(0).notNull(),
	aspTotalDosingDays: int("asp_total_dosing_days").default(0).notNull(),
	aspUpdaedAt: datetime("asp_updaed_at", { mode: 'string'}),
	aspCreatedAt: datetime("asp_created_at", { mode: 'string'}).default(sql`(CURRENT_TIMESTAMP)`).notNull(),
},
(table) => {
	return {
		idxAspOddDate: index("idx_asp_odd_date").on(table.oddId, table.aspTreatStartDate),
		tnAnalysisPrescibeAspId: primaryKey({ columns: [table.aspId], name: "tn_analysis_prescibe_asp_id"}),
	}
});

export const tnAuth = mysqlTable("tn_auth", {
	athId: int("ath_id", { unsigned: true }).autoincrement().primaryKey().notNull(),
	athName: varchar("ath_name", { length: 20 }).notNull(),
	athUpdatedAt: datetime("ath_updated_at", { mode: 'string'}),
	athCreatedAt: datetime("ath_created_at", { mode: 'string'}).default(sql`(CURRENT_TIMESTAMP)`),
},
(table) => {
	return {
		athId: index("ath_id").on(table.athId),
		tnAuthAthId: primaryKey({ columns: [table.athId], name: "tn_auth_ath_id"}),
	}
});

export const tnBanner = mysqlTable("tn_banner", {
	bnnId: int("bnn_id", { unsigned: true }).autoincrement().primaryKey().notNull(),
	bnnName: varchar("bnn_name", { length: 20 }).notNull(),
	bnnTitle: varchar("bnn_title", { length: 20 }),
	bnnSort: int("bnn_sort").default(0).notNull(),
	bnnShow: tinyint("bnn_show").default(1).notNull(),
	bnnLocationType: varchar("bnn_location_type", { length: 10 }).notNull(),
	bnnLinked: tinyint("bnn_linked").default(0).notNull(),
	bnnLink: varchar("bnn_link", { length: 100 }),
	bnnImg: varchar("bnn_img", { length: 255 }).notNull(),
	bnnOpenedAt: datetime("bnn_opened_at", { mode: 'string'}),
	bnnClosedAt: datetime("bnn_closed_at", { mode: 'string'}),
	bnnUpdatedAt: datetime("bnn_updated_at", { mode: 'string'}),
	bnnCreatedAt: datetime("bnn_created_at", { mode: 'string'}).default(sql`(CURRENT_TIMESTAMP)`).notNull(),
},
(table) => {
	return {
		tnBannerBnnId: primaryKey({ columns: [table.bnnId], name: "tn_banner_bnn_id"}),
	}
});

export const tnBoard = mysqlTable("tn_board", {
	brdId: int("brd_id", { unsigned: true }).autoincrement().primaryKey().notNull(),
	memId: int("mem_id", { unsigned: true }).references(() => tnMember.memId, { onDelete: "cascade", onUpdate: "cascade" } ),
	brdType: varchar("brd_type", { length: 15 }).notNull(),
	brdAccessType: varchar("brd_access_type", { length: 15 }).default('ACT001').notNull(),
	brdTitle: varchar("brd_title", { length: 255 }).notNull(),
	brdContent: text("brd_content").notNull(),
	brdPhone: varchar("brd_phone", { length: 128 }),
	brdSort: int("brd_sort").default(0).notNull(),
	brdFix: tinyint("brd_fix").default(0).notNull(),
	brdShow: tinyint("brd_show").default(1).notNull(),
	brdAnswered: tinyint("brd_answered").default(0).notNull(),
	brdUpdatedAt: datetime("brd_updated_at", { mode: 'string'}),
	brdCreatedAt: datetime("brd_created_at", { mode: 'string'}).default(sql`(CURRENT_TIMESTAMP)`).notNull(),
},
(table) => {
	return {
		memId: index("mem_id").on(table.memId),
		tnBoardBrdId: primaryKey({ columns: [table.brdId], name: "tn_board_brd_id"}),
	}
});

export const tnBoardCategory = mysqlTable("tn_board_category", {
	bcaId: int("bca_id", { unsigned: true }).autoincrement().primaryKey().notNull(),
	bcaName: varchar("bca_name", { length: 20 }).notNull(),
	bcaSort: int("bca_sort").default(0).notNull(),
	bcaShow: tinyint("bca_show").default(1).notNull(),
	bcaUpdatedAt: datetime("bca_updated_at", { mode: 'string'}),
	bcaCreatedAt: datetime("bca_created_at", { mode: 'string'}).default(sql`(CURRENT_TIMESTAMP)`).notNull(),
},
(table) => {
	return {
		tnBoardCategoryBcaId: primaryKey({ columns: [table.bcaId], name: "tn_board_category_bca_id"}),
	}
});

export const tnBoardCategoryMap = mysqlTable("tn_board_category_map", {
	brdId: int("brd_id", { unsigned: true }).notNull().references(() => tnBoard.brdId, { onDelete: "cascade", onUpdate: "cascade" } ),
	bcaId: int("bca_id", { unsigned: true }).notNull().references(() => tnBoardCategory.bcaId, { onDelete: "cascade", onUpdate: "cascade" } ),
	brcmUpdatedAt: datetime("brcm_updated_at", { mode: 'string'}),
	brcmCreatedAt: datetime("brcm_created_at", { mode: 'string'}).default(sql`(CURRENT_TIMESTAMP)`).notNull(),
},
(table) => {
	return {
		bcaId: index("bca_id").on(table.bcaId),
		tnBoardCategoryMapBrdIdBcaId: primaryKey({ columns: [table.brdId, table.bcaId], name: "tn_board_category_map_brd_id_bca_id"}),
	}
});

export const tnBoardComment = mysqlTable("tn_board_comment", {
	brcId: int("brc_id", { unsigned: true }).autoincrement().primaryKey().notNull(),
	brdId: int("brd_id", { unsigned: true }).notNull().references(() => tnBoard.brdId, { onDelete: "cascade", onUpdate: "cascade" } ),
	admId: int("adm_id", { unsigned: true }).references(() => tnAdmin.admId, { onDelete: "cascade", onUpdate: "cascade" } ),
	brcContent: text("brc_content").notNull(),
	brcUpdatedAt: datetime("brc_updated_at", { mode: 'string'}),
	brcCreatedAt: datetime("brc_created_at", { mode: 'string'}).default(sql`(CURRENT_TIMESTAMP)`).notNull(),
},
(table) => {
	return {
		admId: index("adm_id").on(table.admId),
		posId: index("pos_id").on(table.brdId),
		tnBoardCommentBrcId: primaryKey({ columns: [table.brcId], name: "tn_board_comment_brc_id"}),
	}
});

export const tnBoardFile = mysqlTable("tn_board_file", {
	brfId: int("brf_id", { unsigned: true }).autoincrement().primaryKey().notNull(),
	brfUrl: varchar("brf_url", { length: 255 }),
	brfOriginalFileName: varchar("brf_original_file_name", { length: 100 }),
	brfUpdatedAt: datetime("brf_updated_at", { mode: 'string'}),
	brfCreatedAt: datetime("brf_created_at", { mode: 'string'}).default(sql`(CURRENT_TIMESTAMP)`).notNull(),
},
(table) => {
	return {
		tnBoardFileBrfId: primaryKey({ columns: [table.brfId], name: "tn_board_file_brf_id"}),
	}
});

export const tnBoardFileMap = mysqlTable("tn_board_file_map", {
	brdId: int("brd_id", { unsigned: true }).notNull().references(() => tnBoard.brdId, { onDelete: "cascade", onUpdate: "cascade" } ),
	brfId: int("brf_id", { unsigned: true }).notNull().references(() => tnBoardFile.brfId, { onDelete: "cascade", onUpdate: "cascade" } ),
	brfmUpdatedAt: datetime("brfm_updated_at", { mode: 'string'}),
	brfmCreatedAt: datetime("brfm_created_at", { mode: 'string'}).default(sql`(CURRENT_TIMESTAMP)`).notNull(),
},
(table) => {
	return {
		brfId: index("brf_id").on(table.brfId),
		tnBoardFileMapBrdIdBrfId: primaryKey({ columns: [table.brdId, table.brfId], name: "tn_board_file_map_brd_id_brf_id"}),
	}
});

export const tnCard = mysqlTable("tn_card", {
	crdId: int("crd_id", { unsigned: true }).autoincrement().primaryKey().notNull(),
	memId: int("mem_id", { unsigned: true }).notNull().references(() => tnMember.memId, { onDelete: "cascade", onUpdate: "cascade" } ),
	crdBillingKey: varchar("crd_billing_key", { length: 255 }).notNull(),
	crdName: varchar("crd_name", { length: 10 }).notNull(),
	crdCardType: varchar("crd_card_type", { length: 10 }).notNull(),
	crdNumber: varchar("crd_number", { length: 20 }).notNull(),
	crdMain: tinyint("crd_main").default(0).notNull(),
	crdUpdatedAt: datetime("crd_updated_at", { mode: 'string'}),
	crdCreatedAt: datetime("crd_created_at", { mode: 'string'}).default(sql`(CURRENT_TIMESTAMP)`).notNull(),
},
(table) => {
	return {
		tnCardCrdId: primaryKey({ columns: [table.crdId], name: "tn_card_crd_id"}),
	}
});

export const tnClient = mysqlTable("tn_client", {
	cliId: int("cli_id", { unsigned: true }).autoincrement().primaryKey().notNull(),
	cliName: varchar("cli_name", { length: 255 }).notNull(),
	cliRegistrationNumber: varchar("cli_registration_number", { length: 12 }).notNull(),
	cliCode: varchar("cli_code", { length: 10 }).notNull(),
	cliPass: varchar("cli_pass", { length: 20 }).notNull(),
	cliCreatedAt: datetime("cli_created_at", { mode: 'string'}).default(sql`(CURRENT_TIMESTAMP)`).notNull(),
	cliUpdatedAt: datetime("cli_updated_at", { mode: 'string'}),
},
(table) => {
	return {
		tnClientCliId: primaryKey({ columns: [table.cliId], name: "tn_client_cli_id"}),
		cliCode: unique("cli_code").on(table.cliCode),
		cliRegistrationNumber: unique("cli_registration_number").on(table.cliRegistrationNumber),
	}
});

export const tnClientAnalysisBasic = mysqlTable("tn_client_analysis_basic", {
	casbId: int("casb_id", { unsigned: true }).autoincrement().primaryKey().notNull(),
	codId: int("cod_id", { unsigned: true }).notNull().references(() => tnClientOrderDetail.codId, { onDelete: "restrict", onUpdate: "restrict" } ),
	// you can use { mode: 'date' }, if you want to have Date as type for this column
	casbTreatStartDate: date("casb_treat_start_date", { mode: 'string' }).notNull(),
	casbHospitalName: varchar("casb_hospital_name", { length: 50 }).notNull(),
	casbDepartment: varchar("casb_department", { length: 20 }),
	casbTreatType: varchar("casb_treat_type", { length: 15 }).notNull(),
	casbDiseaseCode: varchar("casb_disease_code", { length: 10 }),
	casbDiseaseName: varchar("casb_disease_name", { length: 255 }),
	casbVisitDays: int("casb_visit_days").default(0).notNull(),
	casbDisease: varchar("casb_disease", { length: 255 }),
	casbInDisease: text("casb_in_disease"),
	casbNotice: text("casb_notice"),
	casbDentures: varchar("casb_dentures", { length: 255 }),
	casbToothOne: varchar("casb_tooth_one", { length: 255 }),
	casbToothFive: varchar("casb_tooth_five", { length: 255 }),
	casbEtc: varchar("casb_etc", { length: 255 }),
	casbDrugNotice: varchar("casb_drug_notice", { length: 255 }),
	casbDosingDays: int("casb_dosing_days").default(0).notNull(),
	casbInTooth: tinyint("casb_in_tooth").default(0).notNull(),
	casbDuplicated: tinyint("casb_duplicated").default(0).notNull(),
	casbSicked: tinyint("casb_sicked").default(0).notNull(),
	casbDosingId: int("casb_dosing_id").default(0).notNull(),
	casbUpdatedAt: datetime("casb_updated_at", { mode: 'string'}),
	casbCreatedAt: datetime("casb_created_at", { mode: 'string'}).default(sql`(CURRENT_TIMESTAMP)`).notNull(),
},
(table) => {
	return {
		cabId: index("cab_id").on(table.casbId),
		tnClientAnalysisBasicCasbIdCodId: primaryKey({ columns: [table.casbId, table.codId], name: "tn_client_analysis_basic_casb_id_cod_id"}),
	}
});

export const tnClientAnalysisCarBasic = mysqlTable("tn_client_analysis_car_basic", {
	cacbId: int("cacb_id", { unsigned: true }).autoincrement().primaryKey().notNull(),
	codId: int("cod_id", { unsigned: true }).notNull().references(() => tnClientOrderDetail.codId, { onDelete: "restrict", onUpdate: "restrict" } ),
	// you can use { mode: 'date' }, if you want to have Date as type for this column
	cacbTreatStartDate: date("cacb_treat_start_date", { mode: 'string' }).notNull(),
	// you can use { mode: 'date' }, if you want to have Date as type for this column
	cacbTreatEndDate: date("cacb_treat_end_date", { mode: 'string' }).notNull(),
	cacbTotalTreatDate: int("cacb_total_treat_date").notNull(),
	cacbTotalAmount: int("cacb_total_amount").notNull(),
	cacbTotalMedicalFee: int("cacb_total_medical_fee"),
	cacbOutpatientTotalAmount: int("cacb_outpatient_total_amount").notNull(),
	cacbInpatientTotalAmount: int("cacb_inpatient_total_amount").notNull(),
	cacbOutpatientMedicalFee: int("cacb_outpatient_medical_fee").notNull(),
	cacbInpatientMedicalFee: int("cacb_inpatient_medical_fee").notNull(),
	cacbOutpatientTreatDate: int("cacb_outpatient_treat_date").notNull(),
	cacbInpatientTreatDate: int("cacb_inpatient_treat_date").notNull(),
	cacbUpdatedAt: datetime("cacb_updated_at", { mode: 'string'}),
	cacbCreatedAt: datetime("cacb_created_at", { mode: 'string'}).default(sql`(CURRENT_TIMESTAMP)`).notNull(),
},
(table) => {
	return {
		acbId: index("acb_id").on(table.cacbId),
		tnAnalysisCarBasicOddIdTnOrderDetailOddIdFk: index("tn_analysis_car_basic_odd_id_tn_order_detail_odd_id_fk").on(table.codId),
		tnClientAnalysisCarBasicCacbIdCodId: primaryKey({ columns: [table.cacbId, table.codId], name: "tn_client_analysis_car_basic_cacb_id_cod_id"}),
	}
});

export const tnClientAnalysisCarDetail = mysqlTable("tn_client_analysis_car_detail", {
	cacdId: int("cacd_id", { unsigned: true }).autoincrement().primaryKey().notNull(),
	cacbId: int("cacb_id", { unsigned: true }).notNull().references(() => tnClientAnalysisCarBasic.cacbId, { onDelete: "restrict", onUpdate: "cascade" } ),
	codId: int("cod_id", { unsigned: true }).notNull().references(() => tnClientOrderDetail.codId, { onDelete: "restrict", onUpdate: "cascade" } ),
	// you can use { mode: 'date' }, if you want to have Date as type for this column
	cacdTreatStartDate: date("cacd_treat_start_date", { mode: 'string' }).notNull(),
	cacdHospitalName: varchar("cacd_hospital_name", { length: 50 }).notNull(),
	cacdDepartment: varchar("cacd_department", { length: 20 }),
	cacdTreatType: varchar("cacd_treat_type", { length: 15 }).notNull(),
	cacdDiseaseCode: varchar("cacd_disease_code", { length: 10 }),
	cacdDiseaseName: varchar("cacd_disease_name", { length: 255 }),
	cacdTreatDate: int("cacd_treat_date").notNull(),
	cacdTotalAmount: int("cacd_total_amount").notNull(),
	cacdMedicalFee: int("cacd_medical_fee").notNull(),
	cacdUpdatedAt: datetime("cacd_updated_at", { mode: 'string'}),
	cacdCreatedAt: datetime("cacd_created_at", { mode: 'string'}).default(sql`(CURRENT_TIMESTAMP)`).notNull(),
},
(table) => {
	return {
		acdId: index("acd_id").on(table.cacdId),
		tnAnalysisCarDetailAsbIdTnAnalysisCarBasicAcbIdFk: index("tn_analysis_car_detail_asb_id_tn_analysis_car_basic_acb_id_fk").on(table.cacbId),
		tnAnalysisCarDetailOddIdTnOrderDetailOddIdFk: index("tn_analysis_car_detail_odd_id_tn_order_detail_odd_id_fk").on(table.codId),
		tnClientAnalysisCarDetailCacdIdCacbIdCodId: primaryKey({ columns: [table.cacdId, table.cacbId, table.codId], name: "tn_client_analysis_car_detail_cacd_id_cacb_id_cod_id"}),
	}
});

export const tnClientAnalysisDetail = mysqlTable("tn_client_analysis_detail", {
	casdId: int("casd_id", { unsigned: true }).autoincrement().primaryKey().notNull(),
	casbId: int("casb_id", { unsigned: true }).notNull().references(() => tnClientAnalysisBasic.casbId, { onDelete: "restrict", onUpdate: "cascade" } ),
	codId: int("cod_id", { unsigned: true }).notNull().references(() => tnClientOrderDetail.codId, { onDelete: "restrict", onUpdate: "cascade" } ),
	// you can use { mode: 'date' }, if you want to have Date as type for this column
	casdTreatStartDate: date("casd_treat_start_date", { mode: 'string' }).notNull(),
	casdHospitalName: varchar("casd_hospital_name", { length: 50 }).notNull(),
	casdCodeName: varchar("casd_code_name", { length: 255 }),
	casdOperation: varchar("casd_operation", { length: 255 }),
	casdDrug: varchar("casd_drug", { length: 255 }),
	casdDrugNotice: varchar("casd_drug_notice", { length: 255 }),
	casdExamination: varchar("casd_examination", { length: 255 }),
	casdVisitDays: int("casd_visit_days").default(0).notNull(),
	casdDosingDays: int("casd_dosing_days").default(0).notNull(),
	casdDosingId: int("casd_dosing_id").default(0).notNull(),
	casdInTooth: text("casd_in_tooth"),
	casdInOperation: text("casd_in_operation"),
	casdInEtc: text("casd_in_etc"),
	casdDentures: varchar("casd_dentures", { length: 255 }),
	casdToothOne: varchar("casd_tooth_one", { length: 255 }),
	casdToothFive: varchar("casd_tooth_five", { length: 255 }),
	casdUpdaedAt: datetime("casd_updaed_at", { mode: 'string'}),
	casdCreatedAt: datetime("casd_created_at", { mode: 'string'}).default(sql`(CURRENT_TIMESTAMP)`).notNull(),
},
(table) => {
	return {
		cabId: index("cab_id").on(table.casbId),
		tnClientAnalysisDetailCasdIdCasbId: primaryKey({ columns: [table.casdId, table.casbId], name: "tn_client_analysis_detail_casd_id_casb_id"}),
	}
});

export const tnClientAnalysisOptionMap = mysqlTable("tn_client_analysis_option_map", {
	ccnCode: varchar("ccn_code", { length: 10 }).notNull().references(() => tnClientContract.ccnCode, { onDelete: "cascade", onUpdate: "cascade" } ),
	cctType: varchar("cct_type", { length: 10 }).notNull(),
	aomCreatedAt: datetime("aom_created_at", { mode: 'string'}).default(sql`(CURRENT_TIMESTAMP)`),
	aomUpdatedAt: datetime("aom_updated_at", { mode: 'string'}),
},
(table) => {
	return {
		tnClientAnalysisOptionMapCcnCodeCctType: primaryKey({ columns: [table.ccnCode, table.cctType], name: "tn_client_analysis_option_map_ccn_code_cct_type"}),
	}
});

export const tnClientAnalysisPrescibe = mysqlTable("tn_client_analysis_prescibe", {
	caspId: int("casp_id", { unsigned: true }).autoincrement().primaryKey().notNull(),
	casbId: int("casb_id", { unsigned: true }).notNull(),
	codId: int("cod_id", { unsigned: true }).notNull(),
	// you can use { mode: 'date' }, if you want to have Date as type for this column
	caspTreatStartDate: date("casp_treat_start_date", { mode: 'string' }).notNull(),
	caspHospitalName: varchar("casp_hospital_name", { length: 50 }).notNull(),
	caspTreatType: varchar("casp_treat_type", { length: 10 }).notNull(),
	caspDrugName: varchar("casp_drug_name", { length: 255 }),
	caspIngredients: varchar("casp_ingredients", { length: 255 }),
	caspOneDose: int("casp_one_dose").default(0).notNull(),
	caspDailyDosesNumber: int("casp_daily_doses_number").default(0).notNull(),
	caspTotalDosingDays: int("casp_total_dosing_days").default(0).notNull(),
	caspUpdaedAt: datetime("casp_updaed_at", { mode: 'string'}),
	caspCreatedAt: datetime("casp_created_at", { mode: 'string'}).default(sql`(CURRENT_TIMESTAMP)`).notNull(),
},
(table) => {
	return {
		tnClientAnalysisPrescibeCaspId: primaryKey({ columns: [table.caspId], name: "tn_client_analysis_prescibe_casp_id"}),
	}
});

export const tnClientContract = mysqlTable("tn_client_contract", {
	ccnId: int("ccn_id", { unsigned: true }).autoincrement().primaryKey().notNull(),
	cliId: int("cli_id", { unsigned: true }).notNull().references(() => tnClient.cliId, { onDelete: "restrict", onUpdate: "restrict" } ),
	ccnCode: varchar("ccn_code", { length: 10 }).notNull(),
	ccnApiPrice: int("ccn_api_price").notNull(),
	ccnContractStartedAt: datetime("ccn_contract_started_at", { mode: 'string'}).notNull(),
	ccnContractEndedAt: datetime("ccn_contract_ended_at", { mode: 'string'}).notNull(),
	ccnCiLimitEnabled: tinyint("ccn_ci_limit_enabled").default(0).notNull(),
	ccnCiLimitCount: int("ccn_ci_limit_count").default(0).notNull(),
	ccnCreatedAt: datetime("ccn_created_at", { mode: 'string'}).default(sql`(CURRENT_TIMESTAMP)`).notNull(),
	ccnUpdatedAt: datetime("ccn_updated_at", { mode: 'string'}),
},
(table) => {
	return {
		ccnCode: index("ccn_code").on(table.ccnCode),
		tnClientContractCcnId: primaryKey({ columns: [table.ccnId], name: "tn_client_contract_ccn_id"}),
	}
});

export const tnClientOrderDetail = mysqlTable("tn_client_order_detail", {
	codId: int("cod_id", { unsigned: true }).autoincrement().primaryKey().notNull(),
	ccnId: int("ccn_id", { unsigned: true }).notNull().references(() => tnClientContract.ccnId, { onDelete: "restrict", onUpdate: "restrict" } ),
	cluId: int("clu_id", { unsigned: true }).references(() => tnClientUser.cluId, { onDelete: "restrict", onUpdate: "restrict" } ),
	codTransactionId: varchar("cod_transaction_id", { length: 30 }).notNull(),
	codState: varchar("cod_state", { length: 10 }),
	codCompletedAt: varchar("cod_completed_at", { length: 255 }),
	codFailedAt: varchar("cod_failed_at", { length: 255 }),
	codCreatedAt: datetime("cod_created_at", { mode: 'string'}).default(sql`(CURRENT_TIMESTAMP)`).notNull(),
	codUpdatedAt: datetime("cod_updated_at", { mode: 'string'}),
},
(table) => {
	return {
		tnClientOrderDetailCodId: primaryKey({ columns: [table.codId], name: "tn_client_order_detail_cod_id"}),
	}
});

export const tnClientSettlement = mysqlTable("tn_client_settlement", {
	cstId: int("cst_id", { unsigned: true }).autoincrement().primaryKey().notNull(),
	cliId: int("cli_id", { unsigned: true }).notNull().references(() => tnClient.cliId, { onDelete: "cascade", onUpdate: "cascade" } ),
	cstCode: varchar("cst_code", { length: 20 }),
	// you can use { mode: 'date' }, if you want to have Date as type for this column
	cstDate: date("cst_date", { mode: 'string' }).notNull(),
	cstOrderDetailCount: int("cst_order_detail_count").notNull(),
	cstSettlementPrice: int("cst_settlement_price").notNull(),
	cstPaid: tinyint("cst_paid").default(0).notNull(),
	cstPaidAt: datetime("cst_paid_at", { mode: 'string'}),
	cstCreatedAt: datetime("cst_created_at", { mode: 'string'}).default(sql`(CURRENT_TIMESTAMP)`).notNull(),
	cstUpdatedAt: datetime("cst_updated_at", { mode: 'string'}),
},
(table) => {
	return {
		tnClientSettlementCstId: primaryKey({ columns: [table.cstId], name: "tn_client_settlement_cst_id"}),
	}
});

export const tnClientSettlementOrderMap = mysqlTable("tn_client_settlement_order_map", {
	cstId: int("cst_id", { unsigned: true }).notNull().references(() => tnClientSettlement.cstId, { onDelete: "cascade", onUpdate: "cascade" } ),
	codId: int("cod_id", { unsigned: true }).notNull().references(() => tnClientOrderDetail.codId, { onDelete: "cascade", onUpdate: "cascade" } ),
	somCreatedAt: datetime("som_created_at", { mode: 'string'}).default(sql`(CURRENT_TIMESTAMP)`).notNull(),
},
(table) => {
	return {
		ordId: index("ord_id").on(table.codId),
		tnClientSettlementOrderMapCstIdCodId: primaryKey({ columns: [table.cstId, table.codId], name: "tn_client_settlement_order_map_cst_id_cod_id"}),
	}
});

export const tnClientUser = mysqlTable("tn_client_user", {
	cluId: int("clu_id", { unsigned: true }).autoincrement().primaryKey().notNull(),
	cliId: int("cli_id", { unsigned: true }).references(() => tnClient.cliId, { onDelete: "cascade", onUpdate: "cascade" } ),
	cluCi: varchar("clu_ci", { length: 255 }),
},
(table) => {
	return {
		tnClientUserCluId: primaryKey({ columns: [table.cluId], name: "tn_client_user_clu_id"}),
	}
});

export const tnCodef = mysqlTable("tn_codef", {
	cdfId: varchar("cdf_id", { length: 100 }).notNull(),
	cdfAccessToken: varchar("cdf_access_token", { length: 1000 }),
	cdfTokenExpiredAt: datetime("cdf_token_expired_at", { mode: 'string'}),
	cdfCreatedAt: datetime("cdf_created_at", { mode: 'string'}).default(sql`(CURRENT_TIMESTAMP)`).notNull(),
	cdfUpdaedAt: datetime("cdf_updaed_at", { mode: 'string'}),
},
(table) => {
	return {
		tnCodefCdfId: primaryKey({ columns: [table.cdfId], name: "tn_codef_cdf_id"}),
		cdfClientId: unique("cdf_client_id").on(table.cdfId),
	}
});

export const tnCodefTest = mysqlTable("tn_codef_test", {
	codefTestId: int("codef_test_id", { unsigned: true }).autoincrement().primaryKey().notNull(),
	oddId: int("odd_id").notNull(),
	codefTestJson: json("codef_test_json").notNull(),
	codefType: varchar("codef_type", { length: 10 }),
	codefTestCreatedAt: datetime("codef_test_created_at", { mode: 'string'}).default(sql`(CURRENT_TIMESTAMP)`),
},
(table) => {
	return {
		tnCodefTestCodefTestId: primaryKey({ columns: [table.codefTestId], name: "tn_codef_test_codef_test_id"}),
	}
});

export const tnCourses = mysqlTable("tn_courses", {
	crsId: int("crs_id", { unsigned: true }).autoincrement().primaryKey().notNull(),
	ccaId: int("cca_id", { unsigned: true }).references(() => tnCoursesCategory.ccaId, { onDelete: "set null", onUpdate: "cascade" } ),
	crsName: varchar("crs_name", { length: 50 }).notNull(),
	crsInstructor: varchar("crs_instructor", { length: 10 }).notNull(),
	crsRecommend: tinyint("crs_recommend").notNull(),
	crsSort: int("crs_sort").notNull(),
	crsShow: tinyint("crs_show").notNull(),
	crsImg: varchar("crs_img", { length: 255 }).notNull(),
	crsDescription: varchar("crs_description", { length: 100 }).notNull(),
	crsSummary: text("crs_summary").notNull(),
	crsIsDeleted: tinyint("crs_is_deleted").default(0).notNull(),
	crsUpdatedAt: datetime("crs_updated_at", { mode: 'string'}),
	crsCreatedAt: datetime("crs_created_at", { mode: 'string'}).default(sql`(CURRENT_TIMESTAMP)`).notNull(),
},
(table) => {
	return {
		crsId: index("crs_id").on(table.crsId),
		tnCoursesCrsId: primaryKey({ columns: [table.crsId], name: "tn_courses_crs_id"}),
	}
});

export const tnCoursesBookmark = mysqlTable("tn_courses_bookmark", {
	crbId: int("crb_id", { unsigned: true }).autoincrement().primaryKey().notNull(),
	crsId: int("crs_id", { unsigned: true }).references(() => tnCourses.crsId, { onDelete: "set null", onUpdate: "cascade" } ),
	memId: int("mem_id", { unsigned: true }).notNull().references(() => tnMember.memId, { onDelete: "cascade", onUpdate: "cascade" } ),
	crbUpdatedAt: datetime("crb_updated_at", { mode: 'string'}),
	crbCreatedAt: datetime("crb_created_at", { mode: 'string'}).default(sql`(CURRENT_TIMESTAMP)`).notNull(),
},
(table) => {
	return {
		tnCoursesBookmarkCrbId: primaryKey({ columns: [table.crbId], name: "tn_courses_bookmark_crb_id"}),
		tnCoursesBookmarkMemIdCrsIdUnique: unique("tn_courses_bookmark_mem_id_crs_id_unique").on(table.crsId, table.memId),
	}
});

export const tnCoursesCategory = mysqlTable("tn_courses_category", {
	ccaId: int("cca_id", { unsigned: true }).autoincrement().primaryKey().notNull(),
	ccaName: varchar("cca_name", { length: 20 }).notNull(),
	ccaSort: int("cca_sort").default(0).notNull(),
	ccaShow: tinyint("cca_show").notNull(),
	ccaUpdatedAt: datetime("cca_updated_at", { mode: 'string'}),
	ccaCreatedAt: datetime("cca_created_at", { mode: 'string'}).default(sql`(CURRENT_TIMESTAMP)`).notNull(),
},
(table) => {
	return {
		tnCoursesCategoryCcaId: primaryKey({ columns: [table.ccaId], name: "tn_courses_category_cca_id"}),
	}
});

export const tnCoursesEnrollments = mysqlTable("tn_courses_enrollments", {
	cemId: int("cem_id", { unsigned: true }).autoincrement().primaryKey().notNull(),
	crsId: int("crs_id", { unsigned: true }).notNull().references(() => tnCourses.crsId, { onUpdate: "cascade" } ),
	memId: int("mem_id", { unsigned: true }).notNull().references(() => tnMember.memId, { onDelete: "cascade", onUpdate: "cascade" } ),
	cemIsCompleted: tinyint("cem_is_completed").default(0).notNull(),
	cemCompletedAt: datetime("cem_completed_at", { mode: 'string'}),
	cemProgressRate: int("cem_progress_rate").default(0).notNull(),
	cemUpdatedAt: datetime("cem_updated_at", { mode: 'string'}),
	cemCreatedAt: datetime("cem_created_at", { mode: 'string'}).default(sql`(CURRENT_TIMESTAMP)`).notNull(),
},
(table) => {
	return {
		tnCoursesEnrollmentsCemId: primaryKey({ columns: [table.cemId], name: "tn_courses_enrollments_cem_id"}),
		tnCoursesEnrollmentsCrsIdMemIdUnique: unique("tn_courses_enrollments_crs_id_mem_id_unique").on(table.crsId, table.memId),
	}
});

export const tnCoursesProgress = mysqlTable("tn_courses_progress", {
	crpId: int("crp_id", { unsigned: true }).autoincrement().primaryKey().notNull(),
	crsId: int("crs_id", { unsigned: true }).notNull().references(() => tnCourses.crsId, { onUpdate: "cascade" } ),
	memId: int("mem_id", { unsigned: true }).notNull().references(() => tnMember.memId, { onDelete: "cascade", onUpdate: "cascade" } ),
	lastWatchedCrvId: int("last_watched_crv_id").notNull(),
	crpUpdatedAt: datetime("crp_updated_at", { mode: 'string'}),
	crpCreatedAt: datetime("crp_created_at", { mode: 'string'}).default(sql`(CURRENT_TIMESTAMP)`).notNull(),
},
(table) => {
	return {
		tnCoursesPrgoressCrsIdTnCoursesCrsId: index("tn_courses_prgoress_crs_id_tn_courses_crs_id").on(table.crsId),
		tnCoursesProgressCrpId: primaryKey({ columns: [table.crpId], name: "tn_courses_progress_crp_id"}),
		tnCoursesProgressCrsIdTnCoursesMemIdUnique: unique("tn_courses_progress_crs_id_tn_courses_mem_id_unique").on(table.crsId, table.memId),
	}
});

export const tnCoursesReviews = mysqlTable("tn_courses_reviews", {
	crrId: int("crr_id", { unsigned: true }).autoincrement().primaryKey().notNull(),
	crsId: int("crs_id", { unsigned: true }).references(() => tnCourses.crsId, { onDelete: "set null", onUpdate: "cascade" } ),
	memId: int("mem_id", { unsigned: true }).notNull().references(() => tnMember.memId, { onDelete: "cascade", onUpdate: "cascade" } ),
	crrContent: text("crr_content").notNull(),
	crrScore: int("crr_score").notNull(),
	crrIsDeleted: tinyint("crr_is_deleted").default(0).notNull(),
	crrShow: tinyint("crr_show").default(1).notNull(),
	crrUpdatedAt: datetime("crr_updated_at", { mode: 'string'}),
	crrCreatedAt: datetime("crr_created_at", { mode: 'string'}).default(sql`(CURRENT_TIMESTAMP)`).notNull(),
},
(table) => {
	return {
		crrId: index("crr_id").on(table.crrId),
		tnCoursesReviewsCrrId: primaryKey({ columns: [table.crrId], name: "tn_courses_reviews_crr_id"}),
		tnCoursesReviewsCrsIdMemIdUnique: unique("tn_courses_reviews_crs_id_mem_id_unique").on(table.crsId, table.memId),
	}
});

export const tnCoursesSections = mysqlTable("tn_courses_sections", {
	cssId: int("css_id", { unsigned: true }).autoincrement().primaryKey().notNull(),
	crsId: int("crs_id", { unsigned: true }).notNull().references(() => tnCourses.crsId, { onDelete: "cascade", onUpdate: "cascade" } ),
	cssTitle: varchar("css_title", { length: 30 }).notNull(),
	cssOrder: int("css_order").notNull(),
	cssUpdatedAt: datetime("css_updated_at", { mode: 'string'}),
	cssCreatedAt: datetime("css_created_at", { mode: 'string'}).default(sql`(CURRENT_TIMESTAMP)`).notNull(),
},
(table) => {
	return {
		cssId: index("css_id").on(table.cssId),
		tnCoursesSectionsCssIdCrsId: primaryKey({ columns: [table.cssId, table.crsId], name: "tn_courses_sections_css_id_crs_id"}),
	}
});

export const tnCoursesVideos = mysqlTable("tn_courses_videos", {
	crvId: int("crv_id", { unsigned: true }).autoincrement().primaryKey().notNull(),
	cssId: int("css_id", { unsigned: true }).notNull().references(() => tnCoursesSections.cssId, { onDelete: "cascade", onUpdate: "cascade" } ),
	crvTitle: varchar("crv_title", { length: 30 }).notNull(),
	crvVideoUrl: varchar("crv_video_url", { length: 255 }).notNull(),
	crvDurationSeconds: int("crv_duration_seconds"),
	crvOrder: int("crv_order").notNull(),
	crvUpdatedAt: datetime("crv_updated_at", { mode: 'string'}),
	crvCreatedAt: datetime("crv_created_at", { mode: 'string'}).default(sql`(CURRENT_TIMESTAMP)`).notNull(),
},
(table) => {
	return {
		tnCoursesVideosCrvId: primaryKey({ columns: [table.crvId], name: "tn_courses_videos_crv_id"}),
	}
});

export const tnCoursesVideosProgress = mysqlTable("tn_courses_videos_progress", {
	crvpId: int("crvp_id", { unsigned: true }).autoincrement().primaryKey().notNull(),
	crvId: int("crv_id", { unsigned: true }).notNull().references(() => tnCoursesVideos.crvId, { onDelete: "restrict", onUpdate: "cascade" } ),
	memId: int("mem_id", { unsigned: true }).notNull().references(() => tnMember.memId, { onDelete: "cascade", onUpdate: "cascade" } ),
	crvpLastWatchedSeconds: int("crvp_last_watched_seconds").default(0).notNull(),
	crvpIsCompleted: tinyint("crvp_is_completed").default(0).notNull(),
	crvpCompletedAt: datetime("crvp_completed_at", { mode: 'string'}),
	crvpUpdatedAt: datetime("crvp_updated_at", { mode: 'string'}),
	crvpCreatedAt: datetime("crvp_created_at", { mode: 'string'}).default(sql`(CURRENT_TIMESTAMP)`).notNull(),
},
(table) => {
	return {
		tnCoursesVideosProgressCrvpId: primaryKey({ columns: [table.crvpId], name: "tn_courses_videos_progress_crvp_id"}),
		tnCoursesVideosProgressCrvIdMemIdUnique: unique("tn_courses_videos_progress_crv_id_mem_id_unique").on(table.crvId, table.memId),
	}
});

export const tnInsurer = mysqlTable("tn_insurer", {
	insId: int("ins_id", { unsigned: true }).autoincrement().primaryKey().notNull(),
	insName: varchar("ins_name", { length: 30 }).notNull(),
	insCode: varchar("ins_code", { length: 10 }).notNull(),
	insType: varchar("ins_type", { length: 10 }),
	insSort: int("ins_sort").default(0).notNull(),
	insIsOnShow: tinyint("ins_is_on_show").default(0),
	insFaxNumber: varchar("ins_fax_number", { length: 20 }),
	insFaxList: json("ins_fax_list").$type<{ faxNumber: string; description?: string }[]>(),
	insFaxType: varchar("ins_fax_type", { length: 10 }).default('FIXED'),
	//* 가상·다중팩스 청구서에 '콜센터 문의(번호)' 로 찍히는 값. 비면 문구만 찍힌다.
	//* 이 선언이 있어야 getTableColumns(tnInsurer) 가 값을 실어 오버레이가 읽을 수 있다 —
	//* 그래서 0030 SQL 을 코드보다 먼저 적용해야 한다(없는 컬럼을 select 하면 조회가 죽는다).
	insCsNumber: varchar("ins_cs_number", { length: 20 }),
	insCreatedAt: datetime("ins_created_at", { mode: 'string'}).default(sql`(CURRENT_TIMESTAMP)`).notNull(),
	insUpdatedAt: datetime("ins_updated_at", { mode: 'string'}),
},
(table) => {
	return {
		tnInsurerInsId: primaryKey({ columns: [table.insId], name: "tn_insurer_ins_id"}),
	}
});

export const tnInsurerInvoice = mysqlTable("tn_insurer_invoice", {
	iivId: int("iiv_id", { unsigned: true }).autoincrement().primaryKey().notNull(),
	insId: int("ins_id", { unsigned: true }).notNull().references(() => tnInsurer.insId, { onDelete: "cascade", onUpdate: "cascade" } ),
	ivcId: int("ivc_id", { unsigned: true }).notNull().references(() => tnInvoice.ivcId),
	iivCoordinateX: decimal("iiv_coordinate_x", { precision: 7, scale: 2 }).notNull(),
	iivStyle: json("iiv_style").notNull(),
	iivCoordinateY: decimal("iiv_coordinate_y", { precision: 7, scale: 2 }).notNull(),
	iivPage: int("iiv_page").notNull(),
},
(table) => {
	return {
		tnInsurerInvoiceIivId: primaryKey({ columns: [table.iivId], name: "tn_insurer_invoice_iiv_id"}),
	}
});

export const tnInvoice = mysqlTable("tn_invoice", {
	ivcId: int("ivc_id", { unsigned: true }).autoincrement().primaryKey().notNull(),
	ivcNameKr: varchar("ivc_name_kr", { length: 30 }).notNull(),
	ivcNameEn: varchar("ivc_name_en", { length: 30 }).notNull(),
	ivcType: varchar("ivc_type", { length: 10 }).notNull(),
},
(table) => {
	return {
		tnInvoiceIvcId: primaryKey({ columns: [table.ivcId], name: "tn_invoice_ivc_id"}),
	}
});

export const tnLossAdjustment = mysqlTable("tn_loss_adjustment", {
	lsaId: int("lsa_id", { unsigned: true }).autoincrement().primaryKey().notNull(),
	memId: int("mem_id", { unsigned: true }).default(0).notNull().references(() => tnMember.memId, { onDelete: "cascade", onUpdate: "cascade" } ),
	lacId: int("lac_id", { unsigned: true }).notNull().references(() => tnLossAdjustmentCategory.lacId, { onDelete: "restrict", onUpdate: "cascade" } ),
	lascId: int("lasc_id", { unsigned: true }),
	lsaTitle: varchar("lsa_title", { length: 255 }).notNull(),
	lsaContent: text("lsa_content").notNull(),
	lsaState: varchar("lsa_state", { length: 15 }).notNull(),
	lsaPhone: varchar("lsa_phone", { length: 128 }),
	lsaUpdatedAt: datetime("lsa_updated_at", { mode: 'string'}),
	lsaCreatedAt: datetime("lsa_created_at", { mode: 'string'}).default(sql`(CURRENT_TIMESTAMP)`).notNull(),
},
(table) => {
	return {
		lacId: index("lac_id").on(table.lacId),
		lascId: index("lasc_id").on(table.lascId),
		lsaId: index("lsa_id").on(table.lsaId),
		memId: index("mem_id").on(table.memId),
		tnLossAdjustmentLsaId: primaryKey({ columns: [table.lsaId], name: "tn_loss_adjustment_lsa_id"}),
	}
});

export const tnLossAdjustmentCategory = mysqlTable("tn_loss_adjustment_category", {
	lacId: int("lac_id", { unsigned: true }).autoincrement().primaryKey().notNull(),
	lacName: varchar("lac_name", { length: 255 }).notNull(),
	lacSort: int("lac_sort").default(0).notNull(),
	lacShow: tinyint("lac_show").default(1).notNull(),
	lacUpdatedAt: datetime("lac_updated_at", { mode: 'string'}),
	lacCreatedAt: datetime("lac_created_at", { mode: 'string'}).default(sql`(CURRENT_TIMESTAMP)`).notNull(),
},
(table) => {
	return {
		lacId: index("lac_id").on(table.lacId),
		tnLossAdjustmentCategoryLacId: primaryKey({ columns: [table.lacId], name: "tn_loss_adjustment_category_lac_id"}),
	}
});

export const tnLossAdjustmentComment = mysqlTable("tn_loss_adjustment_comment", {
	lacmId: int("lacm_id", { unsigned: true }).autoincrement().primaryKey().notNull(),
	admId: int("adm_id", { unsigned: true }).references(() => tnAdmin.admId, { onDelete: "set null", onUpdate: "cascade" } ),
	lsaId: int("lsa_id", { unsigned: true }).notNull().references(() => tnLossAdjustment.lsaId, { onDelete: "cascade", onUpdate: "cascade" } ),
	lacmContent: text("lacm_content").notNull(),
	lacmUpdatedAt: datetime("lacm_updated_at", { mode: 'string'}),
	lacmCreatedAt: datetime("lacm_created_at", { mode: 'string'}).default(sql`(CURRENT_TIMESTAMP)`).notNull(),
},
(table) => {
	return {
		lacmId: index("lacm_id").on(table.lacmId),
		tnLossAdjustmentCommentLacmId: primaryKey({ columns: [table.lacmId], name: "tn_loss_adjustment_comment_lacm_id"}),
	}
});

export const tnLossAdjustmentFile = mysqlTable("tn_loss_adjustment_file", {
	lafId: int("laf_id", { unsigned: true }).autoincrement().primaryKey().notNull(),
	lafUrl: varchar("laf_url", { length: 255 }),
	lafOriginalFileName: varchar("laf_original_file_name", { length: 100 }),
	lafUpdatedAt: datetime("laf_updated_at", { mode: 'string'}),
	lafCreatedAt: datetime("laf_created_at", { mode: 'string'}).default(sql`(CURRENT_TIMESTAMP)`).notNull(),
},
(table) => {
	return {
		tnLossAdjustmentFileLafId: primaryKey({ columns: [table.lafId], name: "tn_loss_adjustment_file_laf_id"}),
	}
});

export const tnLossAdjustmentFileMap = mysqlTable("tn_loss_adjustment_file_map", {
	lsaId: int("lsa_id", { unsigned: true }).notNull().references(() => tnLossAdjustment.lsaId, { onDelete: "cascade", onUpdate: "cascade" } ),
	lafId: int("laf_id", { unsigned: true }).notNull().references(() => tnLossAdjustmentFile.lafId, { onDelete: "cascade", onUpdate: "cascade" } ),
	lafmUpdatedAt: datetime("lafm_updated_at", { mode: 'string'}),
	lafmCreatedAt: datetime("lafm_created_at", { mode: 'string'}).default(sql`(CURRENT_TIMESTAMP)`),
},
(table) => {
	return {
		lafId: index("laf_id").on(table.lafId),
		tnLossAdjustmentFileMapLsaIdLafId: primaryKey({ columns: [table.lsaId, table.lafId], name: "tn_loss_adjustment_file_map_lsa_id_laf_id"}),
	}
});

export const tnLossAdjustmentSubCategory = mysqlTable("tn_loss_adjustment_sub_category", {
	lascId: int("lasc_id", { unsigned: true }).autoincrement().primaryKey().notNull(),
	lacId: int("lac_Id", { unsigned: true }).notNull().references(() => tnLossAdjustmentCategory.lacId, { onDelete: "cascade", onUpdate: "cascade" } ),
	lascName: varchar("lasc_name", { length: 255 }),
	lascSort: int("lasc_sort").default(0).notNull(),
	lascUpdatedAt: datetime("lasc_updated_at", { mode: 'string'}),
	lascCreatedAt: datetime("lasc_created_at", { mode: 'string'}).default(sql`(CURRENT_TIMESTAMP)`).notNull(),
},
(table) => {
	return {
		lascId: index("lasc_id").on(table.lascId),
		tnLossAdjustmentSubCategoryLascIdLacId: primaryKey({ columns: [table.lascId, table.lacId], name: "tn_loss_adjustment_sub_category_lasc_id_lac_Id"}),
	}
});

export const tnMember = mysqlTable("tn_member", {
	memId: int("mem_id", { unsigned: true }).autoincrement().primaryKey().notNull(),
	agcId: int("agc_id", { unsigned: true }),
	//* 기업조직(task-688): 마이그레이션 후 NOT NULL ALTER 예정. 신규 등록 시 항상 지정 필수.
	orgId: varchar("org_id", { length: 26 }).references(() => tnAgencyOrganization.orgId, { onDelete: "restrict", onUpdate: "cascade" } ),
	//* 조직관리자 자격(corp 권한위임): 1이면 자기 org_id 부분트리 조회 권한(CORP_ORG)
	memIsOrgManager: tinyint("mem_is_org_manager").default(0).notNull(),
	sagCode: varchar("sag_code", { length: 20 }),
	sacCode: varchar("sac_code", { length: 20 }),
	memType: varchar("mem_type", { length: 15 }).notNull(),
	memName: varchar("mem_name", { length: 128 }).notNull(),
	memLoginId: varchar("mem_login_id", { length: 20 }).notNull(),
	memPassword: varchar("mem_password", { length: 100 }).notNull(),
	memEmail: varchar("mem_email", { length: 128 }),
	memPhone: varchar("mem_phone", { length: 128 }).notNull(),
	memAgency: varchar("mem_agency", { length: 30 }).default('').notNull(),
	memIsResigned: tinyint("mem_is_resigned").default(0),
	memResignedAt: datetime("mem_resigned_at", { mode: 'string'}),
	memLastLoginAt: datetime("mem_last_login_at", { mode: 'string'}),
	memFcmToken: varchar("mem_fcm_token", { length: 255 }),
	memRefreshToken: varchar("mem_refresh_token", { length: 255 }),
	memMyReferralCode: varchar("mem_my_referral_code", { length: 6 }),
	memReferralCode: varchar("mem_referral_code", { length: 6 }),
	memMoney: int("mem_money", { unsigned: true }).default(0).notNull(),
	memPurchaseMoney: int("mem_purchase_money", { unsigned: true }).default(0).notNull(),
	memAgencyMoney: int("mem_agency_money", { unsigned: true }).default(0).notNull(),
	memPushPayment: tinyint("mem_push_payment").default(1).notNull(),
	memPushAnalysis: tinyint("mem_push_analysis").default(1).notNull(),
	memPushEvent: tinyint("mem_push_event").default(1).notNull(),
	memUpdatedAt: datetime("mem_updated_at", { mode: 'string'}),
	memCreatedAt: datetime("mem_created_at", { mode: 'string'}).default(sql`(CURRENT_TIMESTAMP)`).notNull(),
},
(table) => {
	return {
		agcId: index("agc_id").on(table.agcId),
		orgId: index("mem_org_id").on(table.orgId),
		tnMemberMemId: primaryKey({ columns: [table.memId], name: "tn_member_mem_id"}),
		admLoginId: unique("adm_login_id").on(table.memLoginId, table.agcId),
		memMyReferralCode: unique("mem_my_referral_code").on(table.memMyReferralCode),
	}
});

export const tnFaxConfig = mysqlTable("tn_fax_config", {
	fxcId: int("fxc_id", { unsigned: true }).autoincrement().primaryKey().notNull(),
	fxcPointPerPage: int("fxc_point_per_page", { unsigned: true }).default(50).notNull(),
	fxcApiUsageAmount: int("fxc_api_usage_amount", { unsigned: true }).default(0).notNull(),
	fxcUpdatedAt: datetime("fxc_updated_at", { mode: 'string'}),
	fxcCreatedAt: datetime("fxc_created_at", { mode: 'string'}).default(sql`(CURRENT_TIMESTAMP)`).notNull(),
},
(table) => {
	return {
		tnFaxConfigFxcId: primaryKey({ columns: [table.fxcId], name: "tn_fax_config_fxc_id"}),
	}
});

export const thFax = mysqlTable("th_fax", {
	fxhId: int("fxh_id", { unsigned: true }).autoincrement().primaryKey().notNull(),
	memId: int("mem_id", { unsigned: true }).notNull().references(() => tnMember.memId, { onDelete: "restrict", onUpdate: "cascade" }),
	ivhId: int("ivh_id", { unsigned: true }).references(() => thInvoice.ivhId, { onDelete: "restrict", onUpdate: "cascade" }),
	fxhReceiverName: varchar("fxh_receiver_name", { length: 50 }).notNull(),
	fxhReceiverFax: varchar("fxh_receiver_fax", { length: 20 }).notNull(),
	fxhPageCount: int("fxh_page_count", { unsigned: true }).notNull(),
	fxhPointUsed: int("fxh_point_used", { unsigned: true }).notNull(),
	fxhApiCost: int("fxh_api_cost", { unsigned: true }).notNull(),
	fxhStatus: varchar("fxh_status", { length: 20 }).notNull(),
	fxhSendResult: text("fxh_send_result"),
	fxhFaxCode: varchar("fxh_fax_code", { length: 50 }),
	fxhIsResend: tinyint("fxh_is_resend").default(0).notNull(),
	fxhOriginalFxhId: int("fxh_original_fxh_id", { unsigned: true }),
	fxhBatchId: varchar("fxh_batch_id", { length: 50 }),
	fxhBatchAlarmSent: tinyint("fxh_batch_alarm_sent").default(0).notNull(),
	fxhRequestStatus: varchar("fxh_request_status", { length: 20 }),
	fxhDeliveryStatus: varchar("fxh_delivery_status", { length: 20 }),
	fxhFailureReason: varchar("fxh_failure_reason", { length: 100 }),
	fxhMwlId: int("fxh_mwl_id", { unsigned: true }),
	fxhCompletedAt: datetime("fxh_completed_at", { mode: 'string' }),
	fxhCreatedAt: datetime("fxh_created_at", { mode: 'string'}).default(sql`(CURRENT_TIMESTAMP)`).notNull(),
},
(table) => {
	return {
		memId: index("idx_fxh_mem_id").on(table.memId),
		ivhId: index("idx_fxh_ivh_id").on(table.ivhId),
		status: index("idx_fxh_status").on(table.fxhStatus),
		faxCode: index("idx_fxh_fax_code").on(table.fxhFaxCode),
		createdAt: index("idx_fxh_created_at").on(table.fxhCreatedAt),
		batchId: index("idx_fxh_batch_id").on(table.fxhBatchId),
		thFaxFxhId: primaryKey({ columns: [table.fxhId], name: "th_fax_fxh_id"}),
	}
});

export const tnMenu = mysqlTable("tn_menu", {
	mnuId: int("mnu_id", { unsigned: true }).autoincrement().primaryKey().notNull(),
	mnuName: varchar("mnu_name", { length: 255 }).notNull(),
	mnuCode: varchar("mnu_code", { length: 255 }),
	mnuParentId: int("mnu_parent_id"),
	mnuDepth: int("mnu_depth").notNull(),
	mnuUrl: varchar("mnu_url", { length: 255 }),
	mnuIcon: varchar("mnu_icon", { length: 255 }),
	mnuUpdatedAt: datetime("mnu_updated_at", { mode: 'string'}),
	mnuCreatedAt: datetime("mnu_created_at", { mode: 'string'}).default(sql`(CURRENT_TIMESTAMP)`),
},
(table) => {
	return {
		mnuId: index("mnu_id").on(table.mnuId),
		tnMenuMnuId: primaryKey({ columns: [table.mnuId], name: "tn_menu_mnu_id"}),
	}
});

export const tnMenuAuthMap = mysqlTable("tn_menu_auth_map", {
	athId: int("ath_id", { unsigned: true }).notNull().references(() => tnAuth.athId, { onDelete: "cascade", onUpdate: "cascade" } ),
	mnuId: int("mnu_id", { unsigned: true }).notNull().references(() => tnMenu.mnuId, { onDelete: "cascade", onUpdate: "cascade" } ),
	mamUpdatedAt: datetime("mam_updated_at", { mode: 'string'}),
	mamCreatedAt: datetime("mam_created_at", { mode: 'string'}).default(sql`(CURRENT_TIMESTAMP)`).notNull(),
},
(table) => {
	return {
		mnuId: index("mnu_id").on(table.mnuId),
		tnMenuAuthMapAthIdMnuId: primaryKey({ columns: [table.athId, table.mnuId], name: "tn_menu_auth_map_ath_id_mnu_id"}),
	}
});

export const tnOrder = mysqlTable("tn_order", {
	ordId: int("ord_id", { unsigned: true }).autoincrement().primaryKey().notNull(),
	pmtId: int("pmt_id", { unsigned: true }).notNull().references(() => tnPayment.pmtId, { onDelete: "restrict", onUpdate: "cascade" } ),
	ordType: varchar("ord_type", { length: 10 }).notNull(),
	ordOid: varchar("ord_oid", { length: 20 }).notNull(),
	ordProductType: varchar("ord_product_type", { length: 10 }).notNull(),
	ordProductCode: varchar("ord_product_code", { length: 30 }).notNull(),
	ordProductName: varchar("ord_product_name", { length: 100 }).notNull(),
	ordLimitedQty: int("ord_limited_qty").notNull(),
	ordUsedQty: int("ord_used_qty").default(0).notNull(),
	ordReservedQty: int("ord_reserved_qty").default(0).notNull(),
	ordInvoiceQty: int("ord_invoice_qty").default(0).notNull(),
	ordSettlementPrice: int("ord_settlement_price").default(0).notNull(),
	//* 과금방식 스냅샷(주문 생성 시 활성계약 act_billing_type 복사) — 정산 집계·표시 기준.
	//*   기업FC 주문만 값 보유(PREPAID/POSTPAID/FREE), B2C 주문은 NULL.
	ordBillingType: varchar("ord_billing_type", { length: 16 }),
	// you can use { mode: 'date' }, if you want to have Date as type for this column
	ordExpiredAt: date("ord_expired_at", { mode: 'string' }),
	ordUpdatedAt: datetime("ord_updated_at", { mode: 'string'}),
	ordCreatedAt: datetime("ord_created_at", { mode: 'string'}).default(sql`(CURRENT_TIMESTAMP)`).notNull(),
},
(table) => {
	return {
		tnOrderOrdId: primaryKey({ columns: [table.ordId], name: "tn_order_ord_id"}),
		ordId: unique("ord_id").on(table.pmtId),
	}
});

export const tnOrderDetail = mysqlTable("tn_order_detail", {
	oddId: int("odd_id", { unsigned: true }).autoincrement().primaryKey().notNull(),
	ordId: int("ord_id", { unsigned: true }).notNull().references(() => tnOrder.ordId, { onDelete: "restrict", onUpdate: "cascade" } ),
	usrId: int("usr_id", { unsigned: true }).references(() => tnUser.usrId, { onDelete: "restrict", onUpdate: "cascade" } ),
	oddTransactionId: varchar("odd_transaction_id", { length: 30 }).notNull(),
	oddState: varchar("odd_state", { length: 10 }).notNull(),
	oddFinalState: varchar("odd_final_state", { length: 10 }),
	//* 진료 처리 공급자 ('codef'|'coocon'|'octover'). 멀티 디스패처가 처리완료 시 기록.
	oddProvider: varchar("odd_provider", { length: 20 }),
	oddReservationSettled: tinyint("odd_reservation_settled").default(0).notNull(),
	oddShow: tinyint("odd_show").default(1).notNull(),
	oddDeletion: tinyint("odd_deletion").default(0).notNull(),
	oddDeletedAt: datetime("odd_deleted_at", { mode: 'string'}),
	oddCompletedAt: datetime("odd_completed_at", { mode: 'string'}),
	oddFailedAt: datetime("odd_failed_at", { mode: 'string'}),
	oddTimeout: tinyint("odd_timeout").default(0).notNull(), //* 수집 타임아웃 실패(병력과다) — 목록에서 재시도 대신 건강이음 안내
	oddUpdatedAt: datetime("odd_updated_at", { mode: 'string'}),
	oddCreatedAt: datetime("odd_created_at", { mode: 'string'}).default(sql`(CURRENT_TIMESTAMP)`).notNull(),
},
(table) => {
	return {
		ordId: index("ord_id").on(table.ordId),
		usrId: index("usr_id").on(table.usrId),
		tnOrderDetailOddId: primaryKey({ columns: [table.oddId], name: "tn_order_detail_odd_id"}),
	}
});

export const tnPayment = mysqlTable("tn_payment", {
	pmtId: int("pmt_id", { unsigned: true }).autoincrement().primaryKey().notNull(),
	subId: int("sub_id", { unsigned: true }).notNull().references(() => tnSubscribe.subId, { onDelete: "restrict", onUpdate: "cascade" } ),
	pmtState: varchar("pmt_state", { length: 10 }).notNull(),
	pmtMethod: varchar("pmt_method", { length: 10 }).notNull(),
	pmtTid: varchar("pmt_tid", { length: 40 }),
	pmtAmount: int("pmt_amount"),
	pmtCardName: varchar("pmt_card_name", { length: 10 }),
	pmtCardType: varchar("pmt_card_type", { length: 10 }),
	pmtCardNumber: varchar("pmt_card_number", { length: 20 }),
	pmtCardBillingKey: varchar("pmt_card_billing_key", { length: 255 }),
	pmtReason: varchar("pmt_reason", { length: 255 }),
	pmtApprovedAt: datetime("pmt_approved_at", { mode: 'string'}),
	pmtCanceledAt: datetime("pmt_canceled_at", { mode: 'string'}),
	pmtUpdatedAt: datetime("pmt_updated_at", { mode: 'string'}),
	pmtCreatedAt: datetime("pmt_created_at", { mode: 'string'}).default(sql`(CURRENT_TIMESTAMP)`).notNull(),
},
(table) => {
	return {
		tnPaymentPmtId: primaryKey({ columns: [table.pmtId], name: "tn_payment_pmt_id"}),
		pmtTid: unique("pmt_tid").on(table.pmtTid),
	}
});

export const tnPopup = mysqlTable("tn_popup", {
	popId: int("pop_id", { unsigned: true }).autoincrement().primaryKey().notNull(),
	popType: varchar("pop_type", { length: 10 }).default('POP002').notNull(),
	popName: varchar("pop_name", { length: 20 }).notNull(),
	popTitle: varchar("pop_title", { length: 20 }),
	popContent: text("pop_content"),
	popDateContent: varchar("pop_date_content", { length: 255 }),
	popSort: int("pop_sort").default(0).notNull(),
	popShow: tinyint("pop_show").default(1).notNull(),
	popLinked: tinyint("pop_linked").default(0).notNull(),
	popLink: varchar("pop_link", { length: 100 }),
	popImg: varchar("pop_img", { length: 255 }),
	popOpenedAt: datetime("pop_opened_at", { mode: 'string'}),
	popClosedAt: datetime("pop_closed_at", { mode: 'string'}),
	popUpdatedAt: datetime("pop_updated_at", { mode: 'string'}),
	popCreatedAt: datetime("pop_created_at", { mode: 'string'}).default(sql`(CURRENT_TIMESTAMP)`).notNull(),
},
(table) => {
	return {
		tnPopupPopId: primaryKey({ columns: [table.popId], name: "tn_popup_pop_id"}),
	}
});

//* 기관별 일시 사용중지 설정 (심평원/국세청)
export const tnInstitutionBlock = mysqlTable("tn_institution_block", {
	isbId: int("isb_id", { unsigned: true }).autoincrement().primaryKey().notNull(),
	isbInstitution: varchar("isb_institution", { length: 10 }).notNull(),
	isbBlocked: tinyint("isb_blocked").default(0).notNull(),
	isbPopType: varchar("isb_pop_type", { length: 10 }).default('POP001').notNull(),
	isbTitle: varchar("isb_title", { length: 100 }),
	isbContent: text("isb_content"),
	isbImg: varchar("isb_img", { length: 255 }),
	isbStartedAt: datetime("isb_started_at", { mode: 'string'}),
	isbEndedAt: datetime("isb_ended_at", { mode: 'string'}),
	isbUpdatedAt: datetime("isb_updated_at", { mode: 'string'}),
	isbCreatedAt: datetime("isb_created_at", { mode: 'string'}).default(sql`(CURRENT_TIMESTAMP)`).notNull(),
},
(table) => {
	return {
		tnInstitutionBlockIsbId: primaryKey({ columns: [table.isbId], name: "tn_institution_block_isb_id"}),
		isbInstitution: unique("isb_institution").on(table.isbInstitution),
	}
});

//* 진료 스크래핑 공급자 설정 (멀티 디스패처 풀). 관리자가 단가/한도/사용여부 조정.
//* 디스패처는 enabled=1 행을 unit_cost 오름차순(=싼 곳 우선)으로 읽어 라우팅.
export const tnTreatProvider = mysqlTable("tn_treat_provider", {
	tprId: int("tpr_id", { unsigned: true }).autoincrement().primaryKey().notNull(),
	tprKey: varchar("tpr_key", { length: 20 }).notNull(), //* 'codef'|'coocon'|'octover'
	tprName: varchar("tpr_name", { length: 50 }).notNull(), //* 표시명
	tprLimitPerMin: int("tpr_limit_per_min").default(30).notNull(), //* 분당 한도
	tprFlowCost: int("tpr_flow_cost").default(3).notNull(), //* 플로우 1건당 비용(한도 소모)
	tprUnitCost: int("tpr_unit_cost").default(1).notNull(), //* 단가(낮을수록 우선)
	tprEnabled: tinyint("tpr_enabled").default(1).notNull(), //* 사용 여부
	tprRateEnabled: tinyint("tpr_rate_enabled").default(0).notNull(), //* 분당 rate-limit(타임) 적용 여부 — ON이면 limitPerMin/flowCost를 '분당 허용건수'로 해석
	tprSplitCount: tinyint("tpr_split_count").default(1).notNull(), //* 수집 분할 횟수(조회기간 N등분 순차+병합). 1=분할없음. 현재 coocon만 지원
	tprSort: int("tpr_sort").default(0).notNull(), //* 표시 정렬
	tprWebhookUrl: varchar("tpr_webhook_url", { length: 255 }), //* 벤더 장애 통보 웹훅 URL(구글챗 등, 빈 값=미발송). 이 벤더 관련 경고만 이 채널로.
	tprUpdatedAt: datetime("tpr_updated_at", { mode: 'string'}),
	tprCreatedAt: datetime("tpr_created_at", { mode: 'string'}).default(sql`(CURRENT_TIMESTAMP)`).notNull(),
},
(table) => {
	return {
		tnTreatProviderTprId: primaryKey({ columns: [table.tprId], name: "tn_treat_provider_tpr_id"}),
		tprKey: unique("tpr_key").on(table.tprKey),
	}
});

//* 진료 전역 설정(key-value). 자동차보험 수집 전체 ON/OFF(enable_treat_car) 등. env 대체, 어드민에서 토글.
export const tnTreatSetting = mysqlTable("tn_treat_setting", {
	tstKey: varchar("tst_key", { length: 50 }).notNull(), //* 설정 키(enable_treat_car 등)
	tstValue: varchar("tst_value", { length: 255 }).notNull(), //* 값('1'/'0' 등 문자열)
	tstUpdatedAt: datetime("tst_updated_at", { mode: 'string'}),
	tstCreatedAt: datetime("tst_created_at", { mode: 'string'}).default(sql`(CURRENT_TIMESTAMP)`).notNull(),
},
(table) => {
	return {
		tnTreatSettingTstKey: primaryKey({ columns: [table.tstKey], name: "tn_treat_setting_tst_key"}),
	}
});

//* 자동차 내부 카나리 1회 요청. 행은 운영자가 승인된 동의문과 함께 사전 발급하고,
//* 일반 알림톡 사용자가 그 문구에 명시 동의한 뒤에만 odd_id 1건으로 소비된다.
export const tnTreatCarRequest = mysqlTable("tn_treat_car_request", {
	tcrId: int("tcr_id", { unsigned: true }).autoincrement().primaryKey().notNull(),
	tcrAltCode: varchar("tcr_alt_code", { length: 30 }).notNull(),
	tcrOddId: int("tcr_odd_id", { unsigned: true }),
	tcrConsentVersion: varchar("tcr_consent_version", { length: 50 }).notNull(),
	tcrConsentContent: text("tcr_consent_content").notNull(),
	tcrConsentContentHash: varchar("tcr_consent_content_hash", { length: 64 }).notNull(),
	tcrAllowedAt: datetime("tcr_allowed_at", { mode: 'string'}).notNull(),
	tcrConsentedAt: datetime("tcr_consented_at", { mode: 'string'}),
	tcrConsumedAt: datetime("tcr_consumed_at", { mode: 'string'}),
	tcrRevokedAt: datetime("tcr_revoked_at", { mode: 'string'}),
	tcrCreatedAt: datetime("tcr_created_at", { mode: 'string'}).default(sql`(CURRENT_TIMESTAMP)`).notNull(),
},
(table) => {
	return {
		tnTreatCarRequestTcrId: primaryKey({ columns: [table.tcrId], name: "tn_treat_car_request_tcr_id"}),
		tcrAltCode: unique("tcr_alt_code").on(table.tcrAltCode),
		tcrOddId: unique("tcr_odd_id").on(table.tcrOddId),
	}
});

//* ★인증 이탈 클라 비콘(2026-07-01): 프론트가 인증단계에서 유저 이탈(탭닫기/전환) 시 stage+timing을
//*   sendBeacon으로 쏜 것을 적재. 서버 퍼널(엔진)이 못 보는 '유저가 언제·어디서 떠났나'를 클라 시점으로 채움.
export const tnTreatDropout = mysqlTable("tn_treat_dropout", {
	tdpId: int("tdp_id", { unsigned: true }).autoincrement().primaryKey().notNull(),
	tdpSessionId: varchar("tdp_session_id", { length: 64 }), //* certify 세션ID(서버 퍼널 조인키)
	tdpAgcCode: varchar("tdp_agc_code", { length: 32 }), //* 대리점/초대 코드
	tdpStage: varchar("tdp_stage", { length: 32 }).notNull(), //* 이탈 단계(certify_wait/sms_wait 등)
	tdpMsOnStage: int("tdp_ms_on_stage"), //* 그 단계에 머문 시간(ms)
	tdpMsSinceSms: int("tdp_ms_since_sms"), //* SMS 발송 후 경과(ms) — 미도착 vs 느림 판별
	tdpEvent: varchar("tdp_event", { length: 20 }), //* 발생 이벤트(pagehide/beforeunload/hidden-timeout)
	tdpCreatedAt: datetime("tdp_created_at", { mode: 'string'}).default(sql`(CURRENT_TIMESTAMP)`).notNull(),
},
(table) => {
	return {
		idxTdpCreated: index("idx_tdp_created").on(table.tdpCreatedAt),
		idxTdpStage: index("idx_tdp_stage").on(table.tdpStage),
	}
});

export const tnProduct = mysqlTable("tn_product", {
	prdId: int("prd_id", { unsigned: true }).autoincrement().primaryKey().notNull(),
	prdType: varchar("prd_type", { length: 10 }).notNull(),
	prdCode: varchar("prd_code", { length: 30 }).notNull(),
	prdName: varchar("prd_name", { length: 100 }).notNull(),
	prdContent: text("prd_content"),
	prdLimitedQty: int("prd_limited_qty").default(0).notNull(),
	prdConsumerPrice: int("prd_consumer_price").default(0).notNull(),
	prdSalePrice: int("prd_sale_price").default(0).notNull(),
	prdImg: varchar("prd_img", { length: 255 }),
	prdSort: int("prd_sort").default(0).notNull(),
	prdShow: tinyint("prd_show").default(1).notNull(),
	prdRecommend: int("prd_recommend").default(0).notNull(),
	prdMonthlyPoint: int("prd_monthly_point", { unsigned: true }).default(0).notNull(),
	prdCaution: text("prd_caution"),
	prdPaymentType: varchar("prd_payment_type", { length: 10 }).default('PCY001').notNull(),
	prdUseType: varchar("prd_use_type", { length: 10 }).default('PCY001').notNull(),
	prdPaymentCycle: int("prd_payment_cycle").default(1).notNull(),
	prdUseCycle: int("prd_use_cycle").default(1).notNull(),
	prdUpdatedAt: datetime("prd_updated_at", { mode: 'string'}),
	prdCreatedAt: datetime("prd_created_at", { mode: 'string'}).default(sql`(CURRENT_TIMESTAMP)`).notNull(),
},
(table) => {
	return {
		prdId: index("prd_id").on(table.prdId),
		tnProductPrdId: primaryKey({ columns: [table.prdId], name: "tn_product_prd_id"}),
		prdCode: unique("prd_code").on(table.prdCode),
	}
});

export const tnPush = mysqlTable("tn_push", {
	pshId: int("psh_id", { unsigned: true }).autoincrement().primaryKey().notNull(),
	pshTitle: varchar("psh_title", { length: 100 }).notNull(),
	pshContent: text("psh_content").notNull(),
	pshUrl: varchar("psh_url", { length: 500 }),
	pshTargetType: varchar("psh_target_type", { length: 20 }).notNull(),
	pshTargetUserIds: text("psh_target_user_ids"),
	pshScheduledAt: datetime("psh_scheduled_at", { mode: 'string'}),
	pshSentAt: datetime("psh_sent_at", { mode: 'string'}),
	pshStatus: varchar("psh_status", { length: 20 }).default('pending').notNull(),
	pshCategory: varchar("psh_category", { length: 20 }).default('event').notNull(),
	pshCreatedAt: datetime("psh_created_at", { mode: 'string'}).default(sql`(CURRENT_TIMESTAMP)`).notNull(),
	pshUpdatedAt: datetime("psh_updated_at", { mode: 'string'}),
	pshDetailContent: text("psh_detail_content"),
},
(table) => {
	return {
		tnPushPshId: primaryKey({ columns: [table.pshId], name: "tn_push_psh_id"}),
	}
});

export const tnRefund = mysqlTable("tn_refund", {
	refId: int("ref_id", { unsigned: true }).autoincrement().primaryKey().notNull(),
	ordId: int("ord_id", { unsigned: true }).notNull().references(() => tnOrder.ordId, { onDelete: "restrict", onUpdate: "cascade" } ),
	refState: varchar("ref_state", { length: 15 }).notNull(),
	refBank: varchar("ref_bank", { length: 20 }),
	refPrice: int("ref_price"),
	refAccountName: varchar("ref_account_name", { length: 10 }),
	refAccountNumber: varchar("ref_account_number", { length: 20 }),
	refMemo: varchar("ref_memo", { length: 255 }),
	refCompletedAt: datetime("ref_completed_at", { mode: 'string'}),
	refUpdatedAt: datetime("ref_updated_at", { mode: 'string'}),
	refCreatedAt: datetime("ref_created_at", { mode: 'string'}).default(sql`(CURRENT_TIMESTAMP)`).notNull(),
},
(table) => {
	return {
		tnRefundRefId: primaryKey({ columns: [table.refId], name: "tn_refund_ref_id"}),
		pmtId: unique("pmt_id").on(table.ordId),
	}
});

export const tnSalesAgency = mysqlTable("tn_sales_agency", {
	sagId: int("sag_id", { unsigned: true }).autoincrement().primaryKey().notNull(),
	sagName: varchar("sag_name", { length: 30 }).notNull(),
	sagCode: varchar("sag_code", { length: 20 }),
	sagDefault: tinyint("sag_default").default(0).notNull(),
	sagEmail: varchar("sag_email", { length: 128 }),
	sagManager: varchar("sag_manager", { length: 128 }),
	sagReceive: tinyint("sag_receive").notNull(),
	sagLoginId: varchar("sag_login_id", { length: 20 }),
	sagPassword: varchar("sag_password", { length: 100 }),
	sagUpdatedAt: datetime("sag_updated_at", { mode: 'string'}),
	sagCreatedAt: datetime("sag_created_at", { mode: 'string'}).default(sql`(CURRENT_TIMESTAMP)`).notNull(),
},
(table) => {
	return {
		tnSalesAgencySagId: primaryKey({ columns: [table.sagId], name: "tn_sales_agency_sag_id"}),
		sagCode: unique("sag_code").on(table.sagCode),
		sagLoginId: unique("sag_login_id").on(table.sagLoginId),
	}
});

export const tnSalesAgencyChannel = mysqlTable("tn_sales_agency_channel", {
	sacId: int("sac_id", { unsigned: true }).autoincrement().primaryKey().notNull(),
	sagId: int("sag_id", { unsigned: true }).notNull().references(() => tnSalesAgency.sagId, { onDelete: "restrict", onUpdate: "cascade" } ),
	sacCode: varchar("sac_code", { length: 20 }).notNull(),
	sacName: varchar("sac_name", { length: 30 }).notNull(),
	sacUpdatedAt: datetime("sac_updated_at", { mode: 'string'}),
	sacCreatedAt: datetime("sac_created_at", { mode: 'string'}).default(sql`(CURRENT_TIMESTAMP)`),
},
(table) => {
	return {
		tnSalesAgencyChannelSacId: primaryKey({ columns: [table.sacId], name: "tn_sales_agency_channel_sac_id"}),
		sacCode: unique("sac_code").on(table.sacCode),
	}
});

//* 영업비 수익 계단의 차감 항목(0032). 값은 효력 시작 후 불변 — 종료 또는 대체로만 바꾼다.
//* 겹침·잔여 연속성은 DB 제약이 아니라 sales-commission/deduction-rules.ts 검증기가 정본이다.
export const tnSalesCommissionDeduction = mysqlTable("tn_sales_commission_deduction", {
	scdId: int("scd_id", { unsigned: true }).autoincrement().primaryKey().notNull(),
	//* 수취인: HQ(보험유니버스) · CHANNEL(채널담당자) · AGENCY(영업대리점)
	scdRecipient: varchar("scd_recipient", { length: 16 }).notNull(),
	//* 산정방식: FLAT(건당 정액) · RATE(공급가액 정률) · RESIDUAL(잔여)
	scdMethod: varchar("scd_method", { length: 16 }).notNull(),
	//* FLAT 일 때만 — 원
	scdAmount: int("scd_amount"),
	//* RATE 일 때만 — 백만분율(0~1,000,000)
	scdRatePpm: int("scd_rate_ppm"),
	//* 적용범위: PRODUCT(prd_code) · CHANNEL(sac_code) · ALL · CORPORATE(agc_corporate_code)
	scdScopeType: varchar("scd_scope_type", { length: 16 }).notNull(),
	scdScopeCode: varchar("scd_scope_code", { length: 30 }),
	//* 반열린 구간 [valid_from, valid_to), valid_to NULL = 무기한
	scdValidFrom: date("scd_valid_from", { mode: 'string' }).notNull(),
	scdValidTo: date("scd_valid_to", { mode: 'string' }),
	scdCreatedBy: int("scd_created_by", { unsigned: true }).notNull(),
	scdClosedBy: int("scd_closed_by", { unsigned: true }),
	scdCreatedAt: datetime("scd_created_at", { mode: 'string'}).default(sql`(CURRENT_TIMESTAMP)`).notNull(),
	scdUpdatedAt: datetime("scd_updated_at", { mode: 'string'}),
},
(table) => {
	return {
		tnSalesCommissionDeductionScdId: primaryKey({ columns: [table.scdId], name: "tn_sales_commission_deduction_scd_id"}),
		scope: index("idx_sales_commission_deduction_scope").on(table.scdRecipient, table.scdScopeCode, table.scdValidFrom),
	}
});

export const tnSubscribe = mysqlTable("tn_subscribe", {
	subId: int("sub_id", { unsigned: true }).autoincrement().primaryKey().notNull(),
	memId: int("mem_id", { unsigned: true }).references(() => tnMember.memId, { onDelete: "set null", onUpdate: "cascade" } ),
	prdId: int("prd_id", { unsigned: true }).notNull().references(() => tnProduct.prdId, { onDelete: "restrict", onUpdate: "cascade" } ),
	subState: varchar("sub_state", { length: 15 }).notNull(),
	subNumber: varchar("sub_number", { length: 30 }).notNull(),
	// you can use { mode: 'date' }, if you want to have Date as type for this column
	subNextPayDay: date("sub_next_pay_day", { mode: 'string' }).notNull(),
	subDisabledAt: datetime("sub_disabled_at", { mode: 'string'}),
	subChangedAt: datetime("sub_changed_at", { mode: 'string'}),
	subChangeCanceledAt: datetime("sub_change_canceled_at", { mode: 'string'}),
	subDisableCompletedAt: datetime("sub_disable_completed_at", { mode: 'string'}),
	subChangeCompletedAt: datetime("sub_change_completed_at", { mode: 'string'}),
	subUpdatedAt: datetime("sub_updated_at", { mode: 'string'}),
	subCreatedAt: datetime("sub_created_at", { mode: 'string'}).default(sql`(CURRENT_TIMESTAMP)`).notNull(),
},
(table) => {
	return {
		subState: index("sub_state").on(table.subState, table.subNextPayDay),
		tnSubscribeSubId: primaryKey({ columns: [table.subId], name: "tn_subscribe_sub_id"}),
		subNumber: unique("sub_number").on(table.subNumber),
	}
});

export const tnSubscribeFailure = mysqlTable("tn_subscribe_failure", {
	sbfId: int("sbf_id", { unsigned: true }).autoincrement().primaryKey().notNull(),
	subId: int("sub_id", { unsigned: true }).notNull(),
	sbfReason: varchar("sbf_reason", { length: 255 }),
	sbfCreatedAt: datetime("sbf_created_at", { mode: 'string'}).default(sql`(CURRENT_TIMESTAMP)`),
},
(table) => {
	return {
		tnSubscribeFailureSbfId: primaryKey({ columns: [table.sbfId], name: "tn_subscribe_failure_sbf_id"}),
	}
});

export const tnTerms = mysqlTable("tn_terms", {
	temId: int("tem_id").notNull(),
	temType: varchar("tem_type", { length: 15 }).notNull(),
	temContent: text("tem_content"),
	temCreatedAt: datetime("tem_created_at", { mode: 'string'}).default(sql`(CURRENT_TIMESTAMP)`).notNull(),
	temUpdatedAt: datetime("tem_updated_at", { mode: 'string'}),
},
(table) => {
	return {
		tnTermsTemId: primaryKey({ columns: [table.temId], name: "tn_terms_tem_id"}),
		temType: unique("uniq_tem_type").on(table.temType),
	}
});

export const tnAgencyTerms = mysqlTable("tn_agency_terms", {
	agtId: int("agt_id", { unsigned: true }).autoincrement().primaryKey().notNull(),
	agcId: int("agc_id", { unsigned: true }).notNull().references(() => tnAgency.agcId, { onDelete: "cascade", onUpdate: "cascade" } ),
	agtType: varchar("agt_type", { length: 15 }).notNull(),
	agtTitle: varchar("agt_title", { length: 255 }).notNull(),
	agtContent: text("agt_content"),
	agtRequired: tinyint("agt_required").default(0).notNull(),
	agtSort: int("agt_sort").default(0).notNull(),
	agtEnabled: tinyint("agt_enabled").default(1).notNull(),
	agtCreatedAt: datetime("agt_created_at", { mode: 'string'}).default(sql`(CURRENT_TIMESTAMP)`).notNull(),
	agtUpdatedAt: datetime("agt_updated_at", { mode: 'string'}),
},
(table) => {
	return {
		tnAgencyTermsAgtId: primaryKey({ columns: [table.agtId], name: "tn_agency_terms_agt_id"}),
		agcIdAgtType: unique("uniq_agc_id_agt_type").on(table.agcId, table.agtType),
	}
});

export const tnReferralBenefit = mysqlTable("tn_referral_benefit", {
	rfbId: int("rfb_id", { unsigned: true }).autoincrement().primaryKey().notNull(),
	rfbEnabled: varchar("rfb_enabled", { length: 1 }).default("N").notNull(),
	rfbReferrerPoint: int("rfb_referrer_point").default(0).notNull(),
	rfbRefereePoint: int("rfb_referee_point").default(0).notNull(),
	rfbExpireEnabled: varchar("rfb_expire_enabled", { length: 1 }).default("N").notNull(),
	rfbExpireDays: int("rfb_expire_days").default(0).notNull(),
	rfbUpdatedAt: datetime("rfb_updated_at", { mode: 'string'}),
	rfbCreatedAt: datetime("rfb_created_at", { mode: 'string'}).default(sql`(CURRENT_TIMESTAMP)`).notNull(),
},
(table) => {
	return {
		tnReferralBenefitRfbId: primaryKey({ columns: [table.rfbId], name: "tn_referral_benefit_rfb_id"}),
	}
});

export const tnUser = mysqlTable("tn_user", {
	usrId: int("usr_id", { unsigned: true }).autoincrement().primaryKey().notNull(),
	memId: int("mem_id", { unsigned: true }),
	usrName: varchar("usr_name", { length: 128 }).notNull(),
	usrPhone: varchar("usr_phone", { length: 128 }).notNull(),
	usrBirth: varchar("usr_birth", { length: 128 }).notNull(),
	usrUpdatedAt: datetime("usr_updated_at", { mode: 'string'}),
	usrCreatedAt: datetime("usr_created_at", { mode: 'string'}).default(sql`(CURRENT_TIMESTAMP)`).notNull(),
},
(table) => {
	return {
		tnUserUsrId: primaryKey({ columns: [table.usrId], name: "tn_user_usr_id"}),
		memId: unique("mem_id").on(table.memId, table.usrName, table.usrPhone, table.usrBirth),
	}
});

export const ttClientTreatBasic = mysqlTable("tt_client_treat_basic", {
	ctrbId: int("ctrb_id", { unsigned: true }).autoincrement().primaryKey().notNull(),
	codId: int("cod_id", { unsigned: true }).notNull(),
	// you can use { mode: 'date' }, if you want to have Date as type for this column
	ctrbTreatStartDate: date("ctrb_treat_start_date", { mode: 'string' }),
	ctrbHospitalName: varchar("ctrb_hospital_name", { length: 50 }),
	ctrbDepartment: varchar("ctrb_department", { length: 20 }),
	ctrbTreatType: varchar("ctrb_treat_type", { length: 10 }),
	ctrbDiseaseCode: varchar("ctrb_disease_code", { length: 10 }),
	ctrbDiseaseName: varchar("ctrb_disease_name", { length: 255 }),
	ctrbVisitDays: int("ctrb_visit_days"),
	ctrbTotalAmount: int("ctrb_total_amount"),
	ctrbPublicCharge: int("ctrb_public_charge"),
	ctrbDeductibleAmt: int("ctrb_deductible_amt"),
	ctrbHospitalCode: varchar("ctrb_hospital_code", { length: 10 }),
	ctrbEtc: varchar("ctrb_etc", { length: 100 }),
	ctrbUpdatedAt: datetime("ctrb_updated_at", { mode: 'string'}),
	ctrbCreatedAt: datetime("ctrb_created_at", { mode: 'string'}).default(sql`(CURRENT_TIMESTAMP)`).notNull(),
},
(table) => {
	return {
		ttTreatBasicOddIdIdx: index("tt_treat_basic_odd_id_IDX").on(table.codId, table.ctrbTreatStartDate, table.ctrbHospitalName),
		ttClientTreatBasicCtrbId: primaryKey({ columns: [table.ctrbId], name: "tt_client_treat_basic_ctrb_id"}),
	}
});

export const ttClientTreatCarBasic = mysqlTable("tt_client_treat_car_basic", {
	ctcbId: int("ctcb_id", { unsigned: true }).autoincrement().primaryKey().notNull(),
	codId: int("cod_id", { unsigned: true }).notNull(),
	// you can use { mode: 'date' }, if you want to have Date as type for this column
	ctcbTreatStartDate: date("ctcb_treat_start_date", { mode: 'string' }),
	ctcbHospitalName: varchar("ctcb_hospital_name", { length: 50 }),
	ctcbDepartment: varchar("ctcb_department", { length: 20 }),
	ctcbTreatType: varchar("ctcb_treat_type", { length: 10 }),
	ctcbDiseaseCode: varchar("ctcb_disease_code", { length: 10 }),
	ctcbDiseaseName: varchar("ctcb_disease_name", { length: 255 }),
	ctcbTreatDate: int("ctcb_treat_date"),
	ctcbTotalAmount: int("ctcb_total_amount"),
	ctcbMedicalFee: int("ctcb_medical_fee"),
	ctcbUpdatedAt: datetime("ctcb_updated_at", { mode: 'string'}),
	ctcbCreatedAt: datetime("ctcb_created_at", { mode: 'string'}).default(sql`(CURRENT_TIMESTAMP)`).notNull(),
},
(table) => {
	return {
		oddId: index("odd_id").on(table.codId),
		tcbId: index("tcb_id").on(table.ctcbId),
		ttClientTreatCarBasicCtcbId: primaryKey({ columns: [table.ctcbId], name: "tt_client_treat_car_basic_ctcb_id"}),
	}
});

export const ttClientTreatCarDetail = mysqlTable("tt_client_treat_car_detail", {
	ctcdId: int("ctcd_id", { unsigned: true }).autoincrement().primaryKey().notNull(),
	codId: int("cod_Id", { unsigned: true }).notNull(),
	// you can use { mode: 'date' }, if you want to have Date as type for this column
	ctcdTreatStartDate: date("ctcd_treat_start_date", { mode: 'string' }),
	ctcdHospitalName: varchar("ctcd_hospital_name", { length: 50 }),
	ctcdTreatType: varchar("ctcd_treat_type", { length: 50 }),
	ctcdCodeName: varchar("ctcd_code_name", { length: 255 }),
	ctcdOneDose: int("ctcd_one_dose"),
	ctcdDailyDosesNumber: int("ctcd_daily_doses_number"),
	ctcdTotalDosingDays: int("ctcd_total_dosing_days"),
	ctcdUpdatedAt: datetime("ctcd_updated_at", { mode: 'string'}),
	ctcdCreatedAt: datetime("ctcd_created_at", { mode: 'string'}).default(sql`(CURRENT_TIMESTAMP)`).notNull(),
},
(table) => {
	return {
		oddId: index("odd_id").on(table.codId),
		tcdId: index("tcd_id").on(table.ctcdId),
		ttClientTreatCarDetailCtcdId: primaryKey({ columns: [table.ctcdId], name: "tt_client_treat_car_detail_ctcd_id"}),
	}
});

export const ttClientTreatDetail = mysqlTable("tt_client_treat_detail", {
	ctrdId: int("ctrd_id", { unsigned: true }).autoincrement().primaryKey().notNull(),
	codId: int("cod_id", { unsigned: true }).notNull(),
	// you can use { mode: 'date' }, if you want to have Date as type for this column
	ctrdTreatStartDate: date("ctrd_treat_start_date", { mode: 'string' }),
	ctrdHospitalName: varchar("ctrd_hospital_name", { length: 50 }),
	ctrdTreatType: varchar("ctrd_treat_type", { length: 50 }),
	ctrdCodeName: varchar("ctrd_code_name", { length: 255 }),
	ctrdOneDose: int("ctrd_one_dose"),
	ctrdDailyDosesNumber: int("ctrd_daily_doses_number"),
	ctrdTotalDosingDays: int("ctrd_total_dosing_days"),
	ctrdUpdatedAt: datetime("ctrd_updated_at", { mode: 'string'}),
	ctrdCreatedAt: datetime("ctrd_created_at", { mode: 'string'}).default(sql`(CURRENT_TIMESTAMP)`),
},
(table) => {
	return {
		ttTreatDetailOddIdIdx: index("tt_treat_detail_odd_id_IDX").on(table.codId, table.ctrdTreatStartDate, table.ctrdHospitalName),
		ttClientTreatDetailCtrdId: primaryKey({ columns: [table.ctrdId], name: "tt_client_treat_detail_ctrd_id"}),
	}
});

export const ttClientTreatPrescribe = mysqlTable("tt_client_treat_prescribe", {
	ctrpId: int("ctrp_id", { unsigned: true }).autoincrement().primaryKey().notNull(),
	codId: int("cod_id"),
	// you can use { mode: 'date' }, if you want to have Date as type for this column
	ctrpTreatStartDate: date("ctrp_treat_start_date", { mode: 'string' }),
	ctrpHospitalName: varchar("ctrp_hospital_name", { length: 50 }),
	ctrpTreatType: varchar("ctrp_treat_type", { length: 10 }),
	ctrpDrugName: varchar("ctrp_drug_name", { length: 255 }),
	ctrpIngredients: varchar("ctrp_ingredients", { length: 255 }),
	ctrpOneDose: int("ctrp_one_dose"),
	ctrpDailyDosesNumber: int("ctrp_daily_doses_number"),
	ctrpTotalDosingDays: int("ctrp_total_dosing_days"),
	ctrpUpdaedAt: datetime("ctrp_updaed_at", { mode: 'string'}),
	ctrpCreatedAt: datetime("ctrp_created_at", { mode: 'string'}).default(sql`(CURRENT_TIMESTAMP)`).notNull(),
},
(table) => {
	return {
		ttTreatPrescribeOddIdIdx: index("tt_treat_prescribe_odd_id_IDX").on(table.codId, table.ctrpTreatStartDate),
		ttClientTreatPrescribeCtrpId: primaryKey({ columns: [table.ctrpId], name: "tt_client_treat_prescribe_ctrp_id"}),
	}
});

export const ttCompareBasic = mysqlTable("tt_compare_basic", {
	cpbId: int("cpb_id", { unsigned: true }).autoincrement().primaryKey().notNull(),
	cpbType: varchar("cpb_type", { length: 10 }).notNull(),
	cpbDiseaseCode: varchar("cpb_disease_code", { length: 10 }).notNull(),
	cpbName: varchar("cpb_name", { length: 255 }).notNull(),
	cpbViewName: text("cpb_view_name"),
	cpbIsSicked: tinyint("cpb_is_sicked").default(0).notNull(),
	cpbUpdatedAt: datetime("cpb_updated_at", { mode: 'string'}),
	cpbCreatedAt: datetime("cpb_created_at", { mode: 'string'}).default(sql`(CURRENT_TIMESTAMP)`).notNull(),
},
(table) => {
	return {
		ttCompareBasicCpbId: primaryKey({ columns: [table.cpbId], name: "tt_compare_basic_cpb_id"}),
		tcCompareBasicCpbTypeIdx: unique("tc_compare_basic_cpb_type_IDX").on(table.cpbType, table.cpbDiseaseCode),
	}
});

export const ttCompareDetail = mysqlTable("tt_compare_detail", {
	cpdId: int("cpd_id", { unsigned: true }).autoincrement().primaryKey().notNull(),
	cpdType: varchar("cpd_type", { length: 10 }).notNull(),
	cpdName: varchar("cpd_name", { length: 255 }).notNull(),
	cpdViewName: text("cpd_view_name"),
	cpdUpdatedAt: datetime("cpd_updated_at", { mode: 'string'}),
	cpdCreatedAt: datetime("cpd_created_at", { mode: 'string'}).default(sql`(CURRENT_TIMESTAMP)`).notNull(),
},
(table) => {
	return {
		tcCompareDetailCpdNameIdx: index("tc_compare_detail_cpd_name_IDX").on(table.cpdName),
		tcCompareDetailCpdTypeIdx: index("tc_compare_detail_cpd_type_IDX").on(table.cpdType),
		ttCompareDetailCpdId: primaryKey({ columns: [table.cpdId], name: "tt_compare_detail_cpd_id"}),
	}
});

export const ttSubscribeReservation = mysqlTable("tt_subscribe_reservation", {
	surId: int("sur_id", { unsigned: true }).autoincrement().primaryKey().notNull(),
	subId: int("sub_id").notNull(),
	prdId: int("prd_id").notNull(),
	surUpdatedAt: datetime("sur_updated_at", { mode: 'string'}),
	surCreatedAt: datetime("sur_created_at", { mode: 'string'}).default(sql`(CURRENT_TIMESTAMP)`).notNull(),
},
(table) => {
	return {
		ttSubscribeReservationSurId: primaryKey({ columns: [table.surId], name: "tt_subscribe_reservation_sur_id"}),
	}
});

export const ttTreatBasic = mysqlTable("tt_treat_basic", {
	trbId: int("trb_id", { unsigned: true }).autoincrement().primaryKey().notNull(),
	oddId: int("odd_id", { unsigned: true }).notNull(),
	// you can use { mode: 'date' }, if you want to have Date as type for this column
	trbTreatStartDate: date("trb_treat_start_date", { mode: 'string' }),
	trbHospitalName: varchar("trb_hospital_name", { length: 50 }),
	trbDepartment: varchar("trb_department", { length: 20 }),
	trbTreatType: varchar("trb_treat_type", { length: 10 }),
	trbDiseaseCode: varchar("trb_disease_code", { length: 10 }),
	trbDiseaseName: varchar("trb_disease_name", { length: 255 }),
	trbVisitDays: int("trb_visit_days"),
	trbTotalAmount: int("trb_total_amount"),
	trbPublicCharge: int("trb_public_charge"),
	trbDeductibleAmt: int("trb_deductible_amt"),
	trbHospitalCode: varchar("trb_hospital_code", { length: 10 }),
	trbEtc: varchar("trb_etc", { length: 100 }),
	trbUpdatedAt: datetime("trb_updated_at", { mode: 'string'}),
	trbCreatedAt: datetime("trb_created_at", { mode: 'string'}).default(sql`(CURRENT_TIMESTAMP)`).notNull(),
},
(table) => {
	return {
		oddIdIdx: index("tt_treat_basic_odd_id_IDX").on(table.oddId, table.trbTreatStartDate, table.trbHospitalName),
		ttTreatBasicTrbId: primaryKey({ columns: [table.trbId], name: "tt_treat_basic_trb_id"}),
	}
});

export const ttTreatCarBasic = mysqlTable("tt_treat_car_basic", {
	tcbId: int("tcb_id", { unsigned: true }).autoincrement().primaryKey().notNull(),
	oddId: int("odd_id", { unsigned: true }).notNull(),
	// you can use { mode: 'date' }, if you want to have Date as type for this column
	tcbTreatStartDate: date("tcb_treat_start_date", { mode: 'string' }),
	tcbHospitalName: varchar("tcb_hospital_name", { length: 50 }),
	tcbDepartment: varchar("tcb_department", { length: 20 }),
	tcbTreatType: varchar("tcb_treat_type", { length: 10 }),
	tcbDiseaseCode: varchar("tcb_disease_code", { length: 10 }),
	tcbDiseaseName: varchar("tcb_disease_name", { length: 255 }),
	tcbTreatDate: int("tcb_treat_date"),
	tcbTotalAmount: int("tcb_total_amount"),
	tcbMedicalFee: int("tcb_medical_fee"),
	tcbUpdatedAt: datetime("tcb_updated_at", { mode: 'string'}),
	tcbCreatedAt: datetime("tcb_created_at", { mode: 'string'}).default(sql`(CURRENT_TIMESTAMP)`).notNull(),
},
(table) => {
	return {
		oddId: index("odd_id").on(table.oddId),
		tcbId: index("tcb_id").on(table.tcbId),
		ttTreatCarBasicTcbId: primaryKey({ columns: [table.tcbId], name: "tt_treat_car_basic_tcb_id"}),
	}
});

export const ttTreatCarDetail = mysqlTable("tt_treat_car_detail", {
	tcdId: int("tcd_id", { unsigned: true }).autoincrement().primaryKey().notNull(),
	oddId: int("odd_Id", { unsigned: true }).notNull(),
	// you can use { mode: 'date' }, if you want to have Date as type for this column
	tcdTreatStartDate: date("tcd_treat_start_date", { mode: 'string' }),
	tcdHospitalName: varchar("tcd_hospital_name", { length: 50 }),
	tcdTreatType: varchar("tcd_treat_type", { length: 50 }),
	tcdCodeName: varchar("tcd_code_name", { length: 255 }),
	tcdOneDose: int("tcd_one_dose"),
	tcdDailyDosesNumber: int("tcd_daily_doses_number"),
	tcdTotalDosingDays: int("tcd_total_dosing_days"),
	tcdUpdatedAt: datetime("tcd_updated_at", { mode: 'string'}),
	tcdCreatedAt: datetime("tcd_created_at", { mode: 'string'}).default(sql`(CURRENT_TIMESTAMP)`).notNull(),
},
(table) => {
	return {
		oddId: index("odd_id").on(table.oddId),
		tcdId: index("tcd_id").on(table.tcdId),
		ttTreatCarDetailTcdId: primaryKey({ columns: [table.tcdId], name: "tt_treat_car_detail_tcd_id"}),
	}
});

export const ttTreatDetail = mysqlTable("tt_treat_detail", {
	trdId: int("trd_id", { unsigned: true }).autoincrement().primaryKey().notNull(),
	oddId: int("odd_id", { unsigned: true }).notNull(),
	// you can use { mode: 'date' }, if you want to have Date as type for this column
	trdTreatStartDate: date("trd_treat_start_date", { mode: 'string' }),
	trdHospitalName: varchar("trd_hospital_name", { length: 50 }),
	trdTreatType: varchar("trd_treat_type", { length: 50 }),
	trdCodeName: varchar("trd_code_name", { length: 255 }),
	trdOneDose: int("trd_one_dose"),
	trdDailyDosesNumber: int("trd_daily_doses_number"),
	trdTotalDosingDays: int("trd_total_dosing_days"),
	trdUpdatedAt: datetime("trd_updated_at", { mode: 'string'}),
	trdCreatedAt: datetime("trd_created_at", { mode: 'string'}).default(sql`(CURRENT_TIMESTAMP)`),
},
(table) => {
	return {
		oddIdIdx: index("tt_treat_detail_odd_id_IDX").on(table.oddId, table.trdTreatStartDate, table.trdHospitalName),
		ttTreatDetailTrdId: primaryKey({ columns: [table.trdId], name: "tt_treat_detail_trd_id"}),
	}
});

export const ttTreatPrescribe = mysqlTable("tt_treat_prescribe", {
	trpId: int("trp_id", { unsigned: true }).autoincrement().primaryKey().notNull(),
	oddId: int("odd_id"),
	// you can use { mode: 'date' }, if you want to have Date as type for this column
	trpTreatStartDate: date("trp_treat_start_date", { mode: 'string' }),
	trpHospitalName: varchar("trp_hospital_name", { length: 50 }),
	trpTreatType: varchar("trp_treat_type", { length: 10 }),
	trpDrugName: varchar("trp_drug_name", { length: 255 }),
	trpIngredients: varchar("trp_ingredients", { length: 255 }),
	trpOneDose: int("trp_one_dose"),
	trpDailyDosesNumber: int("trp_daily_doses_number"),
	trpTotalDosingDays: int("trp_total_dosing_days"),
	trpUpdaedAt: datetime("trp_updaed_at", { mode: 'string'}),
	trpCreatedAt: datetime("trp_created_at", { mode: 'string'}).default(sql`(CURRENT_TIMESTAMP)`).notNull(),
},
(table) => {
	return {
		oddIdIdx: index("tt_treat_prescribe_odd_id_IDX").on(table.oddId, table.trpTreatStartDate),
		ttTreatPrescribeTrpId: primaryKey({ columns: [table.trpId], name: "tt_treat_prescribe_trp_id"}),
	}
});

//* 심평원 '내가 먹는약 한눈에' API 응답 임시 저장 테이블 (정회원)
export const ttTreatMedicineSummary = mysqlTable("tt_treat_medicine_summary", {
	tmsId: int("tms_id", { unsigned: true }).autoincrement().primaryKey().notNull(),
	oddId: int("odd_id", { unsigned: true }).notNull(),
	//* 조제일자
	tmsDispenseDate: date("tms_dispense_date", { mode: 'string' }),
	//* 처방기관(병원명)
	tmsPrescribingHospital: varchar("tms_prescribing_hospital", { length: 50 }),
	//* 조제기관(약국명)
	tmsDispensingPharmacy: varchar("tms_dispensing_pharmacy", { length: 50 }),
	//* 처방기관 코드
	tmsPrescribingHospitalCode: varchar("tms_prescribing_hospital_code", { length: 10 }),
	//* 조제기관 코드
	tmsDispensingPharmacyCode: varchar("tms_dispensing_pharmacy_code", { length: 10 }),
	//* 약품명
	tmsDrugName: varchar("tms_drug_name", { length: 255 }),
	//* 총 투약일수
	tmsTotalDosingDays: int("tms_total_dosing_days"),
	tmsUpdatedAt: datetime("tms_updated_at", { mode: 'string'}),
	tmsCreatedAt: datetime("tms_created_at", { mode: 'string'}).default(sql`(CURRENT_TIMESTAMP)`).notNull(),
},
(table) => {
	return {
		oddIdIdx: index("tt_treat_medicine_summary_odd_id_IDX").on(table.oddId, table.tmsDispenseDate),
		ttTreatMedicineSummaryTmsId: primaryKey({ columns: [table.tmsId], name: "tt_treat_medicine_summary_tms_id"}),
	}
});

// 추천보험관리 백업 테이블 (임시 테이블)
export const ttDiseaseMajor = mysqlTable("tt_disease_major", {
	dsmMajorCode: varchar("dsm_major_code", { length: 10 }).notNull(),
	dsmMajorName: varchar("dsm_major_name", { length: 200 }).notNull(),
	dsmInsuranceComment: varchar("dsm_insurance_comment", { length: 200 }),
	dsmRegDate: timestamp("dsm_reg_date", { mode: 'string' }),
	dsmUpdDate: timestamp("dsm_upd_date", { mode: 'string' }),
},
(table) => {
	return {
		ttDiseaseMajorDsmMajorCode: primaryKey({ columns: [table.dsmMajorCode], name: "tt_disease_major_dsm_major_code"}),
	}
});

export const ttDiseaseMiddle = mysqlTable("tt_disease_middle", {
	dsdMajorCode: varchar("dsd_major_code", { length: 10 }).notNull(),
	dsdMiddleCode: varchar("dsd_middle_code", { length: 10 }).notNull(),
	dsdMiddleName: varchar("dsd_middle_name", { length: 200 }).notNull(),
	dsdInsuranceComment: varchar("dsd_insurance_comment", { length: 200 }),
	dsdRegDate: timestamp("dsd_reg_date", { mode: 'string' }),
	dsdUpdDate: timestamp("dsd_upd_date", { mode: 'string' }),
},
(table) => {
	return {
		ttDiseaseMiddleDsdMajorCodeDsdMiddleCode: primaryKey({ columns: [table.dsdMajorCode, table.dsdMiddleCode], name: "tt_disease_middle_dsd_major_code_dsd_middle_code"}),
	}
});

export const ttDiseaseMinor = mysqlTable("tt_disease_minor", {
	dsnMajorCode: varchar("dsn_major_code", { length: 10 }).notNull(),
	dsnMiddleCode: varchar("dsn_middle_code", { length: 10 }).notNull(),
	dsnMinorCode: varchar("dsn_minor_code", { length: 10 }).notNull(),
	dsnMinorName: varchar("dsn_minor_name", { length: 200 }).notNull(),
	dsnInsuranceComment: varchar("dsn_insurance_comment", { length: 200 }),
	dsnRegDate: timestamp("dsn_reg_date", { mode: 'string' }),
	dsnUpdDate: timestamp("dsn_upd_date", { mode: 'string' }),
},
(table) => {
	return {
		ttDiseaseMinorDsnMajorCodeDsnMiddleCodeDsnMinorCode: primaryKey({ columns: [table.dsnMajorCode, table.dsnMiddleCode, table.dsnMinorCode], name: "tt_disease_minor_dsn_major_code_dsn_middle_code_dsn_minor_code"}),
	}
});

export const ttDiseaseDetail = mysqlTable("tt_disease_detail", {
	ddtMajorCode: varchar("ddt_major_code", { length: 10 }).notNull(),
	ddtMiddleCode: varchar("ddt_middle_code", { length: 10 }).notNull(),
	ddtMinorCode: varchar("ddt_minor_code", { length: 10 }).notNull(),
	ddtDetailCode: varchar("ddt_detail_code", { length: 10 }).notNull(),
	ddtDetailName: varchar("ddt_detail_name", { length: 200 }).notNull(),
	ddtInsuranceComment: varchar("ddt_insurance_comment", { length: 200 }),
	ddtRegDate: timestamp("ddt_reg_date", { mode: 'string' }),
	ddtUpdDate: timestamp("ddt_upd_date", { mode: 'string' }),
},
(table) => {
	return {
		ttDiseaseDetailDdtMajorCodeDdtMiddleCodeDdtMinorCodeDdtDetailCode: primaryKey({ columns: [table.ddtMajorCode, table.ddtMiddleCode, table.ddtMinorCode, table.ddtDetailCode], name: "tt_disease_detail_ddt_major_code_ddt_middle_code_ddt_minor_code_ddt_detail_code"}),
	}
});

export const ttDiseaseFineClassification = mysqlTable("tt_disease_fine_classification", {
	dfcMajorCode: varchar("dfc_major_code", { length: 10 }).notNull(),
	dfcMiddleCode: varchar("dfc_middle_code", { length: 10 }).notNull(),
	dfcMinorCode: varchar("dfc_minor_code", { length: 10 }).notNull(),
	dfcDetailCode: varchar("dfc_detail_code", { length: 10 }).notNull(),
	dfcFineCode: varchar("dfc_fine_code", { length: 10 }).notNull(),
	dfcFineName: varchar("dfc_fine_name", { length: 200 }).notNull(),
	dfcInsuranceComment: varchar("dfc_insurance_comment", { length: 200 }),
	dfcRegDate: timestamp("dfc_reg_date", { mode: 'string' }),
	dfcUpdDate: timestamp("dfc_upd_date", { mode: 'string' }),
},
(table) => {
	return {
		ttDiseaseFineClassificationPk: primaryKey({ columns: [table.dfcMajorCode, table.dfcMiddleCode, table.dfcMinorCode, table.dfcDetailCode, table.dfcFineCode], name: "tt_disease_fine_classification_pk"}),
	}
});

export const ttDiseaseSubFineClassification = mysqlTable("tt_disease_sub_fine_classification", {
	dsfMajorCode: varchar("dsf_major_code", { length: 10 }).notNull(),
	dsfMiddleCode: varchar("dsf_middle_code", { length: 10 }).notNull(),
	dsfMinorCode: varchar("dsf_minor_code", { length: 10 }).notNull(),
	dsfDetailCode: varchar("dsf_detail_code", { length: 10 }).notNull(),
	dsfFineCode: varchar("dsf_fine_code", { length: 10 }).notNull(),
	dsfSubFineCode: varchar("dsf_sub_fine_code", { length: 10 }).notNull(),
	dsfSubFineName: varchar("dsf_sub_fine_name", { length: 200 }).notNull(),
	dsfInsuranceComment: varchar("dsf_insurance_comment", { length: 200 }),
	dsfRegDate: timestamp("dsf_reg_date", { mode: 'string' }),
	dsfUpdDate: timestamp("dsf_upd_date", { mode: 'string' }),
},
(table) => {
	return {
		ttDiseaseSubFineClassificationPk: primaryKey({ columns: [table.dsfMajorCode, table.dsfMiddleCode, table.dsfMinorCode, table.dsfDetailCode, table.dsfFineCode, table.dsfSubFineCode], name: "tt_disease_sub_fine_classification_pk"}),
	}
});

// 투약기준관리 - 대분류 (Category)
export const tcMedicationCategory = mysqlTable("tc_medication_category", {
	mcId: int("mc_id").autoincrement().notNull(),
	mcName: varchar("mc_name", { length: 255 }).notNull(),
	mcCreatedAt: timestamp("mc_created_at", { mode: 'string' }).defaultNow(),
},
(table) => {
	return {
		idxMcName: index("idx_mc_name").on(table.mcName),
		tcMedicationCategoryMcId: primaryKey({ columns: [table.mcId], name: "tc_medication_category_mc_id"}),
	}
});

// 투약기준관리 - 중분류 (Standard)
export const tcMedicationStandard = mysqlTable("tc_medication_standard", {
	mscId: int("msc_id").autoincrement().notNull(),
	mscCategoryId: int("msc_category_id").notNull().references(() => tcMedicationCategory.mcId, { onDelete: "cascade", onUpdate: "cascade" }),
	mscCode: varchar("msc_code", { length: 500 }).notNull(),
	mscName: varchar("msc_name", { length: 500 }).notNull(),
	mscCreatedAt: timestamp("msc_created_at", { mode: 'string' }).defaultNow(),
	mscUpdatedAt: timestamp("msc_updated_at", { mode: 'string' }).defaultNow().onUpdateNow(),
},
(table) => {
	return {
		idxMscCategoryId: index("idx_msc_category_id").on(table.mscCategoryId),
		idxMscCode: index("idx_msc_code").on(table.mscCode),
		idxMscName: index("idx_msc_name").on(table.mscName),
		tcMedicationStandardMscId: primaryKey({ columns: [table.mscId], name: "tc_medication_standard_msc_id"}),
	}
});

// 투약기준관리 백업 테이블 - 대분류
export const ttMedicationCategory = mysqlTable("tt_medication_category", {
	mcId: int("mc_id").notNull(),
	mcName: varchar("mc_name", { length: 255 }).notNull(),
	mcCreatedAt: timestamp("mc_created_at", { mode: 'string' }),
},
(table) => {
	return {
		ttMedicationCategoryMcId: primaryKey({ columns: [table.mcId], name: "tt_medication_category_mc_id"}),
	}
});

// 투약기준관리 백업 테이블 - 중분류
export const ttMedicationStandard = mysqlTable("tt_medication_standard", {
	mscId: int("msc_id").notNull(),
	mscCategoryId: int("msc_category_id").notNull(),
	mscCode: varchar("msc_code", { length: 500 }).notNull(),
	mscName: varchar("msc_name", { length: 500 }).notNull(),
	mscCreatedAt: timestamp("msc_created_at", { mode: 'string' }),
	mscUpdatedAt: timestamp("msc_updated_at", { mode: 'string' }),
},
(table) => {
	return {
		ttMedicationStandardMscId: primaryKey({ columns: [table.mscId], name: "tt_medication_standard_msc_id"}),
	}
});

// ========================================
// B2C 전용 테이블 스키마
// ========================================

export const tnB2cUser = mysqlTable("tn_b2c_user", {
	bcuId: int("bcu_id", { unsigned: true }).autoincrement().primaryKey().notNull(),
	bcuName: varchar("bcu_name", { length: 128 }).notNull(), // 암호화된 이름
	bcuPhone: varchar("bcu_phone", { length: 128 }).notNull(), // 암호화된 전화번호
	bcuBirth: varchar("bcu_birth", { length: 128 }).notNull(), // 암호화된 생년월일
	bcuCreatedAt: datetime("bcu_created_at", { mode: 'string'}).default(sql`(CURRENT_TIMESTAMP)`).notNull(),
	bcuUpdatedAt: datetime("bcu_updated_at", { mode: 'string'}),
},
(table) => {
	return {
		ukBcuPhone: unique("uk_bcu_phone").on(table.bcuPhone),
		tnB2cUserBcuId: primaryKey({ columns: [table.bcuId], name: "tn_b2c_user_bcu_id"}),
	}
});

export const tnB2cOrderDetail = mysqlTable("tn_b2c_order_detail", {
	bodId: int("bod_id", { unsigned: true }).autoincrement().primaryKey().notNull(),
	bcuId: int("bcu_id", { unsigned: true }).references(() => tnB2cUser.bcuId, { onDelete: "restrict", onUpdate: "restrict" } ),
	bodAgcCode: varchar("bod_agc_code", { length: 30 }),
	bodTransactionId: varchar("bod_transaction_id", { length: 30 }).notNull(),
	bodState: varchar("bod_state", { length: 10 }),
	bodCompletedAt: varchar("bod_completed_at", { length: 255 }),
	bodFailedAt: varchar("bod_failed_at", { length: 255 }),
	bodConsultRequested: tinyint("bod_consult_requested").default(0).notNull(),
	bodMarketingAgree: tinyint("bod_marketing_agree").default(0).notNull(),
	bodExposed: tinyint("bod_exposed").default(0).notNull(),
	bodAssignedStatus: tinyint("bod_assigned_status").default(0).notNull(),
	bodAssignedMemberId: varchar("bod_assigned_member_id", { length: 50 }),
	bodAssignedDate: datetime("bod_assigned_date", { mode: 'string'}),
	bodCreatedAt: datetime("bod_created_at", { mode: 'string'}).default(sql`(CURRENT_TIMESTAMP)`).notNull(),
	bodUpdatedAt: datetime("bod_updated_at", { mode: 'string'}),
},
(table) => {
	return {
		idxBodAgcCode: index("idx_bod_agc_code").on(table.bodAgcCode),
		idxBodTransactionId: index("idx_bod_transaction_id").on(table.bodTransactionId),
		idxBodState: index("idx_bod_state").on(table.bodState),
		tnB2cOrderDetailBodId: primaryKey({ columns: [table.bodId], name: "tn_b2c_order_detail_bod_id"}),
	}
});

export const logB2cTreat = mysqlTable("log_b2c_treat", {
	lbtId: int("lbt_id", { unsigned: true }).autoincrement().primaryKey().notNull(),
	lbtBodId: int("lbt_bod_id", { unsigned: true }).notNull(),
	lbtBcuName: varchar("lbt_bcu_name", { length: 128 }).notNull(),
	lbtBcuPhone: varchar("lbt_bcu_phone", { length: 128 }).notNull(),
	lbtBcuBirth: varchar("lbt_bcu_birth", { length: 128 }).notNull(),
	lbtAgcId: int("lbt_agc_id"),
	lbtAgcCorporateName: varchar("lbt_agc_corporate_name", { length: 30 }),
	lbtBodTransactionId: varchar("lbt_bod_transaction_id", { length: 30 }).notNull(),
	lbtCodefRequestType: varchar("lbt_codef_request_type", { length: 10 }).notNull(),
	lbtCodefInitiatedBy: varchar("lbt_codef_initiated_by", { length: 10 }).notNull(),
	lbtCodefRequestStage: varchar("lbt_codef_request_stage", { length: 10 }).notNull(),
	lbtCodefCertType: varchar("lbt_codef_cert_type", { length: 10 }).notNull(),
	lbtCodefResultStatus: varchar("lbt_codef_result_status", { length: 10 }).notNull(),
	lbtCodefResultCode: varchar("lbt_codef_result_code", { length: 10 }).notNull(),
	lbtCodefResultMessage: text("lbt_codef_result_message").notNull(),
	lbtCreatedAt: datetime("lbt_created_at", { mode: 'string'}).default(sql`(CURRENT_TIMESTAMP)`).notNull(),
},
(table) => {
	return {
		idxBodId: index("idx_bod_id").on(table.lbtBodId),
		idxAgcId: index("idx_agc_id").on(table.lbtAgcId),
		idxCreatedAt: index("idx_created_at").on(table.lbtCreatedAt),
		logB2cTreatLbtId: primaryKey({ columns: [table.lbtId], name: "log_b2c_treat_lbt_id"}),
	}
});

export const tnB2cAnalysisBasic = mysqlTable("tn_b2c_analysis_basic", {
	basbId: int("basb_id", { unsigned: true }).autoincrement().notNull(),
	bodId: int("bod_id", { unsigned: true }).notNull().references(() => tnB2cOrderDetail.bodId, { onDelete: "restrict", onUpdate: "restrict" } ),
	basbTreatStartDate: date("basb_treat_start_date", { mode: 'string' }).notNull(),
	basbHospitalName: varchar("basb_hospital_name", { length: 50 }).notNull(),
	basbDepartment: varchar("basb_department", { length: 20 }),
	basbTreatType: varchar("basb_treat_type", { length: 15 }).notNull(),
	basbDiseaseCode: varchar("basb_disease_code", { length: 10 }),
	basbDiseaseName: varchar("basb_disease_name", { length: 255 }),
	basbVisitDays: int("basb_visit_days").notNull().default(0),
	basbDisease: varchar("basb_disease", { length: 255 }),
	basbInDisease: text("basb_in_disease"),
	basbNotice: text("basb_notice"),
	basbDentures: varchar("basb_dentures", { length: 255 }),
	basbToothOne: varchar("basb_tooth_one", { length: 255 }),
	basbToothFive: varchar("basb_tooth_five", { length: 255 }),
	basbEtc: varchar("basb_etc", { length: 255 }),
	basbDrugNotice: varchar("basb_drug_notice", { length: 255 }),
	basbDosingDays: int("basb_dosing_days").notNull().default(0),
	basbInTooth: tinyint("basb_in_tooth").notNull().default(0),
	basbDuplicated: tinyint("basb_duplicated").notNull().default(0),
	basbSicked: tinyint("basb_sicked").notNull().default(0),
	basbDosingId: int("basb_dosing_id").notNull().default(0),
	basbUpdatedAt: datetime("basb_updated_at", { mode: 'string'}),
	basbCreatedAt: datetime("basb_created_at", { mode: 'string'}).default(sql`(CURRENT_TIMESTAMP)`).notNull(),
},
(table) => {
	return {
		tnB2cAnalysisBasicPk: primaryKey({ columns: [table.basbId, table.bodId], name: "PRIMARY"}),
		idxBasbId: index("asb_id").on(table.basbId),
	}
});

export const tnB2cAnalysisDetail = mysqlTable("tn_b2c_analysis_detail", {
	basdId: int("basd_id", { unsigned: true }).autoincrement().notNull(),
	basbId: int("basb_id", { unsigned: true }).notNull().references(() => tnB2cAnalysisBasic.basbId, { onDelete: "restrict", onUpdate: "cascade" } ),
	bodId: int("bod_id", { unsigned: true }).notNull().references(() => tnB2cOrderDetail.bodId, { onDelete: "restrict", onUpdate: "cascade" } ),
	basdTreatStartDate: date("basd_treat_start_date", { mode: 'string' }).notNull(),
	basdHospitalName: varchar("basd_hospital_name", { length: 50 }).notNull(),
	basdCodeName: varchar("basd_code_name", { length: 255 }),
	basdOperation: varchar("basd_operation", { length: 255 }),
	basdDrug: varchar("basd_drug", { length: 255 }),
	basdDrugNotice: varchar("basd_drug_notice", { length: 255 }),
	basdExamination: varchar("basd_examination", { length: 255 }),
	basdVisitDays: int("basd_visit_days").notNull().default(0),
	basdDosingDays: int("basd_dosing_days").notNull().default(0),
	basdDosingId: int("basd_dosing_id").notNull().default(0),
	basdInTooth: text("basd_in_tooth"),
	basdInOperation: text("basd_in_operation"),
	basdInEtc: text("basd_in_etc"),
	basdDentures: varchar("basd_dentures", { length: 255 }),
	basdToothOne: varchar("basd_tooth_one", { length: 255 }),
	basdToothFive: varchar("basd_tooth_five", { length: 255 }),
	basdUpdatedAt: datetime("basd_updaed_at", { mode: 'string'}),
	basdCreatedAt: datetime("basd_created_at", { mode: 'string'}).default(sql`(CURRENT_TIMESTAMP)`).notNull(),
},
(table) => {
	return {
		tnB2cAnalysisDetailPk: primaryKey({ columns: [table.basdId, table.basbId, table.bodId], name: "PRIMARY"}),
		idxBasbId: index("asb_id").on(table.basbId),
	}
});

export const tnB2cAnalysisPrescribe = mysqlTable("tn_b2c_analysis_prescribe", {
	baspId: int("basp_id", { unsigned: true }).autoincrement().primaryKey().notNull(),
	basbId: int("basb_id", { unsigned: true }).notNull(),
	bodId: int("bod_id", { unsigned: true }).notNull(),
	baspTreatStartDate: date("basp_treat_start_date", { mode: 'string' }).notNull(),
	baspHospitalName: varchar("basp_hospital_name", { length: 50 }).notNull(),
	baspTreatType: varchar("basp_treat_type", { length: 10 }).notNull(),
	baspDrugName: varchar("basp_drug_name", { length: 255 }),
	baspIngredients: varchar("basp_ingredients", { length: 255 }),
	baspOneDose: int("basp_one_dose").notNull().default(0),
	baspDailyDosesNumber: int("basp_daily_doses_number").notNull().default(0),
	baspTotalDosingDays: int("basp_total_dosing_days").notNull().default(0),
	baspUpdatedAt: datetime("basp_updaed_at", { mode: 'string'}),
	baspCreatedAt: datetime("basp_created_at", { mode: 'string'}).default(sql`(CURRENT_TIMESTAMP)`).notNull(),
},
(table) => {
	return {
		idxBaspBodDate: index("idx_basp_bod_date").on(table.bodId, table.baspTreatStartDate),
	}
});

export const tnB2cAnalysisCarBasic = mysqlTable("tn_b2c_analysis_car_basic", {
	bacbId: int("bacb_id", { unsigned: true }).autoincrement().notNull(),
	bodId: int("bod_id", { unsigned: true }).notNull().references(() => tnB2cOrderDetail.bodId, { onDelete: "restrict", onUpdate: "restrict" } ),
	bacbTreatStartDate: date("bacb_treat_start_date", { mode: 'string' }).notNull(),
	bacbTreatEndDate: date("bacb_treat_end_date", { mode: 'string' }).notNull(),
	bacbTotalTreatDate: int("bacb_total_treat_date").notNull(),
	bacbTotalAmount: int("bacb_total_amount").notNull(),
	bacbTotalMedicalFee: int("bacb_total_medical_fee"),
	bacbOutpatientTotalAmount: int("bacb_outpatient_total_amount").notNull(),
	bacbInpatientTotalAmount: int("bacb_inpatient_total_amount").notNull(),
	bacbOutpatientMedicalFee: int("bacb_outpatient_medical_fee").notNull(),
	bacbInpatientMedicalFee: int("bacb_inpatient_medical_fee").notNull(),
	bacbOutpatientTreatDate: int("bacb_outpatient_treat_date").notNull(),
	bacbInpatientTreatDate: int("bacb_inpatient_treat_date").notNull(),
	bacbUpdatedAt: datetime("bacb_updated_at", { mode: 'string'}),
	bacbCreatedAt: datetime("bacb_created_at", { mode: 'string'}).default(sql`(CURRENT_TIMESTAMP)`).notNull(),
},
(table) => {
	return {
		tnB2cAnalysisCarBasicPk: primaryKey({ columns: [table.bacbId, table.bodId], name: "PRIMARY"}),
		idxBacbId: index("acb_id").on(table.bacbId),
	}
});

export const tnB2cAnalysisCarDetail = mysqlTable("tn_b2c_analysis_car_detail", {
	bacdId: int("bacd_id", { unsigned: true }).autoincrement().notNull(),
	bacbId: int("bacb_id", { unsigned: true }).notNull().references(() => tnB2cAnalysisCarBasic.bacbId, { onDelete: "restrict", onUpdate: "cascade" } ),
	bodId: int("bod_id", { unsigned: true }).notNull().references(() => tnB2cOrderDetail.bodId, { onDelete: "restrict", onUpdate: "cascade" } ),
	bacdTreatStartDate: date("bacd_treat_start_date", { mode: 'string' }).notNull(),
	bacdHospitalName: varchar("bacd_hospital_name", { length: 50 }).notNull(),
	bacdDepartment: varchar("bacd_department", { length: 20 }),
	bacdTreatType: varchar("bacd_treat_type", { length: 15 }).notNull(),
	bacdDiseaseCode: varchar("bacd_disease_code", { length: 10 }),
	bacdDiseaseName: varchar("bacd_disease_name", { length: 255 }),
	bacdTreatDate: int("bacd_treat_date").notNull(),
	bacdTotalAmount: int("bacd_total_amount").notNull(),
	bacdMedicalFee: int("bacd_medical_fee").notNull(),
	bacdUpdatedAt: datetime("bacd_updated_at", { mode: 'string'}),
	bacdCreatedAt: datetime("bacd_created_at", { mode: 'string'}).default(sql`(CURRENT_TIMESTAMP)`).notNull(),
},
(table) => {
	return {
		tnB2cAnalysisCarDetailPk: primaryKey({ columns: [table.bacdId, table.bacbId, table.bodId], name: "PRIMARY"}),
		idxBacdId: index("acd_id").on(table.bacdId),
	}
});

export const ttB2cTreatBasic = mysqlTable("tt_b2c_treat_basic", {
	btrbId: int("btrb_id", { unsigned: true }).autoincrement().primaryKey().notNull(),
	bodId: int("bod_id", { unsigned: true }).notNull(),
	btrbTreatStartDate: date("btrb_treat_start_date", { mode: 'string' }),
	btrbHospitalName: varchar("btrb_hospital_name", { length: 50 }),
	btrbDepartment: varchar("btrb_department", { length: 20 }),
	btrbTreatType: varchar("btrb_treat_type", { length: 10 }),
	btrbDiseaseCode: varchar("btrb_disease_code", { length: 10 }),
	btrbDiseaseName: varchar("btrb_disease_name", { length: 255 }),
	btrbVisitDays: int("btrb_visit_days"),
	btrbTotalAmount: int("btrb_total_amount"),
	btrbPublicCharge: int("btrb_public_charge"),
	btrbDeductibleAmt: int("btrb_deductible_amt"),
	btrbHospitalCode: varchar("btrb_hospital_code", { length: 10 }),
	btrbEtc: varchar("btrb_etc", { length: 100 }),
	btrbUpdatedAt: datetime("btrb_updated_at", { mode: 'string'}),
	btrbCreatedAt: datetime("btrb_created_at", { mode: 'string'}).default(sql`(CURRENT_TIMESTAMP)`).notNull(),
});

export const ttB2cTreatDetail = mysqlTable("tt_b2c_treat_detail", {
	btrdId: int("btrd_id", { unsigned: true }).autoincrement().primaryKey().notNull(),
	bodId: int("bod_id", { unsigned: true }).notNull(),
	btrdTreatStartDate: date("btrd_treat_start_date", { mode: 'string' }),
	btrdHospitalName: varchar("btrd_hospital_name", { length: 50 }),
	btrdTreatType: varchar("btrd_treat_type", { length: 50 }),
	btrdCodeName: varchar("btrd_code_name", { length: 255 }),
	btrdOneDose: int("btrd_one_dose"),
	btrdDailyDosesNumber: int("btrd_daily_doses_number"),
	btrdTotalDosingDays: int("btrd_total_dosing_days"),
	btrdUpdatedAt: datetime("btrd_updated_at", { mode: 'string'}),
	btrdCreatedAt: datetime("btrd_created_at", { mode: 'string'}).default(sql`(CURRENT_TIMESTAMP)`),
});

export const ttB2cTreatPrescribe = mysqlTable("tt_b2c_treat_prescribe", {
	btrpId: int("btrp_id", { unsigned: true }).autoincrement().primaryKey().notNull(),
	bodId: int("bod_id"),
	btrpTreatStartDate: date("btrp_treat_start_date", { mode: 'string' }),
	btrpHospitalName: varchar("btrp_hospital_name", { length: 50 }),
	btrpTreatType: varchar("btrp_treat_type", { length: 10 }),
	btrpDrugName: varchar("btrp_drug_name", { length: 255 }),
	btrpIngredients: varchar("btrp_ingredients", { length: 255 }),
	btrpOneDose: int("btrp_one_dose"),
	btrpDailyDosesNumber: int("btrp_daily_doses_number"),
	btrpTotalDosingDays: int("btrp_total_dosing_days"),
	btrpUpdatedAt: datetime("btrp_updaed_at", { mode: 'string'}),
	btrpCreatedAt: datetime("btrp_created_at", { mode: 'string'}).default(sql`(CURRENT_TIMESTAMP)`).notNull(),
});

export const ttB2cTreatCarBasic = mysqlTable("tt_b2c_treat_car_basic", {
	btcbId: int("btcb_id", { unsigned: true }).autoincrement().primaryKey().notNull(),
	bodId: int("bod_id", { unsigned: true }).notNull(),
	btcbTreatStartDate: date("btcb_treat_start_date", { mode: 'string' }),
	btcbHospitalName: varchar("btcb_hospital_name", { length: 50 }),
	btcbDepartment: varchar("btcb_department", { length: 20 }),
	btcbTreatType: varchar("btcb_treat_type", { length: 10 }),
	btcbDiseaseCode: varchar("btcb_disease_code", { length: 10 }),
	btcbDiseaseName: varchar("btcb_disease_name", { length: 255 }),
	btcbTreatDate: int("btcb_treat_date"),
	btcbTotalAmount: int("btcb_total_amount"),
	btcbMedicalFee: int("btcb_medical_fee"),
	btcbUpdatedAt: datetime("btcb_updated_at", { mode: 'string'}),
	btcbCreatedAt: datetime("btcb_created_at", { mode: 'string'}).default(sql`(CURRENT_TIMESTAMP)`).notNull(),
});

export const ttB2cTreatCarDetail = mysqlTable("tt_b2c_treat_car_detail", {
	btcdId: int("btcd_id", { unsigned: true }).autoincrement().primaryKey().notNull(),
	bodId: int("bod_id", { unsigned: true }).notNull(),
	btcdTreatStartDate: date("btcd_treat_start_date", { mode: 'string' }),
	btcdHospitalName: varchar("btcd_hospital_name", { length: 50 }),
	btcdTreatType: varchar("btcd_treat_type", { length: 50 }),
	btcdCodeName: varchar("btcd_code_name", { length: 255 }),
	btcdOneDose: int("btcd_one_dose"),
	btcdDailyDosesNumber: int("btcd_daily_doses_number"),
	btcdTotalDosingDays: int("btcd_total_dosing_days"),
	btcdUpdatedAt: datetime("btcd_updated_at", { mode: 'string'}),
	btcdCreatedAt: datetime("btcd_created_at", { mode: 'string'}).default(sql`(CURRENT_TIMESTAMP)`).notNull(),
});

//* 심평원 '내가 먹는약 한눈에' API 응답 임시 저장 테이블 (B2C)
export const ttB2cTreatMedicineSummary = mysqlTable("tt_b2c_treat_medicine_summary", {
	btmsId: int("btms_id", { unsigned: true }).autoincrement().primaryKey().notNull(),
	bodId: int("bod_id", { unsigned: true }).notNull(),
	btmsDispenseDate: date("btms_dispense_date", { mode: 'string' }),
	btmsPrescribingHospital: varchar("btms_prescribing_hospital", { length: 50 }),
	btmsDispensingPharmacy: varchar("btms_dispensing_pharmacy", { length: 50 }),
	btmsPrescribingHospitalCode: varchar("btms_prescribing_hospital_code", { length: 10 }),
	btmsDispensingPharmacyCode: varchar("btms_dispensing_pharmacy_code", { length: 10 }),
	btmsDrugName: varchar("btms_drug_name", { length: 255 }),
	btmsTotalDosingDays: int("btms_total_dosing_days"),
	btmsUpdatedAt: datetime("btms_updated_at", { mode: 'string'}),
	btmsCreatedAt: datetime("btms_created_at", { mode: 'string'}).default(sql`(CURRENT_TIMESTAMP)`).notNull(),
});

// ============================================================================
// 머니 시스템 테이블 (Money System Tables)
// ============================================================================

/**
 * tn_money_issue - 회원머니 적립 배치
 * 관리자가 일반/기업회원에게 머니 "적립/적립회수" 일괄 처리
 */
export const tnMoneyIssue = mysqlTable("tn_money_issue", {
	mniId: int("mni_id", { unsigned: true }).autoincrement().primaryKey().notNull(),
	admId: int("adm_id", { unsigned: true }),
	agcId: int("agc_id", { unsigned: true }),
	mniType: varchar("mni_type", { length: 20 }).notNull(),
	mniTargetType: varchar("mni_target_type", { length: 20 }).notNull(),
	mniMemberType: varchar("mni_member_type", { length: 20 }).notNull(),
	mniTitle: varchar("mni_title", { length: 100 }).notNull(),
	mniReason: varchar("mni_reason", { length: 255 }),
	mniAmount: int("mni_amount", { unsigned: true }).notNull(),
	mniMemberCount: int("mni_member_count", { unsigned: true }).default(0).notNull(),
	mniTotalAmount: int("mni_total_amount", { unsigned: true }).default(0).notNull(),
	mniHasExpiry: tinyint("mni_has_expiry").default(0).notNull(),
	mniExpiryDays: int("mni_expiry_days", { unsigned: true }),
	mniCreatedAt: datetime("mni_created_at", { mode: 'string'}).default(sql`(CURRENT_TIMESTAMP)`).notNull(),
},
(table) => {
	return {
		tnMoneyIssueMniId: primaryKey({ columns: [table.mniId], name: "tn_money_issue_mni_id"}),
		idxMniAgc: index("idx_mni_agc").on(table.agcId),
		idxMniType: index("idx_mni_type").on(table.mniType),
		idxMniCreated: index("idx_mni_created").on(table.mniCreatedAt),
	}
});

/**
 * tn_money_issue_target - 적립 대상 회원
 */
export const tnMoneyIssueTarget = mysqlTable("tn_money_issue_target", {
	mitId: int("mit_id", { unsigned: true }).autoincrement().primaryKey().notNull(),
	mniId: int("mni_id", { unsigned: true }).notNull(),
	memId: int("mem_id", { unsigned: true }).notNull(),
	mitAmount: int("mit_amount", { unsigned: true }).notNull(),
	mitCreatedAt: datetime("mit_created_at", { mode: 'string'}).default(sql`(CURRENT_TIMESTAMP)`).notNull(),
},
(table) => {
	return {
		tnMoneyIssueTargetMitId: primaryKey({ columns: [table.mitId], name: "tn_money_issue_target_mit_id"}),
		idxMitMniId: index("idx_mit_mni_id").on(table.mniId),
		idxMitMemId: index("idx_mit_mem_id").on(table.memId),
	}
});

/**
 * th_money_corp - 기업머니 이력
 * 기업의 보유머니 변동 이력
 */
export const thMoneyCorp = mysqlTable("th_money_corp", {
	mcpId: int("mcp_id", { unsigned: true }).autoincrement().primaryKey().notNull(),
	agcId: int("agc_id", { unsigned: true }).notNull(),
	admId: int("adm_id", { unsigned: true }),
	mngId: int("mng_id", { unsigned: true }),
	mcpActorType: varchar("mcp_actor_type", { length: 20 }),
	mcpActorMemId: int("mcp_actor_mem_id", { unsigned: true }),
	mcpType: varchar("mcp_type", { length: 20 }).notNull(),
	mcpTitle: varchar("mcp_title", { length: 100 }).notNull(),
	mcpReason: varchar("mcp_reason", { length: 255 }),
	mcpAmount: int("mcp_amount").notNull(),
	mcpBalance: int("mcp_balance", { unsigned: true }).notNull(),
	mcpCreatedAt: datetime("mcp_created_at", { mode: 'string'}).default(sql`(CURRENT_TIMESTAMP)`).notNull(),
},
(table) => {
	return {
		thMoneyCorpMcpId: primaryKey({ columns: [table.mcpId], name: "th_money_corp_mcp_id"}),
		idxMcpAgcId: index("idx_mcp_agc_id").on(table.agcId),
		idxMcpMngId: index("idx_mcp_mng_id").on(table.mngId),
		idxMcpActorMemId: index("idx_mcp_actor_mem_id").on(table.mcpActorMemId),
		idxMcpCreated: index("idx_mcp_created").on(table.mcpCreatedAt),
	}
});

/**
 * tn_money_charge_request - 기업머니 충전요청
 * 기업관리자가 충전 요청하고 서비스 관리자가 승인/반려한다.
 */
export const tnMoneyChargeRequest = mysqlTable("tn_money_charge_request", {
	mcrId: int("mcr_id", { unsigned: true }).autoincrement().primaryKey().notNull(),
	agcId: int("agc_id", { unsigned: true }).notNull(),
	requestMemId: int("request_mem_id", { unsigned: true }),
	approvedAdmId: int("approved_adm_id", { unsigned: true }),
	mcrStatus: varchar("mcr_status", { length: 20 }).default("REQUESTED").notNull(),
	mcrPaymentMethod: varchar("mcr_payment_method", { length: 20 }).default("MANUAL").notNull(),
	mcrTitle: varchar("mcr_title", { length: 100 }).notNull(),
	mcrReason: varchar("mcr_reason", { length: 255 }),
	mcrAmount: int("mcr_amount", { unsigned: true }).notNull(),
	mcrAdminMemo: varchar("mcr_admin_memo", { length: 255 }),
	mcrRejectedReason: varchar("mcr_rejected_reason", { length: 255 }),
	mcrApprovedAt: datetime("mcr_approved_at", { mode: 'string'}),
	mcrRejectedAt: datetime("mcr_rejected_at", { mode: 'string'}),
	mcrCanceledAt: datetime("mcr_canceled_at", { mode: 'string'}),
	mcrCreatedAt: datetime("mcr_created_at", { mode: 'string'}).default(sql`(CURRENT_TIMESTAMP)`).notNull(),
	mcrUpdatedAt: datetime("mcr_updated_at", { mode: 'string'}),
},
(table) => {
	return {
		tnMoneyChargeRequestMcrId: primaryKey({ columns: [table.mcrId], name: "tn_money_charge_request_mcr_id"}),
		idxMcrAgcId: index("idx_mcr_agc_id").on(table.agcId),
		idxMcrStatus: index("idx_mcr_status").on(table.mcrStatus),
		idxMcrCreated: index("idx_mcr_created").on(table.mcrCreatedAt),
	}
});

/**
 * tn_money_grant - 기업회원 지급 배치
 * 기업머니에서 기업회원에게 "지급/지급회수"
 */
export const tnMoneyGrant = mysqlTable("tn_money_grant", {
	mngId: int("mng_id", { unsigned: true }).autoincrement().primaryKey().notNull(),
	agcId: int("agc_id", { unsigned: true }).notNull(),
	admId: int("adm_id", { unsigned: true }),
	mngActorType: varchar("mng_actor_type", { length: 20 }),
	mngActorMemId: int("mng_actor_mem_id", { unsigned: true }),
	mngType: varchar("mng_type", { length: 20 }).notNull(),
	mngTargetType: varchar("mng_target_type", { length: 20 }).notNull(),
	mngTitle: varchar("mng_title", { length: 100 }).notNull(),
	mngReason: varchar("mng_reason", { length: 255 }),
	mngAmount: int("mng_amount", { unsigned: true }).notNull(),
	mngMemberCount: int("mng_member_count", { unsigned: true }).default(0).notNull(),
	mngTotalAmount: int("mng_total_amount", { unsigned: true }).default(0).notNull(),
	mngHasExpiry: tinyint("mng_has_expiry").default(0).notNull(),
	mngExpiryDays: int("mng_expiry_days", { unsigned: true }),
	mngCreatedAt: datetime("mng_created_at", { mode: 'string'}).default(sql`(CURRENT_TIMESTAMP)`).notNull(),
},
(table) => {
	return {
		tnMoneyGrantMngId: primaryKey({ columns: [table.mngId], name: "tn_money_grant_mng_id"}),
		idxMngAgcId: index("idx_mng_agc_id").on(table.agcId),
		idxMngActorMemId: index("idx_mng_actor_mem_id").on(table.mngActorMemId),
		idxMngType: index("idx_mng_type").on(table.mngType),
		idxMngCreated: index("idx_mng_created").on(table.mngCreatedAt),
	}
});

/**
 * tn_money_grant_target - 지급 대상 회원
 */
export const tnMoneyGrantTarget = mysqlTable("tn_money_grant_target", {
	mgtId: int("mgt_id", { unsigned: true }).autoincrement().primaryKey().notNull(),
	mngId: int("mng_id", { unsigned: true }).notNull(),
	memId: int("mem_id", { unsigned: true }).notNull(),
	mgtAmount: int("mgt_amount", { unsigned: true }).notNull(),
	mgtCreatedAt: datetime("mgt_created_at", { mode: 'string'}).default(sql`(CURRENT_TIMESTAMP)`).notNull(),
},
(table) => {
	return {
		tnMoneyGrantTargetMgtId: primaryKey({ columns: [table.mgtId], name: "tn_money_grant_target_mgt_id"}),
		idxMgtMngId: index("idx_mgt_mng_id").on(table.mngId),
		idxMgtMemId: index("idx_mgt_mem_id").on(table.memId),
	}
});

/**
 * tn_money_payment - 결제 정보
 */
export const tnMoneyPayment = mysqlTable("tn_money_payment", {
	mpyId: int("mpy_id", { unsigned: true }).autoincrement().primaryKey().notNull(),
	memId: int("mem_id", { unsigned: true }).notNull(),
	mpyOrderNumber: varchar("mpy_order_number", { length: 50 }).notNull(),
	mpyTid: varchar("mpy_tid", { length: 100 }),
	mpyAmount: int("mpy_amount", { unsigned: true }).notNull(),
	mpyMoney: int("mpy_money", { unsigned: true }).notNull(),
	mpyStatus: varchar("mpy_status", { length: 20 }).default('COMPLETED').notNull(),
	mpyCardType: varchar("mpy_card_type", { length: 20 }),
	mpyCardName: varchar("mpy_card_name", { length: 50 }),
	mpyCardNumber: varchar("mpy_card_number", { length: 30 }),
	mpyCanceledAmount: int("mpy_canceled_amount", { unsigned: true }).default(0).notNull(),
	mpyCancelCount: int("mpy_cancel_count", { unsigned: true }).default(0).notNull(),
	mpyApprovedAt: datetime("mpy_approved_at", { mode: 'string'}),
	mpyCanceledAt: datetime("mpy_canceled_at", { mode: 'string'}),
	mpyCreatedAt: datetime("mpy_created_at", { mode: 'string'}).default(sql`(CURRENT_TIMESTAMP)`).notNull(),
	mpyUpdatedAt: datetime("mpy_updated_at", { mode: 'string'}),
},
(table) => {
	return {
		tnMoneyPaymentMpyId: primaryKey({ columns: [table.mpyId], name: "tn_money_payment_mpy_id"}),
		idxMpyMemId: index("idx_mpy_mem_id").on(table.memId),
		idxMpyStatus: index("idx_mpy_status").on(table.mpyStatus),
		idxMpyCreated: index("idx_mpy_created").on(table.mpyCreatedAt),
		mpyOrderNumber: unique("mpy_order_number").on(table.mpyOrderNumber),
	}
});

/**
 * th_money_payment_cancel - 결제취소 이력
 */
export const thMoneyPaymentCancel = mysqlTable("th_money_payment_cancel", {
	mpcId: int("mpc_id", { unsigned: true }).autoincrement().primaryKey().notNull(),
	mpyId: int("mpy_id", { unsigned: true }).notNull(),
	admId: int("adm_id", { unsigned: true }),
	mpcType: varchar("mpc_type", { length: 20 }).notNull(),
	mpcAmount: int("mpc_amount", { unsigned: true }).notNull(),
	mpcReason: varchar("mpc_reason", { length: 255 }),
	mpcSequence: int("mpc_sequence", { unsigned: true }).default(1).notNull(),
	mpcCreatedAt: datetime("mpc_created_at", { mode: 'string'}).default(sql`(CURRENT_TIMESTAMP)`).notNull(),
},
(table) => {
	return {
		thMoneyPaymentCancelMpcId: primaryKey({ columns: [table.mpcId], name: "th_money_payment_cancel_mpc_id"}),
		idxMpcMpyId: index("idx_mpc_mpy_id").on(table.mpyId),
	}
});

/**
 * tn_money_refund - 환불 관리
 */
export const tnMoneyRefund = mysqlTable("tn_money_refund", {
	mrfId: int("mrf_id", { unsigned: true }).autoincrement().primaryKey().notNull(),
	memId: int("mem_id", { unsigned: true }).notNull(),
	mwlId: int("mwl_id", { unsigned: true }),
	admId: int("adm_id", { unsigned: true }),
	mrfStatus: varchar("mrf_status", { length: 20 }).default('PENDING').notNull(),
	mrfAmount: int("mrf_amount", { unsigned: true }).notNull(),
	mrfFee: int("mrf_fee", { unsigned: true }).default(0).notNull(),
	mrfActualAmount: int("mrf_actual_amount", { unsigned: true }).notNull(),
	mrfBankName: varchar("mrf_bank_name", { length: 50 }).notNull(),
	mrfAccountNumber: varchar("mrf_account_number", { length: 100 }).notNull(),
	mrfAccountHolder: varchar("mrf_account_holder", { length: 50 }).notNull(),
	mrfReason: varchar("mrf_reason", { length: 500 }).notNull(),
	mrfAdminMemo: varchar("mrf_admin_memo", { length: 500 }),
	mrfProcessedAt: datetime("mrf_processed_at", { mode: 'string'}),
	mrfCreatedAt: datetime("mrf_created_at", { mode: 'string'}).default(sql`(CURRENT_TIMESTAMP)`).notNull(),
},
(table) => {
	return {
		tnMoneyRefundMrfId: primaryKey({ columns: [table.mrfId], name: "tn_money_refund_mrf_id"}),
		idxMrfMemId: index("idx_mrf_mem_id").on(table.memId),
		idxMrfStatus: index("idx_mrf_status").on(table.mrfStatus),
		idxMrfCreated: index("idx_mrf_created").on(table.mrfCreatedAt),
	}
});

/**
 * th_money_wallet - 유저 머니 이력
 * 사용자가 보는 단순 이력 (1건 = 1이력)
 */
export const thMoneyWallet = mysqlTable("th_money_wallet", {
	mwlId: int("mwl_id", { unsigned: true }).autoincrement().primaryKey().notNull(),
	memId: int("mem_id", { unsigned: true }).notNull(),
	mwlType: varchar("mwl_type", { length: 20 }).notNull(),
	mwlAmount: int("mwl_amount").notNull(),
	mwlBalance: int("mwl_balance", { unsigned: true }).notNull(),
	mwlDescription: varchar("mwl_description", { length: 255 }),
	mwlCreatedAt: datetime("mwl_created_at", { mode: 'string'}).default(sql`(CURRENT_TIMESTAMP)`).notNull(),
},
(table) => {
	return {
		thMoneyWalletMwlId: primaryKey({ columns: [table.mwlId], name: "th_money_wallet_mwl_id"}),
		idxMwlMemId: index("idx_mwl_mem_id").on(table.memId),
		idxMwlType: index("idx_mwl_type").on(table.mwlType),
		idxMwlCreated: index("idx_mwl_created").on(table.mwlCreatedAt),
	}
});

/**
 * tn_money_source - FIFO 원천
 * 충전/적립/지급 건별 잔액 추적
 */
export const tnMoneySource = mysqlTable("tn_money_source", {
	msrId: int("msr_id", { unsigned: true }).autoincrement().primaryKey().notNull(),
	memId: int("mem_id", { unsigned: true }).notNull(),
	mwlId: int("mwl_id", { unsigned: true }).notNull(),
	msrType: varchar("msr_type", { length: 20 }).notNull(),
	msrMoneyType: varchar("msr_money_type", { length: 20 }).notNull(),
	msrOriginalAmount: int("msr_original_amount", { unsigned: true }).notNull(),
	msrRemainingAmount: int("msr_remaining_amount", { unsigned: true }).notNull(),
	mniId: int("mni_id", { unsigned: true }),
	mngId: int("mng_id", { unsigned: true }),
	mpyId: int("mpy_id", { unsigned: true }),
	msrExpiredAt: datetime("msr_expired_at", { mode: 'string'}),
	msrCreatedAt: datetime("msr_created_at", { mode: 'string'}).default(sql`(CURRENT_TIMESTAMP)`).notNull(),
},
(table) => {
	return {
		tnMoneySourceMsrId: primaryKey({ columns: [table.msrId], name: "tn_money_source_msr_id"}),
		idxMsrMemId: index("idx_msr_mem_id").on(table.memId),
		idxMsrMwlId: index("idx_msr_mwl_id").on(table.mwlId),
		idxMsrRemaining: index("idx_msr_remaining").on(table.msrRemainingAmount),
		idxMsrExpired: index("idx_msr_expired").on(table.msrExpiredAt),
		idxMsrFifo: index("idx_msr_fifo").on(table.memId, table.msrRemainingAmount, table.msrType, table.msrExpiredAt, table.msrCreatedAt),
	}
});

/**
 * th_money_usage - 사용 상세
 * source 잔액 변동 기록 (FIFO 추적)
 */
export const thMoneyUsage = mysqlTable("th_money_usage", {
	musId: int("mus_id", { unsigned: true }).autoincrement().primaryKey().notNull(),
	mwlId: int("mwl_id", { unsigned: true }).notNull(),
	msrId: int("msr_id", { unsigned: true }).notNull(),
	musType: varchar("mus_type", { length: 20 }).notNull(),
	musAmount: int("mus_amount", { unsigned: true }).notNull(),
	musCreatedAt: datetime("mus_created_at", { mode: 'string'}).default(sql`(CURRENT_TIMESTAMP)`).notNull(),
},
(table) => {
	return {
		thMoneyUsageMusId: primaryKey({ columns: [table.musId], name: "th_money_usage_mus_id"}),
		idxMusMwlId: index("idx_mus_mwl_id").on(table.mwlId),
		idxMusMsrId: index("idx_mus_msr_id").on(table.msrId),
	}
});

export const tnLossAnalysis = mysqlTable("tn_loss_analysis", {
	lsaId: int("lsa_id", { unsigned: true }).autoincrement().primaryKey().notNull(),
	memId: int("mem_id", { unsigned: true }).notNull().references(() => tnMember.memId, { onDelete: "restrict", onUpdate: "cascade" }),
	ordId: int("ord_id", { unsigned: true }).notNull().references(() => tnOrder.ordId, { onDelete: "restrict", onUpdate: "cascade" }),
	altId: int("alt_id", { unsigned: true }).notNull().references(() => tnAlimtalk.altId, { onDelete: "restrict", onUpdate: "cascade" }),
	usrId: int("usr_id", { unsigned: true }).references(() => tnUser.usrId, { onDelete: "set null", onUpdate: "cascade" }),
	lsaState: varchar("lsa_state", { length: 20 }).notNull(),
	lsaProvider: varchar("lsa_provider", { length: 30 }),
	lsaCarrier: varchar("lsa_carrier", { length: 1 }),
	lsaSessionId: varchar("lsa_session_id", { length: 64 }),
	lsaAvailableYears: json("lsa_available_years"),
	lsaStartYear: int("lsa_start_year", { unsigned: true }),
	lsaEndYear: int("lsa_end_year", { unsigned: true }),
	lsaTotalRows: int("lsa_total_rows", { unsigned: true }),
	lsaResult: json("lsa_result"),
	lsaErrorCode: varchar("lsa_error_code", { length: 64 }),
	lsaErrorMessage: varchar("lsa_error_message", { length: 500 }),
	lsaCompletedAt: datetime("lsa_completed_at", { mode: 'string'}),
	lsaUpdatedAt: datetime("lsa_updated_at", { mode: 'string'}),
	lsaCreatedAt: datetime("lsa_created_at", { mode: 'string'}).default(sql`(CURRENT_TIMESTAMP)`).notNull(),
},
(table) => ({
	altId: unique("uq_loss_analysis_alt_id").on(table.altId),
	memberCreated: index("idx_loss_analysis_member_created").on(table.memId, table.lsaCreatedAt),
	stateCreated: index("idx_loss_analysis_state_created").on(table.lsaState, table.lsaCreatedAt),
}));

export const logLossAnalysis = mysqlTable("log_loss_analysis", {
	lslId: int("lsl_id", { unsigned: true }).autoincrement().primaryKey().notNull(),
	lsaId: int("lsa_id", { unsigned: true }).notNull().references(() => tnLossAnalysis.lsaId, { onDelete: "cascade", onUpdate: "cascade" }),
	lslStage: varchar("lsl_stage", { length: 20 }).notNull(),
	lslStatus: varchar("lsl_status", { length: 10 }).notNull(),
	lslCode: varchar("lsl_code", { length: 64 }),
	lslMessage: varchar("lsl_message", { length: 500 }),
	lslElapsedMs: int("lsl_elapsed_ms", { unsigned: true }),
	lslCreatedAt: datetime("lsl_created_at", { mode: 'string'}).default(sql`(CURRENT_TIMESTAMP)`).notNull(),
},
(table) => ({
	analysisCreated: index("idx_loss_log_analysis_created").on(table.lsaId, table.lslCreatedAt),
	created: index("idx_loss_log_created").on(table.lslCreatedAt),
}));

export const ttDdxVerdict = mysqlTable("tt_ddx_verdict", {
	ddvId: int("ddv_id", { unsigned: true }).autoincrement().primaryKey().notNull(),
	oddId: int("odd_id", { unsigned: true }).notNull().references(() => tnOrderDetail.oddId, { onUpdate: "cascade" }),
	ddvState: varchar("ddv_state", { length: 20 }).notNull(),
	ddvAnalysisId: varchar("ddv_analysis_id", { length: 64 }),
	ddvResult: json("ddv_result"),
	ddvAttempts: int("ddv_attempts", { unsigned: true }).default(0).notNull(),
	ddvErrorCode: varchar("ddv_error_code", { length: 64 }),
	ddvErrorMessage: varchar("ddv_error_message", { length: 500 }),
	ddvRequestedAt: datetime("ddv_requested_at", { mode: 'string'}),
	ddvSentAt: datetime("ddv_sent_at", { mode: 'string'}),
	ddvCompletedAt: datetime("ddv_completed_at", { mode: 'string'}),
	ddvUpdatedAt: datetime("ddv_updated_at", { mode: 'string'}),
	ddvCreatedAt: datetime("ddv_created_at", { mode: 'string'}).default(sql`(CURRENT_TIMESTAMP)`).notNull(),
},
(table) => ({
	oddId: unique("uq_ddv_odd_id").on(table.oddId),
	stateCreated: index("idx_ddv_state_created").on(table.ddvState, table.ddvCreatedAt),
}));

//* 운영 알림 웹훅 채널. 다중 채널 발송의 근거 — 채널마다 대상 알림 종류를 지정한다.
export const tnAlertChannel = mysqlTable("tn_alert_channel", {
	alcId: int("alc_id", { unsigned: true }).autoincrement().primaryKey().notNull(),
	alcName: varchar("alc_name", { length: 100 }).notNull(), //* 표시명
	alcUrl: varchar("alc_url", { length: 500 }).notNull(), //* 웹훅 URL(구글챗/슬랙 incoming webhook)
	alcTypes: text("alc_types"), //* JSON 배열. NULL/빈배열 = 전체 종류
	alcEnabled: tinyint("alc_enabled").default(1).notNull(),
	alcUpdatedAt: datetime("alc_updated_at", { mode: 'string'}),
	alcCreatedAt: datetime("alc_created_at", { mode: 'string'}).default(sql`(CURRENT_TIMESTAMP)`).notNull(),
});

//* 운영 알림 전역 설정(key-value). 억제창·지속성·폴링주기·타입 ON/OFF·전체 OFF·리스·억제 상태.
//*  tn_treat_setting 을 쓰지 않는 이유: tst_value 가 varchar(255) 라 억제 상태 JSON 이 금방 넘친다.
export const tnAlertSetting = mysqlTable("tn_alert_setting", {
	alsKey: varchar("als_key", { length: 100 }).notNull(), //* 설정 키(alert_enabled 등)
	alsValue: text("als_value").notNull(), //* 값(문자열 또는 JSON)
	alsUpdatedAt: datetime("als_updated_at", { mode: 'string'}),
	alsCreatedAt: datetime("als_created_at", { mode: 'string'}).default(sql`(CURRENT_TIMESTAMP)`).notNull(),
},
(table) => {
	return {
		tnAlertSettingAlsKey: primaryKey({ columns: [table.alsKey], name: "tn_alert_setting_als_key"}),
	}
});

//* 운영 알림 발송 이력(M3 §D1). 추가 전용 원장 — INSERT 는 경쟁이 없어 리스가 필요 없다.
//*  원문 웹훅 URL 을 담는 컬럼이 없다: URL 이 곧 발송 권한이라 행마다 복제하면 백업·덤프로
//*  자격증명이 무기한 퍼진다(R5-F1). 채널 집계는 alc_id, 표시는 마스킹 값이다.
export const tnAlertHistory = mysqlTable("tn_alert_history", {
	alhId: bigint("alh_id", { mode: 'number', unsigned: true }).autoincrement().primaryKey().notNull(),
	alhKind: varchar("alh_kind", { length: 30 }).notNull(), //* fire|recover|digest|test|fallback|fallback-recover|snooze-summary
	alhRuleId: varchar("alh_rule_id", { length: 50 }), //* 다중 규칙 다이제스트·테스트는 NULL
	alcId: int("alc_id", { unsigned: true }), //* FK 를 걸지 않는다 — 채널 삭제 후에도 이력은 남아야 한다
	alhUrlMasked: varchar("alh_url_masked", { length: 200 }).notNull(),
	alhOk: tinyint("alh_ok").notNull(),
	alhStatus: int("alh_status"),
	alhError: varchar("alh_error", { length: 255 }),
	alhText: varchar("alh_text", { length: 500 }).notNull(),
	alhCreatedAt: datetime("alh_created_at", { mode: 'string'}).default(sql`(CURRENT_TIMESTAMP)`).notNull(),
},
(table) => ({
	created: index("idx_alert_history_created").on(table.alhCreatedAt),
	channel: index("idx_alert_history_channel").on(table.alcId, table.alhCreatedAt),
}));


//* 관리자 금전행위 감사 원본(T1) — 수기 SQL `drizzle/0031_admin_audit.sql` 의 손 선언이다. 추가 전용이고 앱은 적재만 한다.
export const tnAdminAudit = mysqlTable("tn_admin_audit", {
	audId: bigint("aud_id", { mode: 'number', unsigned: true }).autoincrement().primaryKey().notNull(),
	audLineVersion: tinyint("aud_line_version", { unsigned: true }).notNull(), //* 감사 줄 형태 버전(AUDIT_LINE_VERSION) — 칸의 의미가 바뀐 전후 행을 가른다
	audActorRole: varchar("aud_actor_role", { length: 16 }).notNull(), //* ADMIN|SALES|CORP|SYSTEM|UNKNOWN — aud_actor_ref_id 의 id 공간 판별자
	audActorRefId: int("aud_actor_ref_id", { unsigned: true }), //* ADMIN=adm_id · SALES=sag_id · CORP=agc_id · SYSTEM=NULL
	audActorLabel: varchar("aud_actor_label", { length: 64 }),
	audActorOrg: varchar("aud_actor_org", { length: 255 }), //* corp ORG 부분트리. 그 외 NULL
	audActorPersonId: int("aud_actor_person_id", { unsigned: true }), //* corp ORG 뒤의 자연인(mem_id). 그 외 NULL
	audAction: varchar("aud_action", { length: 64 }).notNull(),
	audOutcome: varchar("aud_outcome", { length: 16 }).default('COMMITTED').notNull(),
	audTargetType: varchar("aud_target_type", { length: 32 }).notNull(),
	audTargetId: int("aud_target_id", { unsigned: true }),
	audAmount: bigint("aud_amount", { mode: 'number' }), //* 부호 있음 — 지급 +, 회수 -
	audTargetCount: int("aud_target_count", { unsigned: true }).default(1).notNull(),
	audChanges: text("aud_changes"), //* 허용목록 JSON. 상한 1KB, 초과분은 앱이 잘라 넣는다
	audBatch: text("aud_batch"), //* 업무 배치 식별자 JSON — changes 와 별도 칸이라 상한이 직렬로 걸리지 않는다
	audReasonCode: varchar("aud_reason_code", { length: 64 }),
	audRequestId: varchar("aud_request_id", { length: 64 }), //* pino reqId — stdout 감사 줄과 상관키
	audIp: varchar("aud_ip", { length: 45 }),
	audUserAgent: varchar("aud_user_agent", { length: 255 }),
	audCreatedAt: datetime("aud_created_at", { mode: 'string'}).default(sql`(CURRENT_TIMESTAMP)`).notNull(),
},
(table) => ({
	actor: index("idx_aud_actor").on(table.audActorRole, table.audActorRefId, table.audCreatedAt),
	target: index("idx_aud_target").on(table.audTargetType, table.audTargetId, table.audCreatedAt),
	action: index("idx_aud_action").on(table.audAction, table.audCreatedAt),
	request: index("idx_aud_request").on(table.audRequestId),
	outcome: index("idx_aud_outcome").on(table.audOutcome, table.audCreatedAt),
	actorLabel: index("idx_aud_actor_label").on(table.audActorLabel, table.audCreatedAt),
}));
