feat: enhance SEP entry and detail handling with new link mode and save functionality
This commit is contained in:
@@ -14,7 +14,7 @@ const recSepId = inject('rec_sep_id') as Ref<string>
|
||||
|
||||
function handleSelection() {
|
||||
recSepId.value = record.sepNumber || ''
|
||||
const pathUrl = `/integration/bpjs-vclaim/sep/${record.sepNumber || ''}/detail`
|
||||
const pathUrl = `/integration/bpjs-vclaim/sep/${record.sepNumber || ''}/link`
|
||||
router.push({ path: pathUrl })
|
||||
}
|
||||
</script>
|
||||
|
||||
@@ -47,6 +47,7 @@ const props = defineProps<{
|
||||
cities: any[]
|
||||
districts: any[]
|
||||
specialists?: TreeItem[]
|
||||
sepNumber?: string
|
||||
objects?: any
|
||||
values?: any
|
||||
}>()
|
||||
@@ -129,6 +130,14 @@ async function onFetchChildren(parentId: string): Promise<void> {
|
||||
console.log('onFetchChildren', parentId)
|
||||
}
|
||||
|
||||
const onBack = () => {
|
||||
emit('event', 'back')
|
||||
}
|
||||
|
||||
const onSaveNumber = () => {
|
||||
emit('event', 'save-sep-number', { sepNumber: props.sepNumber})
|
||||
}
|
||||
|
||||
// Submit handler
|
||||
const onSubmit = handleSubmit((values) => {
|
||||
console.log('✅ Validated form values:', JSON.stringify(values, null, 2))
|
||||
@@ -966,6 +975,7 @@ onMounted(() => {
|
||||
<!-- Actions -->
|
||||
<div class="mt-6 flex justify-end gap-2">
|
||||
<Button
|
||||
v-if="props.mode === 'detail'"
|
||||
variant="ghost"
|
||||
type="button"
|
||||
class="h-[40px] min-w-[120px] text-orange-400 hover:bg-green-50"
|
||||
@@ -978,6 +988,7 @@ onMounted(() => {
|
||||
Riwayat SEP
|
||||
</Button>
|
||||
<Button
|
||||
v-if="props.mode === 'detail'"
|
||||
variant="outline"
|
||||
type="button"
|
||||
class="h-[40px] min-w-[120px] rounded-md border-orange-400 text-orange-400 hover:bg-green-50 hover:text-orange-400"
|
||||
@@ -989,6 +1000,7 @@ onMounted(() => {
|
||||
Preview
|
||||
</Button>
|
||||
<Button
|
||||
v-if="props.mode === 'add'"
|
||||
type="button"
|
||||
class="h-[40px] min-w-[120px] text-white"
|
||||
:disabled="isLoading"
|
||||
@@ -1000,6 +1012,32 @@ onMounted(() => {
|
||||
/>
|
||||
Simpan
|
||||
</Button>
|
||||
<Button
|
||||
v-if="props.mode === 'detail'"
|
||||
type="button"
|
||||
class="h-[40px] min-w-[120px] text-white"
|
||||
:disabled="isLoading"
|
||||
@click="onBack"
|
||||
>
|
||||
<Icon
|
||||
name="i-lucide-chevron-left"
|
||||
class="h-5 w-5"
|
||||
/>
|
||||
Kembali
|
||||
</Button>
|
||||
<Button
|
||||
v-if="props.mode === 'link'"
|
||||
type="button"
|
||||
class="h-[40px] min-w-[120px] text-white"
|
||||
:disabled="isLoading"
|
||||
@click="onSaveNumber"
|
||||
>
|
||||
<Icon
|
||||
name="i-lucide-save"
|
||||
class="h-5 w-5"
|
||||
/>
|
||||
Terapkan
|
||||
</Button>
|
||||
</div>
|
||||
</form>
|
||||
</div>
|
||||
|
||||
@@ -9,6 +9,7 @@ import AppViewLetter from '~/components/app/sep/view-letter.vue'
|
||||
|
||||
// Handler
|
||||
import { useIntegrationSepEntry } from '~/handlers/integration-sep-entry.handler'
|
||||
import { useIntegrationSepDetail } from '~/handlers/integration-sep-detail.handler'
|
||||
|
||||
const {
|
||||
histories,
|
||||
@@ -55,8 +56,18 @@ const {
|
||||
handleInit,
|
||||
} = useIntegrationSepEntry()
|
||||
|
||||
const { valueObjects, getSepDetail } = useIntegrationSepDetail()
|
||||
|
||||
const props = defineProps<{
|
||||
mode: 'add' | 'edit' | 'detail' | 'link'
|
||||
}>()
|
||||
|
||||
onMounted(async () => {
|
||||
await handleInit()
|
||||
if (['detail', 'link'].includes(props.mode)) {
|
||||
await getSepDetail()
|
||||
selectedObjects.value = { ...selectedObjects.value, ...valueObjects.value }
|
||||
}
|
||||
})
|
||||
</script>
|
||||
|
||||
@@ -66,10 +77,10 @@ onMounted(async () => {
|
||||
name="i-lucide-panel-bottom"
|
||||
class="me-2"
|
||||
/>
|
||||
<span class="font-semibold">Tambah</span>
|
||||
SEP
|
||||
<span class="font-semibold">{{ ['detail', 'link'].includes(props.mode) ? 'Detail' : 'Tambah' }} SEP</span>
|
||||
</div>
|
||||
<AppSepEntryForm
|
||||
:mode="props.mode"
|
||||
:is-save-loading="isSaveLoading"
|
||||
:is-service="isServiceHidden"
|
||||
:doctors="doctors"
|
||||
|
||||
@@ -39,67 +39,55 @@ export function useIntegrationSepDetail() {
|
||||
if (result.success && result.body?.response) {
|
||||
const response = result.body.response
|
||||
sepData.value = response
|
||||
|
||||
// Map response to form objects
|
||||
// patientName.value = objects?.patientName || ''
|
||||
// nationalIdentity.value = objects?.nationalIdentity || ''
|
||||
// medicalRecordNumber.value = objects?.medicalRecordNumber || ''
|
||||
// doctorId.value = objects?.doctorId || ''
|
||||
// subSpecialistId.value = objects?.subSpecialistId || ''
|
||||
// registerDate.value = objects?.registerDate || ''
|
||||
// paymentType.value = objects?.paymentType || ''
|
||||
// patientCategory.value = objects?.patientCategory || ''
|
||||
// cardNumber.value = objects?.cardNumber || ''
|
||||
// sepType.value = objects?.sepType || ''
|
||||
// sepNumber.value = objects?.sepNumber || ''
|
||||
// sepReference.value = objects?.sepReference || ''
|
||||
// sepControlDate.value = objects?.sepControlDate || ''
|
||||
// sepTrafficStatus.value = objects?.sepTrafficStatus || ''
|
||||
// diagnosis.value = objects?.diagnosis || ''
|
||||
|
||||
// if (Object.keys(response).length > 0) {
|
||||
// formObjects.value.patientName = response.peserta?.nama || '-'
|
||||
// formObjects.value.medicalRecordNumber = response.peserta?.noMr || '-'
|
||||
// formObjects.value.cardNumber = response.peserta?.noKartu || '-'
|
||||
// formObjects.value.registerDate = response.tglSep || null
|
||||
// formObjects.value.sepReference = response.noSep || '-'
|
||||
// formObjects.value.sepControlDate = response.tglSep || null
|
||||
// formObjects.value.sepTrafficStatus = response.nmstatusKecelakaan || '-'
|
||||
// formObjects.value.diagnosis = response.diagnosa || '-'
|
||||
// vclaimReference.value = {
|
||||
// noSep: response.noSep || sepNumberValue.trim(),
|
||||
// tglRujukan: response.tglSep ? new Date(response.tglSep).toISOString() : null,
|
||||
// ppkDirujuk: response.noRujukan || 'rssa',
|
||||
// jnsPelayanan:
|
||||
// response.jnsPelayanan === 'Rawat Jalan' ? '2' : response.jnsPelayanan === 'Rawat Inap' ? '1' : null,
|
||||
// catatan: response.catatan || '',
|
||||
// diagRujukan: response.diagnosa || '',
|
||||
// tipeRujukan: response.tujuanKunj?.kode ?? '0',
|
||||
// poliRujukan: response.poli || '',
|
||||
// user: userStore.user?.user_name || '',
|
||||
// }
|
||||
// }
|
||||
|
||||
valueObjects.value = {
|
||||
noSep: response.noSep || noSep.value,
|
||||
tglRujukan: response.tglSep ? new Date(response.tglSep).toISOString().split('T')[0] : '',
|
||||
ppkDirujuk: response.noRujukan || '',
|
||||
jnsPelayanan: mapServiceCodeToLabel(response.jnsPelayanan),
|
||||
catatan: response.catatan || '',
|
||||
diagRujukan: response.diagnosa || '',
|
||||
tipeRujukan: response.tujuanKunj?.kode ?? '0',
|
||||
poliRujukan: response.poli || '',
|
||||
user: response.dpjp?.kdDPJP || response.dpjp?.nmDPJP || '',
|
||||
// Additional fields dari response
|
||||
patientName: response.peserta?.nama || '-',
|
||||
medicalRecordNumber: response.peserta?.noMr || '-',
|
||||
sepNumber: response.noSep || noSep.value,
|
||||
eSep: response.eSEP === 'True' ? 'yes' : 'no',
|
||||
serviceType: response.jnsPelayanan === 'Rawat Jalan' ? '2' : response.jnsPelayanan === 'Rawat Inap' ? '1' : null,
|
||||
sepDate: response.tglSep ? new Date(response.tglSep).toISOString().split('T')[0] : '',
|
||||
cardNumber: response.peserta?.noKartu || '-',
|
||||
diagnosis: response.diagnosa || '-',
|
||||
sepReference: response.noSep || '-',
|
||||
sepControlDate: response.tglSep || null,
|
||||
sepTrafficStatus: response.nmstatusKecelakaan || '-',
|
||||
kelasRawat: response.kelasRawat || '-',
|
||||
referralNumber: response.noRujukan || '-',
|
||||
patientName: response.peserta?.nama || '-',
|
||||
phoneNumber: response.peserta?.noTelp || '-',
|
||||
medicalRecordNumber: response.peserta?.noMr || '-',
|
||||
memberInsurance: response.peserta?.asuransi || '-',
|
||||
memberClass: response.peserta?.hakKelas || '-',
|
||||
memberGender: response.peserta?.kelamin || '-',
|
||||
memberBirthDate: response.peserta?.tglLahir || '-',
|
||||
memberType: response.peserta?.jnsPeserta || '-',
|
||||
referralLetterNumber: response.noRujukan || '-',
|
||||
initialDiagnosis: response.diagnosa || '-',
|
||||
attendingDoctor: response.dpjp?.kdDPJP || '-',
|
||||
attendingDoctorName: response.dpjp?.nmDPJP || '-',
|
||||
polyName: response.poli || '-',
|
||||
cob: response.cob === '1' ? 'yes' : 'no',
|
||||
cataract: response.katarak === '1' ? 'yes' : 'no',
|
||||
clinicExcecutive: response.poliEksekutif === '1' ? 'yes' : 'no',
|
||||
procedureType: response.flagProcedure?.kode || '-',
|
||||
procedureTypeName: response.flagProcedure?.nama || '-',
|
||||
supportCode: response.kdPenunjang?.kode || '-',
|
||||
supportCodeName: response.kdPenunjang?.nama || '-',
|
||||
note: response.catatan || response.informasi || '-',
|
||||
classLevel: response.kelasRawat || '-',
|
||||
classLevelUpgrade: response.klsRawat?.klsRawatNaik || '-',
|
||||
classPaySource: response.klsRawat?.pembiayaan || '-',
|
||||
responsiblePerson: response.klsRawat?.penanggungJawab || response.penjamin || '-',
|
||||
purposeOfVisit: response.tujuanKunj?.kode || '-',
|
||||
purposeOfVisitName: response.tujuanKunj?.nama || '-',
|
||||
serviceAssessment: response.assestmenPel?.kode || '-',
|
||||
serviceAssessmentName: response.assestmenPel?.nama || '-',
|
||||
trafficAccident: response.nmstatusKecelakaan || '',
|
||||
trafficAccidentCode: response.kdStatusKecelakaan || '',
|
||||
lpNumber: response.kontrol?.noSurat || '-',
|
||||
accidentDate: response.lokasiKejadian?.tglKejadian || '-',
|
||||
accidentNote: response.lokasiKejadian?.ketKejadian || '-',
|
||||
accidentProvince: response.lokasiKejadian?.kdProp || '-',
|
||||
accidentCity: response.lokasiKejadian?.kdKab || '-',
|
||||
accidentDistrict: response.lokasiKejadian?.kdKec || '-',
|
||||
accidentLocation: response.lokasiKejadian?.lokasi || '-',
|
||||
suplesi: response.jnsPelayanan === 'Rawat Jalan' ? 'yes' : 'no',
|
||||
suplesiNumber: response.jnsPelayanan === 'Rawat Jalan' ? response.noRujukan || '-' : '-',
|
||||
controlLetterNumber: response.kontrol?.noSurat || '-',
|
||||
controlLetterDoctor: response.kontrol?.kdDokter || '-',
|
||||
controlLetterDoctorName: response.kontrol?.nmDokter || '-',
|
||||
}
|
||||
} else {
|
||||
toast({
|
||||
|
||||
@@ -442,6 +442,9 @@ export function useIntegrationSepEntry() {
|
||||
if (menu === 'back') {
|
||||
navigateTo('/integration/bpjs-vclaim/sep')
|
||||
}
|
||||
if (menu === 'save-sep-number') {
|
||||
navigateTo({ path: resourcePath.value, query: { 'sep-number': value.sepNumber || '' } })
|
||||
}
|
||||
if (menu === 'save-sep') {
|
||||
isSaveLoading.value = true
|
||||
|
||||
|
||||
@@ -0,0 +1,26 @@
|
||||
<script setup lang="ts">
|
||||
import Error from '~/components/pub/my-ui/error/error.vue'
|
||||
import Content from '~/components/content/sep/entry.vue'
|
||||
|
||||
definePageMeta({
|
||||
middleware: [],
|
||||
roles: ['doctor', 'nurse', 'admisi', 'pharmacy', 'billing', 'management'],
|
||||
title: 'Detail SEP',
|
||||
contentFrame: 'cf-full-width',
|
||||
})
|
||||
|
||||
const route = useRoute()
|
||||
|
||||
useHead({
|
||||
title: () => route.meta.title as string,
|
||||
})
|
||||
|
||||
const canCreate = true
|
||||
</script>
|
||||
|
||||
<template>
|
||||
<div v-if="canCreate">
|
||||
<Content mode="detail" />
|
||||
</div>
|
||||
<Error v-else :status-code="403" />
|
||||
</template>
|
||||
@@ -0,0 +1,26 @@
|
||||
<script setup lang="ts">
|
||||
import Error from '~/components/pub/my-ui/error/error.vue'
|
||||
import Content from '~/components/content/sep/entry.vue'
|
||||
|
||||
definePageMeta({
|
||||
middleware: [],
|
||||
roles: ['doctor', 'nurse', 'admisi', 'pharmacy', 'billing', 'management'],
|
||||
title: 'Detail SEP',
|
||||
contentFrame: 'cf-full-width',
|
||||
})
|
||||
|
||||
const route = useRoute()
|
||||
|
||||
useHead({
|
||||
title: () => route.meta.title as string,
|
||||
})
|
||||
|
||||
const canCreate = true
|
||||
</script>
|
||||
|
||||
<template>
|
||||
<div v-if="canCreate">
|
||||
<Content mode="link" />
|
||||
</div>
|
||||
<Error v-else :status-code="403" />
|
||||
</template>
|
||||
@@ -1,7 +1,6 @@
|
||||
<script setup lang="ts">
|
||||
import type { PagePermission } from '~/models/role'
|
||||
import Error from '~/components/pub/my-ui/error/error.vue'
|
||||
import { PAGE_PERMISSIONS } from '~/lib/page-permission'
|
||||
import Content from '~/components/content/sep/entry.vue'
|
||||
|
||||
definePageMeta({
|
||||
middleware: [],
|
||||
@@ -16,26 +15,12 @@ useHead({
|
||||
title: () => route.meta.title as string,
|
||||
})
|
||||
|
||||
const roleAccess: PagePermission = PAGE_PERMISSIONS['/doctor']
|
||||
|
||||
const { checkRole, hasCreateAccess } = useRBAC()
|
||||
|
||||
// Check if user has access to this page
|
||||
const hasAccess = checkRole(roleAccess)
|
||||
// if (!hasAccess) {
|
||||
// throw createError({
|
||||
// statusCode: 403,
|
||||
// statusMessage: 'Access denied',
|
||||
// })
|
||||
// }
|
||||
|
||||
// Define permission-based computed properties
|
||||
const canCreate = true // hasCreateAccess(roleAccess)
|
||||
const canCreate = true
|
||||
</script>
|
||||
|
||||
<template>
|
||||
<div v-if="canCreate">
|
||||
<ContentSepEntry />
|
||||
<Content mode="add" />
|
||||
</div>
|
||||
<Error v-else :status-code="403" />
|
||||
</template>
|
||||
|
||||
@@ -1,7 +1,6 @@
|
||||
<script setup lang="ts">
|
||||
import type { PagePermission } from '~/models/role'
|
||||
import Error from '~/components/pub/my-ui/error/error.vue'
|
||||
import { PAGE_PERMISSIONS } from '~/lib/page-permission'
|
||||
import Content from '~/components/content/sep/list.vue'
|
||||
|
||||
definePageMeta({
|
||||
middleware: ['rbac'],
|
||||
@@ -16,24 +15,13 @@ useHead({
|
||||
title: () => route.meta.title as string,
|
||||
})
|
||||
|
||||
const roleAccess: PagePermission = PAGE_PERMISSIONS['/doctor']
|
||||
|
||||
const { checkRole, hasReadAccess } = useRBAC()
|
||||
|
||||
// Check if user has access to this page
|
||||
const hasAccess = checkRole(roleAccess)
|
||||
// if (!hasAccess) {
|
||||
// navigateTo('/403')
|
||||
// }
|
||||
|
||||
// Define permission-based computed properties
|
||||
const canRead = true // hasReadAccess(roleAccess)
|
||||
const canRead = true
|
||||
</script>
|
||||
|
||||
<template>
|
||||
<div>
|
||||
<div v-if="canRead">
|
||||
<ContentSepList />
|
||||
<Content />
|
||||
</div>
|
||||
<Error v-else :status-code="403" />
|
||||
</div>
|
||||
|
||||
Reference in New Issue
Block a user