aggiunto lo store ProfessionalExpenses

This commit is contained in:
fabio
2026-02-19 10:29:31 +01:00
parent 823a5054a0
commit e752807ede
2 changed files with 94 additions and 20 deletions

View File

@@ -63,7 +63,6 @@
v-if="form.eatsOut"
v-model="form.hasCanteenOrVouchers"
:label="t('professionalExpenses.hasCanteenOrVouchers')"
:rules="[requiredWhenEatsOut]"
class="q-mt-md"
/>
</div>
@@ -78,9 +77,10 @@
</template>
<script setup lang="ts">
import { reactive, onMounted, ref, nextTick, watch, computed } from 'vue'
import { onMounted, ref, nextTick, watch, computed } from 'vue'
import { useI18n } from 'vue-i18n'
import type { StepDescriptor } from '../../types/types'
import { useProfessionalExpensesStore, type ProfessionalExpensesData } from '../../stores/professionalExpenses'
type CommuteMethod = 'CAR' | 'BUS' | 'BIKE' | 'WALK'
@@ -94,6 +94,7 @@ type ProfessionalExpensesForm = {
hasCanteenOrVouchers: boolean
}
const store = useProfessionalExpensesStore()
const props = defineProps<{ step?: StepDescriptor }>()
const emit = defineEmits(['next', 'prev'])
@@ -120,15 +121,7 @@ const minLength = (n: number, msg?: string) => (v: unknown) => {
const form = reactive<ProfessionalExpensesForm>({
expensesChanged: false,
workplaceDescription: '',
commuteMethod: null,
commuteKm: null,
lunchAtHome: false,
eatsOut: false,
hasCanteenOrVouchers: false
})
const form = store.data as ProfessionalExpensesForm
const commuteMethodOptions = computed<Array<{ label: string; value: CommuteMethod }>>(() => [
{ label: t('professionalExpenses.commuteMethodOptions.car'), value: 'CAR' },
@@ -137,11 +130,6 @@ const commuteMethodOptions = computed<Array<{ label: string; value: CommuteMetho
{ label: t('professionalExpenses.commuteMethodOptions.walk'), value: 'WALK' }
])
const requiredWhenEatsOut = (v: boolean | null) => {
if (!form.eatsOut) return true
return v !== null || t('validation.required')
}
/* const professionalExpensesSchema = {
fields: [
{ key: "expensesChanged", type: "boolean", required: true },
@@ -160,10 +148,13 @@ onMounted(async () => {
formRef.value?.resetValidation?.()
})
// persist when expensesChanged toggles
watch(() => form.expensesChanged, () => {
//store.setChildren(buildPayload())
})
watch(
() => form,
() => {
store.persist()
},
{ deep: true }
)
watch(() => form.eatsOut, (value) => {
if (!value) form.hasCanteenOrVouchers = false
@@ -179,10 +170,12 @@ async function saveAndNext() {
} catch {
return
}
store.setProfessionalExpenses(form as ProfessionalExpensesData)
emit('next', props.step?.next)
}
function emitPrev() {
store.setProfessionalExpenses(form as ProfessionalExpensesData)
emit('prev', props.step?.prev)
}

View File

@@ -0,0 +1,81 @@
import { defineStore } from 'pinia'
import { LocalStorage } from 'quasar'
export type CommuteMethod = 'CAR' | 'BUS' | 'BIKE' | 'WALK'
export interface ProfessionalExpensesData {
expensesChanged: boolean
workplaceDescription: string
commuteMethod: CommuteMethod | null
commuteKm: number | null
lunchAtHome: boolean
eatsOut: boolean
hasCanteenOrVouchers: boolean
}
const STORAGE_KEY = 'professionalExpenses:v1'
const DEFAULT: ProfessionalExpensesData = {
expensesChanged: false,
workplaceDescription: '',
commuteMethod: null,
commuteKm: null,
lunchAtHome: false,
eatsOut: false,
hasCanteenOrVouchers: false
}
function isRecord(v: unknown): v is Record<string, unknown> {
return !!v && typeof v === 'object' && !Array.isArray(v)
}
export const useProfessionalExpensesStore = defineStore('professionalexpensesstore', {
state: () => {
try {
let saved: unknown = LocalStorage.getItem(STORAGE_KEY)
if (typeof saved === 'string') {
try {
saved = JSON.parse(saved)
} catch {
saved = null
}
}
if (isRecord(saved)) {
const merged = { ...DEFAULT, ...(saved as Partial<ProfessionalExpensesData>) } as ProfessionalExpensesData
return {
data: {
...merged,
hasCanteenOrVouchers: merged.hasCanteenOrVouchers === true
}
}
}
} catch {
// ignore and fall back to default
}
return { data: { ...DEFAULT } as ProfessionalExpensesData }
},
actions: {
persist() {
try {
LocalStorage.set(STORAGE_KEY, this.data)
} catch (err) {
console.error('professionalExpenses.store: persist error', err)
}
},
getProfessionalExpenses() {
return this.data
},
setProfessionalExpenses(partial: Partial<ProfessionalExpensesData>) {
this.data = { ...this.data, ...partial }
this.persist()
},
replaceProfessionalExpenses(payload: ProfessionalExpensesData) {
this.data = payload
this.persist()
},
resetProfessionalExpenses() {
this.data = { ...DEFAULT }
this.persist()
}
}
})