From 7ee6f401966fe143eb3b6bc39360ad55bab53e47 Mon Sep 17 00:00:00 2001 From: Khafid Prayoga Date: Tue, 25 Nov 2025 13:53:12 +0700 Subject: [PATCH 01/28] init: treatment report feat(treatment-report): add treatment report component with sample data Implement new treatment report feature including list view component, sample data, and configuration. The component supports pagination, filtering by date range, and search functionality. Also integrates with encounter process and home views. wip: init form and schema --- .../app/treatment-report/entry-form.vue | 7 ++ .../app/treatment-report/fields/index.ts | 1 + .../treatment-report/fields/select-dpjp.vue | 3 + .../app/treatment-report/list.cfg.ts | 88 ++++++++++++++++++ app/components/app/treatment-report/list.vue | 39 ++++++++ app/components/app/treatment-report/sample.ts | 54 +++++++++++ app/components/content/encounter/home.vue | 10 ++- app/components/content/encounter/process.vue | 8 ++ .../content/treatment-report/add.vue | 7 ++ .../content/treatment-report/list.vue | 73 +++++++++++++++ app/pages/(features)/treatment-report/add.vue | 45 ++++++++++ app/schemas/treatment-report.schema.ts | 89 +++++++++++++++++++ 12 files changed, 422 insertions(+), 2 deletions(-) create mode 100644 app/components/app/treatment-report/entry-form.vue create mode 100644 app/components/app/treatment-report/fields/index.ts create mode 100644 app/components/app/treatment-report/fields/select-dpjp.vue create mode 100644 app/components/app/treatment-report/list.cfg.ts create mode 100644 app/components/app/treatment-report/list.vue create mode 100644 app/components/app/treatment-report/sample.ts create mode 100644 app/components/content/treatment-report/add.vue create mode 100644 app/components/content/treatment-report/list.vue create mode 100644 app/pages/(features)/treatment-report/add.vue create mode 100644 app/schemas/treatment-report.schema.ts diff --git a/app/components/app/treatment-report/entry-form.vue b/app/components/app/treatment-report/entry-form.vue new file mode 100644 index 00000000..2a474b15 --- /dev/null +++ b/app/components/app/treatment-report/entry-form.vue @@ -0,0 +1,7 @@ + + + diff --git a/app/components/app/treatment-report/fields/index.ts b/app/components/app/treatment-report/fields/index.ts new file mode 100644 index 00000000..ab2e32e9 --- /dev/null +++ b/app/components/app/treatment-report/fields/index.ts @@ -0,0 +1 @@ +export { default as SelectDPJP } from './select-dpjp.vue' diff --git a/app/components/app/treatment-report/fields/select-dpjp.vue b/app/components/app/treatment-report/fields/select-dpjp.vue new file mode 100644 index 00000000..dae90589 --- /dev/null +++ b/app/components/app/treatment-report/fields/select-dpjp.vue @@ -0,0 +1,3 @@ + + + diff --git a/app/components/app/treatment-report/list.cfg.ts b/app/components/app/treatment-report/list.cfg.ts new file mode 100644 index 00000000..9b4c5df1 --- /dev/null +++ b/app/components/app/treatment-report/list.cfg.ts @@ -0,0 +1,88 @@ +import { defineAsyncComponent } from 'vue' + +import { format } from 'date-fns' +import { id } from 'date-fns/locale' + +import type { Config, RecComponent } from '~/components/pub/my-ui/data-table' +import type { TreatmentReportData } from '~/components/app/treatment-report/sample' +const action = defineAsyncComponent(() => import('~/components/pub/my-ui/data/dropdown-action-dud.vue')) + +export const config: Config = { + cols: [ + { width: 120 }, + { width: 120 }, + { width: 120 }, + { width: 120 }, + { width: 120 }, + { width: 120 }, + { width: 120 }, + { width: 50 }, + ], + + headers: [ + [ + { label: 'TANGGAL LAPORAN' }, + { label: 'DPJP' }, + { label: 'OPERATOR' }, + { label: 'TANGGAL PEMBEDAHAN' }, + { label: 'JENIS OPERASI' }, + { label: 'KODE BILLING' }, + { label: 'SISTEM OPERASI' }, + { label: 'AKSI' }, + ], + ], + + keys: ['reportAt', 'dpjp', 'operator', 'operationAt', 'operationType', 'billing', 'system', 'action'], + + delKeyNames: [ + { key: 'code', label: 'Kode' }, + { key: 'name', label: 'Nama' }, + ], + + parses: { + reportAt: (rec: unknown): unknown => { + const attr = (rec as TreatmentReportData).reportAt + const result = format(new Date(attr), 'd MMMM yyyy, HH:mm', { locale: id }) + + return result + }, + operationAt: (rec: unknown): unknown => { + const attr = (rec as TreatmentReportData).operationAt + const result = format(new Date(attr), 'd MMMM yyyy', { locale: id }) + + return result + }, + system: (rec: unknown): unknown => { + return 'Cito' + }, + operator: (rec: unknown): unknown => { + return 'dr. Dewi Arum Sawitri, Sp.An' + }, + billing: (rec: unknown): unknown => { + return 'General' + }, + operationType: (rec: unknown): unknown => { + return 'Besar' + }, + dpjp: (rec: unknown): unknown => { + return 'dr. Irwansyah Kurniawan Sp.Bo' + }, + parent: (rec: unknown): unknown => { + const recX = rec as any + return recX.parent?.name || '-' + }, + }, + + components: { + action(rec, idx) { + const res: RecComponent = { + idx, + rec: rec as object, + component: action, + } + return res + }, + }, + + htmls: {}, +} diff --git a/app/components/app/treatment-report/list.vue b/app/components/app/treatment-report/list.vue new file mode 100644 index 00000000..6ad7dd81 --- /dev/null +++ b/app/components/app/treatment-report/list.vue @@ -0,0 +1,39 @@ + + + diff --git a/app/components/app/treatment-report/sample.ts b/app/components/app/treatment-report/sample.ts new file mode 100644 index 00000000..9446b91c --- /dev/null +++ b/app/components/app/treatment-report/sample.ts @@ -0,0 +1,54 @@ +import { addWeeks, formatISO } from 'date-fns' + +export type TreatmentReportData = { + id: number + reportAt: string + operationAt: string + noRm: string + noBill: string + nama: string + jk: string + alamat: string + klinik: string + dokter: string + caraBayar: string + rujukan: string + ketRujukan: string + asal: string +} + +export const sampleRows: TreatmentReportData[] = [ + { + id: 1, + reportAt: formatISO(addWeeks(new Date(), -1)), + operationAt: formatISO(addWeeks(new Date(), 1)), + noRm: 'RM23311224', + noBill: '-', + nama: 'Ahmad Baidowi', + jk: 'L', + alamat: 'Jl Jaksa Agung S. No. 9', + klinik: 'Penyakit dalam', + dokter: 'Dr. Andreas Sutaji', + caraBayar: 'JKN', + rujukan: 'Faskes BPJS', + ketRujukan: 'RUMAH SAKIT - RS Lawang Medika - Malang', + asal: 'Rawat Jalan Reguler', + }, + { + id: 2, + reportAt: new Date().toISOString(), + operationAt: formatISO(addWeeks(new Date(), 2)), + noRm: 'RM23455667', + noBill: '-', + nama: 'Abraham Sulaiman', + jk: 'L', + alamat: 'Purwantoro, Blimbing', + klinik: 'Penyakit dalam', + dokter: 'Dr. Andreas Sutaji', + caraBayar: 'JKN', + rujukan: 'Faskes BPJS', + ketRujukan: 'RUMAH SAKIT - RS Lawang Medika - Malang', + asal: 'Rawat Jalan Reguler', + }, + // tambahkan lebih banyak baris contoh jika perlu +] diff --git a/app/components/content/encounter/home.vue b/app/components/content/encounter/home.vue index 1f2c2943..c9822e52 100644 --- a/app/components/content/encounter/home.vue +++ b/app/components/content/encounter/home.vue @@ -130,7 +130,6 @@ const tabsRaws: TabItem[] = [ component: MedicineProtocolList, props: { data: protocolRows, paginationMeta }, }, - { value: 'report', label: 'Laporan Tindakan', groups: ['chemotherapy'] }, { value: 'patient-note', label: 'CPRJ', groups: ['ambulatory', 'rehabilitation', 'chemotherapy'] }, { value: 'education-assessment', @@ -162,13 +161,20 @@ const tabsRaws: TabItem[] = [ { value: 'resume', label: 'Resume', groups: ['ambulatory', 'rehabilitation', 'chemotherapy'] }, { value: 'control', label: 'Surat Kontrol', groups: ['ambulatory', 'rehabilitation', 'chemotherapy'] }, { value: 'screening', label: 'Skrinning MPP', groups: ['ambulatory', 'rehabilitation', 'chemotherapy'] }, + { + value: 'report', + label: 'Laporan Tindakan', + groups: ['ambulatory', 'rehabilitation', 'chemotherapy'], + component: Consultation, + props: { encounter: data }, + }, { value: 'supporting-document', label: 'Upload Dokumen Pendukung', groups: ['ambulatory', 'rehabilitation'] }, { value: 'price-list', label: 'Tarif Tindakan', groups: ['ambulatory', 'rehabilitation', 'chemotherapy'] }, ] const tabs = computed(() => { return tabsRaws - .filter((tab: TabItem) => tab.groups ? tab.groups.some((group: string) => props.classes?.includes(group)) : true) + .filter((tab: TabItem) => (tab.groups ? tab.groups.some((group: string) => props.classes?.includes(group)) : true)) .map((tab: TabItem) => { return { ...tab, props: { ...tab.props, encounter: data } } }) diff --git a/app/components/content/encounter/process.vue b/app/components/content/encounter/process.vue index 02fc7495..43b0f55b 100644 --- a/app/components/content/encounter/process.vue +++ b/app/components/content/encounter/process.vue @@ -22,6 +22,7 @@ import CpLabOrder from '~/components/content/cp-lab-order/main.vue' import Radiology from '~/components/content/radiology-order/main.vue' import Consultation from '~/components/content/consultation/list.vue' import Cprj from '~/components/content/cprj/entry.vue' +import TreatmentReport from '~/components/content/treatment-report/list.vue' import DocUploadList from '~/components/content/document-upload/list.vue' import GeneralConsentList from '~/components/content/general-consent/entry.vue' import ResumeList from '~/components/content/resume/list.vue' @@ -90,6 +91,13 @@ const tabs: TabItem[] = [ { value: 'resume', label: 'Resume', component: ResumeList, props: { encounter: data } }, { value: 'control', label: 'Surat Kontrol', component: ControlLetterList, props: { encounter: data } }, { value: 'screening', label: 'Skrinning MPP' }, + { + value: 'report', + label: 'Laporan Tindakan', + groups: ['ambulatory', 'rehabilitation', 'chemotherapy'], + component: TreatmentReport, + props: { encounter: data }, + }, { value: 'supporting-document', label: 'Upload Dokumen Pendukung', diff --git a/app/components/content/treatment-report/add.vue b/app/components/content/treatment-report/add.vue new file mode 100644 index 00000000..c1446a5a --- /dev/null +++ b/app/components/content/treatment-report/add.vue @@ -0,0 +1,7 @@ + + + diff --git a/app/components/content/treatment-report/list.vue b/app/components/content/treatment-report/list.vue new file mode 100644 index 00000000..e6ece811 --- /dev/null +++ b/app/components/content/treatment-report/list.vue @@ -0,0 +1,73 @@ + + + diff --git a/app/pages/(features)/treatment-report/add.vue b/app/pages/(features)/treatment-report/add.vue new file mode 100644 index 00000000..b8459422 --- /dev/null +++ b/app/pages/(features)/treatment-report/add.vue @@ -0,0 +1,45 @@ + + + diff --git a/app/schemas/treatment-report.schema.ts b/app/schemas/treatment-report.schema.ts new file mode 100644 index 00000000..f9aac9a8 --- /dev/null +++ b/app/schemas/treatment-report.schema.ts @@ -0,0 +1,89 @@ +import { z } from 'zod' + +const isoDateTime = z.string().min(1, 'Tanggal / waktu wajib diisi') +const positiveInt = z.number().int().nonnegative() + +const OperatorTeamSchema = z.object({ + dpjpId: z.number().int(), + operatorId: z.number().int(), + assistantOperatorId: z.number().int().optional().nullable(), + instrumentNurseId: z.number().int().optional().nullable(), + + surgeryDate: isoDateTime, + actionDiagnosis: z.string().min(1), + + postOpNurseId: z.number().int().optional().nullable(), +}) + +const ProcedureSchema = z.object({ + id: z.number().int().optional(), + name: z.string().min(1), + code: z.string().min(1), +}) + +const OperationExecutionSchema = z.object({ + surgeryType: z.enum(['kecil', 'sedang', 'besar', 'khusus']), + billingCode: z.string().min(1), + operationSystem: z.enum(['khusus', 'cito', 'elektif']), + + operationStartAt: isoDateTime, + operationEndAt: isoDateTime, + + anesthesiaStartAt: isoDateTime, + anesthesiaEndAt: isoDateTime, + + surgeryCleanType: z.enum(['bersih', 'bersih_terkontaminasi', 'terkontaminasi', 'kotor']).optional(), + surgeryNumber: z.enum(['1', '2', '3', '4+', 'tidak_diketahui']).optional(), + + birthPlaceNote: z.string().optional(), + babyWeightGram: positiveInt.optional(), + birthCondition: z.string().optional(), + + operationDescription: z.string().min(1), + + bleedingAmountCc: positiveInt.optional(), + + birthRemark: z.enum(['lahir_hidup', 'lahir_mati', 'abortus', 'tidak_diketahui']).optional(), +}) + +const BloodComponentSchema = z.object({ + used: z.boolean().default(false), + volumeCc: positiveInt.optional(), +}) + +const BloodInputSchema = z.object({ + prc: BloodComponentSchema, + ffp: BloodComponentSchema, + wb: BloodComponentSchema, + tc: BloodComponentSchema, +}) + +const ImplantSchema = z.object({ + brand: z.string().optional(), + name: z.string().optional(), + stickerNumber: z.string().optional(), + companionName: z.string().optional(), +}) + +const SpecimenSchema = z.object({ + destination: z.string().min(1), +}) + +const TissueNoteSchema = z.object({ + note: z.string().min(1), +}) + +export const ActionReportSchema = z.object({ + operatorTeam: OperatorTeamSchema, + procedures: z.array(ProcedureSchema).min(1), + + operationExecution: OperationExecutionSchema, + + bloodInput: BloodInputSchema.optional(), + implant: ImplantSchema.optional(), + specimen: SpecimenSchema.optional(), + + tissueNotes: z.array(TissueNoteSchema).optional(), +}) + +export type ActionReportFormData = z.infer From 3fbcdf9e2aa107e01df9b2764588edfae67fdbe2 Mon Sep 17 00:00:00 2001 From: Khafid Prayoga Date: Tue, 25 Nov 2025 15:32:58 +0700 Subject: [PATCH 02/28] refactor(treatment-report): restructure treatment report form and components - Replace SelectDPJP with SelectDoctor component - Update schema naming from ActionReport to TreatmentReport - Add doctor selection functionality to treatment report form - Improve form layout and field organization - Update related model imports to use single quotes - add fragment for better form grouping - cherry pick form field from another branch --- app/components/app/doctor/fields/index.ts | 1 + .../app/doctor/fields/select-doctor.vue | 72 ++++++++ .../app/treatment-report/entry-form.vue | 161 ++++++++++++++++- .../app/treatment-report/fields/index.ts | 1 - .../treatment-report/fields/select-dpjp.vue | 3 - .../content/treatment-report/add.vue | 16 +- .../pub/my-ui/form/button-action.vue | 165 ++++++++++++++++++ app/components/pub/my-ui/form/file-field.vue | 5 +- app/components/pub/my-ui/form/fragment.vue | 26 +++ app/components/pub/my-ui/form/index.ts | 11 ++ app/components/pub/my-ui/form/input-base.vue | 75 +++++--- app/components/pub/my-ui/form/select.vue | 9 +- app/models/doctor.ts | 8 +- app/models/person.ts | 19 +- app/schemas/treatment-report.schema.ts | 6 +- 15 files changed, 532 insertions(+), 46 deletions(-) create mode 100644 app/components/app/doctor/fields/index.ts create mode 100644 app/components/app/doctor/fields/select-doctor.vue delete mode 100644 app/components/app/treatment-report/fields/index.ts delete mode 100644 app/components/app/treatment-report/fields/select-dpjp.vue create mode 100644 app/components/pub/my-ui/form/button-action.vue create mode 100644 app/components/pub/my-ui/form/fragment.vue create mode 100644 app/components/pub/my-ui/form/index.ts diff --git a/app/components/app/doctor/fields/index.ts b/app/components/app/doctor/fields/index.ts new file mode 100644 index 00000000..32d92f2f --- /dev/null +++ b/app/components/app/doctor/fields/index.ts @@ -0,0 +1 @@ +export { default as SelectDoctor } from './select-doctor.vue' diff --git a/app/components/app/doctor/fields/select-doctor.vue b/app/components/app/doctor/fields/select-doctor.vue new file mode 100644 index 00000000..daa55062 --- /dev/null +++ b/app/components/app/doctor/fields/select-doctor.vue @@ -0,0 +1,72 @@ + + + diff --git a/app/components/app/treatment-report/entry-form.vue b/app/components/app/treatment-report/entry-form.vue index 2a474b15..8cc7db1a 100644 --- a/app/components/app/treatment-report/entry-form.vue +++ b/app/components/app/treatment-report/entry-form.vue @@ -1,7 +1,164 @@ diff --git a/app/components/app/treatment-report/fields/index.ts b/app/components/app/treatment-report/fields/index.ts deleted file mode 100644 index ab2e32e9..00000000 --- a/app/components/app/treatment-report/fields/index.ts +++ /dev/null @@ -1 +0,0 @@ -export { default as SelectDPJP } from './select-dpjp.vue' diff --git a/app/components/app/treatment-report/fields/select-dpjp.vue b/app/components/app/treatment-report/fields/select-dpjp.vue deleted file mode 100644 index dae90589..00000000 --- a/app/components/app/treatment-report/fields/select-dpjp.vue +++ /dev/null @@ -1,3 +0,0 @@ - - - diff --git a/app/components/content/treatment-report/add.vue b/app/components/content/treatment-report/add.vue index c1446a5a..6789238e 100644 --- a/app/components/content/treatment-report/add.vue +++ b/app/components/content/treatment-report/add.vue @@ -1,7 +1,21 @@ diff --git a/app/components/pub/my-ui/form/button-action.vue b/app/components/pub/my-ui/form/button-action.vue new file mode 100644 index 00000000..a1054948 --- /dev/null +++ b/app/components/pub/my-ui/form/button-action.vue @@ -0,0 +1,165 @@ + + + diff --git a/app/components/pub/my-ui/form/file-field.vue b/app/components/pub/my-ui/form/file-field.vue index 31885a6f..332d2e88 100644 --- a/app/components/pub/my-ui/form/file-field.vue +++ b/app/components/pub/my-ui/form/file-field.vue @@ -1,8 +1,5 @@ + + diff --git a/app/components/pub/my-ui/form/index.ts b/app/components/pub/my-ui/form/index.ts new file mode 100644 index 00000000..246bb8c6 --- /dev/null +++ b/app/components/pub/my-ui/form/index.ts @@ -0,0 +1,11 @@ +export { default as Block } from './block.vue' +export { default as ButtonAction } from './button-action.vue' +export { default as FieldGroup } from './field-group.vue' +export { default as Field } from './field.vue' +export { default as FileField } from './file-field.vue' +export { default as Fragment } from './fragment.vue' +export { default as InputBase } from './input-base.vue' +export { default as Label } from './label.vue' +export { default as Select } from './select.vue' +export { default as TextAreaInput } from './text-area-input.vue' +export { default as TextCaptcha } from './text-captcha.vue' diff --git a/app/components/pub/my-ui/form/input-base.vue b/app/components/pub/my-ui/form/input-base.vue index c31b2073..050a0f78 100644 --- a/app/components/pub/my-ui/form/input-base.vue +++ b/app/components/pub/my-ui/form/input-base.vue @@ -1,17 +1,16 @@ diff --git a/app/components/pub/my-ui/form/select.vue b/app/components/pub/my-ui/form/select.vue index 0cfc926b..0227d2b1 100644 --- a/app/components/pub/my-ui/form/select.vue +++ b/app/components/pub/my-ui/form/select.vue @@ -1,6 +1,7 @@ diff --git a/app/components/content/treatment-report/add.vue b/app/components/content/treatment-report/add.vue index 6789238e..e92cd473 100644 --- a/app/components/content/treatment-report/add.vue +++ b/app/components/content/treatment-report/add.vue @@ -4,6 +4,7 @@ import { genDoctor, type Doctor } from '~/models/doctor' // components import AppTreatmentReportEntry from '~/components/app/treatment-report/entry-form.vue' +import type { TreatmentReportFormData } from '~/schemas/treatment-report.schema' const doctors = ref([]) @@ -17,5 +18,12 @@ const doctors = ref([]) diff --git a/app/components/pub/my-ui/combobox/combobox.vue b/app/components/pub/my-ui/combobox/combobox.vue index 713edd57..de544717 100644 --- a/app/components/pub/my-ui/combobox/combobox.vue +++ b/app/components/pub/my-ui/combobox/combobox.vue @@ -5,7 +5,7 @@ import { type Item } from './index' const props = defineProps<{ id?: string - modelValue?: string + modelValue?: string | number items: Item[] placeholder?: string searchPlaceholder?: string @@ -15,8 +15,8 @@ const props = defineProps<{ }>() const emit = defineEmits<{ - 'update:modelValue': [value: string] - 'update:searchText': [value: string] + 'update:modelValue': [value: string | number] + 'update:searchText': [value: string | number] }>() const open = ref(false) diff --git a/app/components/pub/my-ui/combobox/index.ts b/app/components/pub/my-ui/combobox/index.ts index e4864f7f..f3038de7 100644 --- a/app/components/pub/my-ui/combobox/index.ts +++ b/app/components/pub/my-ui/combobox/index.ts @@ -1,5 +1,5 @@ export interface Item { - value: string + value: string | number label: string code?: string priority?: number @@ -7,12 +7,12 @@ export interface Item { export function recStrToItem(input: Record): Item[] { const items: Item[] = [] - let idx = 0; + let idx = 0 for (const key in input) { if (input.hasOwnProperty(key)) { items.push({ - value: key || ('unknown-' + idx), - label: input[key] || ('unknown-' + idx), + value: key || 'unknown-' + idx, + label: input[key] || 'unknown-' + idx, }) } idx++ diff --git a/app/models/_base.ts b/app/models/_base.ts index 6aaa99fc..ed6f7204 100644 --- a/app/models/_base.ts +++ b/app/models/_base.ts @@ -1,4 +1,3 @@ - export interface Base { id: number createdAt: string | null @@ -20,7 +19,9 @@ export interface TreeItem { export function genBase(): Base { return { - id: 0, + // -1 buat mock data + // backend harusnya non-negative/ > 0 (untuk auto increment constraint) jadi harusnya aman ya + id: -1, createdAt: '', updatedAt: '', } diff --git a/app/schemas/treatment-report.schema.ts b/app/schemas/treatment-report.schema.ts index 5bb247d0..eeb1c889 100644 --- a/app/schemas/treatment-report.schema.ts +++ b/app/schemas/treatment-report.schema.ts @@ -4,10 +4,18 @@ const isoDateTime = z.string().min(1, 'Tanggal / waktu wajib diisi') const positiveInt = z.number().int().nonnegative() const OperatorTeamSchema = z.object({ - dpjpId: z.number().int(), - operatorId: z.number().int(), - assistantOperatorId: z.number().int().optional().nullable(), - instrumentNurseId: z.number().int().optional().nullable(), + dpjpId: z.coerce + .number({ + invalid_type_error: 'Dokter Pemeriksa wajib diisi', + }) + .int(), + operatorId: z.coerce + .number({ + invalid_type_error: 'Operator wajib diisi', + }) + .int(), + assistantOperatorId: z.coerce.number().int().optional().nullable(), + instrumentNurseId: z.coerce.number().int().optional().nullable(), surgeryDate: isoDateTime, actionDiagnosis: z.string().min(1), From f5704536d1542b96dfd57ccc7cf5b8a13e0e4a54 Mon Sep 17 00:00:00 2001 From: Khafid Prayoga Date: Tue, 25 Nov 2025 21:12:18 +0700 Subject: [PATCH 04/28] feat(treatment-report): add error handling and toast notification Implement error handling in treatment report form submission and display toast notifications when errors occur. The form now emits error events and prevents default form submission behavior. --- .../app/treatment-report/entry-form.vue | 15 +++++++++++++-- app/components/content/treatment-report/add.vue | 13 ++++++++++++- 2 files changed, 25 insertions(+), 3 deletions(-) diff --git a/app/components/app/treatment-report/entry-form.vue b/app/components/app/treatment-report/entry-form.vue index 77367f97..8e19cc64 100644 --- a/app/components/app/treatment-report/entry-form.vue +++ b/app/components/app/treatment-report/entry-form.vue @@ -35,7 +35,9 @@ interface Props { const props = defineProps() const emit = defineEmits<{ (e: 'submit', payload: FormData): void + (e: 'error', errors: Error): void }>() + const { isLoading, mode = 'create' } = props const isReadonly = computed(() => { if (isLoading) { @@ -48,6 +50,7 @@ const isReadonly = computed(() => { return false }) + const formSchema = toTypedSchema(TreatmentReportSchema) const { handleSubmit, values, resetForm, setFieldValue, setValues, validate } = useForm({ @@ -75,12 +78,20 @@ defineExpose({ // #endregion region // #region Utilities & event handlers -const onSubmit = handleSubmit((formValues: FormData) => emit('submit', formValues)) +// const onSubmit = handleSubmit((formValues: FormData) => emit('submit', formValues)) +const onSubmit = handleSubmit( + (values) => { + emit('submit', values) + }, + (errors) => { + emit('error', new Error('Silahkan lengkapi form terlebih dahulu')) + }, +) // #endregion