forked from verdnatura/salix-front
232 lines
7.6 KiB
Vue
232 lines
7.6 KiB
Vue
<script setup>
|
|
import { useRoute, useRouter } from 'vue-router';
|
|
import { reactive, ref } from 'vue';
|
|
import { useI18n } from 'vue-i18n';
|
|
import axios from 'axios';
|
|
import { useState } from 'composables/useState';
|
|
import FormModel from 'components/FormModel.vue';
|
|
import FetchData from 'components/FetchData.vue';
|
|
import VnRow from 'components/ui/VnRow.vue';
|
|
import VnSelect from 'components/common/VnSelect.vue';
|
|
import VnInputDate from 'components/common/VnInputDate.vue';
|
|
import VnSubToolbar from 'src/components/ui/VnSubToolbar.vue';
|
|
|
|
const { t } = useI18n();
|
|
const route = useRoute();
|
|
const state = useState();
|
|
const ORDER_MODEL = 'order';
|
|
|
|
const router = useRouter();
|
|
const isNew = Boolean(!route.params.id);
|
|
const initialFormState = reactive({
|
|
clientFk: null,
|
|
addressFk: null,
|
|
agencyModeFk: null,
|
|
landed: null,
|
|
});
|
|
const clientList = ref([]);
|
|
const agencyList = ref([]);
|
|
const addressList = ref([]);
|
|
const clientId = ref(null);
|
|
|
|
const onClientsFetched = (data) => {
|
|
clientList.value = data;
|
|
initialFormState.clientFk = Number(route.query?.clientFk) || null;
|
|
clientId.value = initialFormState.clientFk;
|
|
|
|
const client = clientList.value.find(
|
|
(client) => client.id === initialFormState.clientFk
|
|
);
|
|
if (!client?.defaultAddressFk)
|
|
throw new Error(t(`No default address found for the client`));
|
|
fetchAddressList(client.defaultAddressFk);
|
|
};
|
|
|
|
const fetchAddressList = async (addressId) => {
|
|
try {
|
|
const { data } = await axios.get('addresses', {
|
|
params: {
|
|
filter: JSON.stringify({
|
|
fields: ['id', 'nickname', 'street', 'city'],
|
|
where: { id: addressId },
|
|
}),
|
|
},
|
|
});
|
|
addressList.value = data;
|
|
if (addressList.value?.length === 1) {
|
|
state.get(ORDER_MODEL).addressFk = addressList.value[0].id;
|
|
}
|
|
} catch (err) {
|
|
console.error(`Error fetching addresses`, err);
|
|
return err.response;
|
|
}
|
|
};
|
|
|
|
const fetchAgencyList = async (landed, addressFk) => {
|
|
if (!landed || !addressFk) {
|
|
return;
|
|
}
|
|
try {
|
|
const { data } = await axios.get('Agencies/landsThatDay', {
|
|
params: {
|
|
addressFk,
|
|
landed: new Date(landed).toISOString(),
|
|
},
|
|
});
|
|
agencyList.value = data;
|
|
} catch (err) {
|
|
console.error(`Error fetching agencies`, err);
|
|
return err.response;
|
|
}
|
|
};
|
|
|
|
const fetchOrderDetails = (order) => {
|
|
fetchAddressList(order?.addressFk);
|
|
fetchAgencyList(order?.landed, order?.addressFk);
|
|
};
|
|
|
|
const orderMapper = (order) => {
|
|
return {
|
|
addressId: order.addressFk,
|
|
agencyModeId: order.agencyModeFk,
|
|
landed: new Date(order.landed).toISOString(),
|
|
};
|
|
};
|
|
const orderFilter = {
|
|
include: [
|
|
{ relation: 'agencyMode', scope: { fields: ['name'] } },
|
|
{
|
|
relation: 'address',
|
|
scope: { fields: ['nickname'] },
|
|
},
|
|
{ relation: 'rows', scope: { fields: ['id'] } },
|
|
{
|
|
relation: 'client',
|
|
scope: {
|
|
fields: [
|
|
'salesPersonFk',
|
|
'name',
|
|
'isActive',
|
|
'isFreezed',
|
|
'isTaxDataChecked',
|
|
],
|
|
include: {
|
|
relation: 'salesPersonUser',
|
|
scope: { fields: ['id', 'name'] },
|
|
},
|
|
},
|
|
},
|
|
],
|
|
};
|
|
|
|
const onClientChange = async (clientId) => {
|
|
try {
|
|
const { data } = await axios.get(`Clients/${clientId}`);
|
|
await fetchAddressList(data.defaultAddressFk);
|
|
} catch (error) {
|
|
console.error('Error al cambiar el cliente:', error);
|
|
}
|
|
};
|
|
|
|
async function onDataSaved(data) {
|
|
await router.push({ path: `/order/${data}/catalog` });
|
|
}
|
|
</script>
|
|
|
|
<template>
|
|
<FetchData
|
|
url="Clients"
|
|
@on-fetch="(data) => onClientsFetched(data)"
|
|
:filter="{ fields: ['id', 'name', 'defaultAddressFk'] }"
|
|
auto-load
|
|
/>
|
|
<VnSubToolbar v-if="isNew" />
|
|
<div class="q-pa-md">
|
|
<FormModel
|
|
:url="!isNew ? `Orders/${route.params.id}` : null"
|
|
url-create="Orders/new"
|
|
@on-data-saved="onDataSaved"
|
|
:model="ORDER_MODEL"
|
|
:form-initial-data="isNew ? initialFormState : null"
|
|
:observe-form-changes="!isNew"
|
|
:mapper="isNew ? orderMapper : null"
|
|
:filter="orderFilter"
|
|
@on-fetch="fetchOrderDetails"
|
|
auto-load
|
|
>
|
|
<template #form="{ data }">
|
|
<VnRow class="row q-gutter-md q-mb-md">
|
|
<VnSelect
|
|
:label="t('order.form.clientFk')"
|
|
v-model="data.clientFk"
|
|
:options="clientList"
|
|
option-value="id"
|
|
option-label="name"
|
|
hide-selected
|
|
@update:model-value="onClientChange"
|
|
>
|
|
<template #option="scope">
|
|
<QItem v-bind="scope.itemProps">
|
|
<QItemSection>
|
|
<QItemLabel>
|
|
{{ `${scope.opt.id}: ${scope.opt.name}` }}
|
|
</QItemLabel>
|
|
</QItemSection>
|
|
</QItem>
|
|
</template>
|
|
</VnSelect>
|
|
<VnSelect
|
|
:label="t('order.form.addressFk')"
|
|
v-model="data.addressFk"
|
|
:options="addressList"
|
|
option-value="id"
|
|
option-label="street"
|
|
hide-selected
|
|
:disable="!addressList?.length"
|
|
@update:model-value="onAddressChange"
|
|
>
|
|
<template #option="scope">
|
|
<QItem v-bind="scope.itemProps">
|
|
<QItemSection>
|
|
<QItemLabel>
|
|
{{
|
|
`${scope.opt.nickname}: ${scope.opt.street},${scope.opt.city}`
|
|
}}
|
|
</QItemLabel>
|
|
</QItemSection>
|
|
</QItem>
|
|
</template>
|
|
</VnSelect>
|
|
</VnRow>
|
|
<VnRow class="row q-gutter-md q-mb-md">
|
|
<VnInputDate
|
|
placeholder="dd-mm-aaa"
|
|
:label="t('order.form.landed')"
|
|
v-model="data.landed"
|
|
@update:model-value="
|
|
() => fetchAgencyList(data.landed, data.addressFk)
|
|
"
|
|
/>
|
|
</VnRow>
|
|
<VnRow class="row q-gutter-md q-mb-md">
|
|
<VnSelect
|
|
:label="t('order.form.agencyModeFk')"
|
|
v-model="data.agencyModeFk"
|
|
:options="agencyList"
|
|
option-value="agencyModeFk"
|
|
option-label="agencyMode"
|
|
hide-selected
|
|
:disable="!agencyList?.length"
|
|
>
|
|
</VnSelect>
|
|
</VnRow>
|
|
</template>
|
|
</FormModel>
|
|
</div>
|
|
</template>
|
|
|
|
<i18n>
|
|
es:
|
|
No default address found for the client: No hay ninguna dirección asociada a este cliente.
|
|
</i18n>
|