Clientes
This commit is contained in:
parent
c8e3191d05
commit
9683ee5102
@ -9,11 +9,11 @@ import {
|
||||
import { useFormContext } from "react-hook-form";
|
||||
import { CURRENCY_OPTIONS, LANGUAGE_OPTIONS } from "../../constants";
|
||||
import { useTranslation } from "../../i18n";
|
||||
import { CreateCustomerFormData } from "../../schemas";
|
||||
import { CustomerFormData } from "../../schemas";
|
||||
|
||||
export const CustomerAdditionalConfigFields = () => {
|
||||
const { t } = useTranslation();
|
||||
const { control } = useFormContext<CreateCustomerFormData>();
|
||||
const { control } = useFormContext<CustomerFormData>();
|
||||
|
||||
return (
|
||||
<Card className='border-0 shadow-none'>
|
||||
|
||||
@ -9,11 +9,11 @@ import {
|
||||
import { useFormContext } from "react-hook-form";
|
||||
import { COUNTRY_OPTIONS } from "../../constants";
|
||||
import { useTranslation } from "../../i18n";
|
||||
import { CreateCustomerFormData } from "../../schemas";
|
||||
import { CustomerFormData } from "../../schemas";
|
||||
|
||||
export const CustomerAddressFields = () => {
|
||||
const { t } = useTranslation();
|
||||
const { control } = useFormContext<CreateCustomerFormData>();
|
||||
const { control } = useFormContext<CustomerFormData>();
|
||||
|
||||
return (
|
||||
<Card className='border-0 shadow-none'>
|
||||
|
||||
@ -15,11 +15,11 @@ import {
|
||||
} from "@repo/shadcn-ui/components";
|
||||
import { useFormContext, useWatch } from "react-hook-form";
|
||||
import { useTranslation } from "../../i18n";
|
||||
import { CreateCustomerFormData } from "../../schemas";
|
||||
import { CustomerFormData } from "../../schemas";
|
||||
|
||||
export const CustomerBasicInfoFields = () => {
|
||||
const { t } = useTranslation();
|
||||
const { control } = useFormContext<CreateCustomerFormData>();
|
||||
const { control } = useFormContext<CustomerFormData>();
|
||||
|
||||
const isCompany = useWatch({
|
||||
control,
|
||||
|
||||
@ -1,8 +1,6 @@
|
||||
import { zodResolver } from "@hookform/resolvers/zod";
|
||||
import { FieldErrors, FormProvider, useForm } from "react-hook-form";
|
||||
import { FieldErrors, useFormContext } from "react-hook-form";
|
||||
|
||||
import { useEffect } from "react";
|
||||
import { CreateCustomerFormData, CreateCustomerFormSchema } from "../../schemas";
|
||||
import { CustomerFormData } from "../../schemas";
|
||||
import { FormDebug } from "../form-debug";
|
||||
import { CustomerAdditionalConfigFields } from "./customer-additional-config-fields";
|
||||
import { CustomerAddressFields } from "./customer-address-fields";
|
||||
@ -11,57 +9,26 @@ import { CustomerContactFields } from "./customer-contact-fields";
|
||||
|
||||
interface CustomerFormProps {
|
||||
formId: string;
|
||||
initialValues: CreateCustomerFormData;
|
||||
onSubmit: (data: CreateCustomerFormData) => void;
|
||||
onError: (errors: FieldErrors<CreateCustomerFormData>) => void;
|
||||
disabled?: boolean;
|
||||
onDirtyChange: (isDirty: boolean) => void;
|
||||
onSubmit: (data: CustomerFormData) => void;
|
||||
onError: (errors: FieldErrors<CustomerFormData>) => void;
|
||||
}
|
||||
|
||||
export function CustomerEditForm({
|
||||
formId,
|
||||
initialValues,
|
||||
onSubmit,
|
||||
onError,
|
||||
disabled,
|
||||
onDirtyChange,
|
||||
}: CustomerFormProps) {
|
||||
const form = useForm<CreateCustomerFormData>({
|
||||
resolver: zodResolver(CreateCustomerFormSchema),
|
||||
defaultValues: initialValues,
|
||||
disabled,
|
||||
});
|
||||
|
||||
const {
|
||||
formState: { isDirty },
|
||||
} = form;
|
||||
|
||||
useEffect(() => {
|
||||
if (onDirtyChange) {
|
||||
onDirtyChange(isDirty);
|
||||
}
|
||||
}, [isDirty, onDirtyChange]);
|
||||
|
||||
// Resetear el form si cambian los valores iniciales
|
||||
useEffect(() => {
|
||||
form.reset(initialValues);
|
||||
}, [initialValues, form]);
|
||||
export const CustomerEditForm = ({ formId, onSubmit, onError }: CustomerFormProps) => {
|
||||
const form = useFormContext<CustomerFormData>();
|
||||
|
||||
return (
|
||||
<FormProvider {...form}>
|
||||
<form id={formId} onSubmit={form.handleSubmit(onSubmit, onError)}>
|
||||
<div className='xl:flex xl:flex-row-reverse xl:items-start'>
|
||||
<div className='w-full xl:w-6/12'>
|
||||
<FormDebug />
|
||||
</div>
|
||||
<div className='w-full xl:grow'>
|
||||
<CustomerBasicInfoFields />
|
||||
<CustomerContactFields />
|
||||
<CustomerAddressFields />
|
||||
<CustomerAdditionalConfigFields />
|
||||
</div>
|
||||
<form id={formId} onSubmit={form.handleSubmit(onSubmit, onError)}>
|
||||
<div className='xl:flex xl:flex-row-reverse xl:items-start'>
|
||||
<div className='w-full xl:w-6/12'>
|
||||
<FormDebug />
|
||||
</div>
|
||||
</form>
|
||||
</FormProvider>
|
||||
<div className='w-full xl:grow'>
|
||||
<CustomerBasicInfoFields />
|
||||
<CustomerContactFields />
|
||||
<CustomerAddressFields />
|
||||
<CustomerAdditionalConfigFields />
|
||||
</div>
|
||||
</div>
|
||||
</form>
|
||||
);
|
||||
}
|
||||
};
|
||||
|
||||
@ -1,4 +1,5 @@
|
||||
export * from "./use-create-customer-mutation";
|
||||
export * from "./use-customer-form";
|
||||
export * from "./use-customer-query";
|
||||
export * from "./use-customers-context";
|
||||
export * from "./use-customers-query";
|
||||
|
||||
@ -2,11 +2,11 @@ import { useDataSource } from "@erp/core/hooks";
|
||||
import { UniqueID, ValidationErrorCollection } from "@repo/rdx-ddd";
|
||||
import { useMutation, useQueryClient } from "@tanstack/react-query";
|
||||
import { CreateCustomerRequestSchema, CustomerCreationResponseDTO } from "../../common";
|
||||
import { CreateCustomerFormData } from "../schemas";
|
||||
import { CustomerFormData } from "../schemas";
|
||||
import { CUSTOMERS_LIST_KEY } from "./use-update-customer-mutation";
|
||||
|
||||
type CreateCustomerPayload = {
|
||||
data: CreateCustomerFormData;
|
||||
data: CustomerFormData;
|
||||
};
|
||||
|
||||
export function useCreateCustomerMutation() {
|
||||
|
||||
36
modules/customers/src/web/hooks/use-customer-form.ts
Normal file
36
modules/customers/src/web/hooks/use-customer-form.ts
Normal file
@ -0,0 +1,36 @@
|
||||
import { zodResolver } from "@hookform/resolvers/zod";
|
||||
import { useEffect } from "react";
|
||||
import { useForm } from "react-hook-form";
|
||||
import { CustomerFormData, CustomerFormSchema } from "../schemas";
|
||||
|
||||
type UseCustomerFormProps = {
|
||||
initialValues: CustomerFormData;
|
||||
disabled?: boolean;
|
||||
onDirtyChange?: (isDirty: boolean) => void;
|
||||
};
|
||||
|
||||
export function useCustomerForm({ initialValues, disabled, onDirtyChange }: UseCustomerFormProps) {
|
||||
const form = useForm<CustomerFormData>({
|
||||
resolver: zodResolver(CustomerFormSchema),
|
||||
defaultValues: initialValues,
|
||||
disabled,
|
||||
});
|
||||
|
||||
const {
|
||||
formState: { isDirty },
|
||||
} = form;
|
||||
|
||||
// Avisar cuando cambia el dirty state
|
||||
useEffect(() => {
|
||||
if (onDirtyChange) {
|
||||
onDirtyChange(isDirty);
|
||||
}
|
||||
}, [isDirty, onDirtyChange]);
|
||||
|
||||
// Resetear el form si cambian los valores iniciales
|
||||
useEffect(() => {
|
||||
form.reset(initialValues);
|
||||
}, [initialValues, form]);
|
||||
|
||||
return form;
|
||||
}
|
||||
@ -2,14 +2,14 @@ import { useDataSource } from "@erp/core/hooks";
|
||||
import { ValidationErrorCollection } from "@repo/rdx-ddd";
|
||||
import { useMutation, useQueryClient } from "@tanstack/react-query";
|
||||
import { UpdateCustomerByIdRequestDTO, UpdateCustomerByIdRequestSchema } from "../../common";
|
||||
import { CreateCustomerFormData } from "../schemas";
|
||||
import { CustomerFormData } from "../schemas";
|
||||
import { CUSTOMER_QUERY_KEY } from "./use-customer-query";
|
||||
|
||||
export const CUSTOMERS_LIST_KEY = ["customers"] as const;
|
||||
|
||||
type UpdateCustomerPayload = {
|
||||
id: string;
|
||||
data: CreateCustomerFormData;
|
||||
data: CustomerFormData;
|
||||
};
|
||||
|
||||
export function useUpdateCustomerMutation() {
|
||||
|
||||
@ -3,17 +3,15 @@ import { useNavigate } from "react-router-dom";
|
||||
|
||||
import { FormCommitButtonGroup, UnsavedChangesProvider } from "@erp/core/hooks";
|
||||
import { showErrorToast, showSuccessToast } from "@repo/shadcn-ui/lib/utils";
|
||||
import { useState } from "react";
|
||||
import { FieldErrors } from "react-hook-form";
|
||||
import { FieldErrors, FormProvider } from "react-hook-form";
|
||||
import { CustomerEditForm, ErrorAlert } from "../../components";
|
||||
import { useCreateCustomerMutation } from "../../hooks";
|
||||
import { useCreateCustomerMutation, useCustomerForm } from "../../hooks";
|
||||
import { useTranslation } from "../../i18n";
|
||||
import { CreateCustomerFormData, defaultCustomerFormData } from "../../schemas";
|
||||
import { CustomerFormData, defaultCustomerFormData } from "../../schemas";
|
||||
|
||||
export const CustomerCreate = () => {
|
||||
const { t } = useTranslation();
|
||||
const navigate = useNavigate();
|
||||
const [isDirty, setIsDirty] = useState(false);
|
||||
|
||||
// 1) Estado de creación (mutación)
|
||||
const {
|
||||
@ -23,23 +21,26 @@ export const CustomerCreate = () => {
|
||||
error: createError,
|
||||
} = useCreateCustomerMutation();
|
||||
|
||||
// 2) Submit con navegación condicionada por éxito
|
||||
const handleSubmit = (formData: CreateCustomerFormData) => {
|
||||
// 2) Form hook
|
||||
const form = useCustomerForm({
|
||||
initialValues: defaultCustomerFormData,
|
||||
});
|
||||
|
||||
// 3) Submit con navegación condicionada por éxito
|
||||
const handleSubmit = (formData: CustomerFormData) => {
|
||||
mutate(
|
||||
{ data: formData },
|
||||
{
|
||||
onSuccess(data) {
|
||||
setIsDirty(false);
|
||||
showSuccessToast(t("pages.create.successTitle"), t("pages.create.successMsg"));
|
||||
|
||||
// El timeout es para que a React le dé tiempo a procesar
|
||||
// el cambio de estado de isDirty / setIsDirty.
|
||||
setTimeout(() => {
|
||||
navigate("/customers/list", {
|
||||
state: { customerId: data.id, isNew: true },
|
||||
replace: true,
|
||||
});
|
||||
}, 0);
|
||||
// 🔹 reset limpia el form e isDirty pasa a false
|
||||
form.reset(defaultCustomerFormData);
|
||||
|
||||
navigate("/customers/list", {
|
||||
state: { customerId: data.id, isNew: true },
|
||||
replace: true,
|
||||
});
|
||||
},
|
||||
onError(error) {
|
||||
showErrorToast(t("pages.create.errorTitle"), error.message);
|
||||
@ -48,7 +49,7 @@ export const CustomerCreate = () => {
|
||||
);
|
||||
};
|
||||
|
||||
const handleError = (errors: FieldErrors<CreateCustomerFormData>) => {
|
||||
const handleError = (errors: FieldErrors<CustomerFormData>) => {
|
||||
console.error("Errores en el formulario:", errors);
|
||||
// Aquí puedes manejar los errores, por ejemplo, mostrar un mensaje al usuario
|
||||
};
|
||||
@ -57,7 +58,7 @@ export const CustomerCreate = () => {
|
||||
<>
|
||||
<AppBreadcrumb />
|
||||
<AppContent>
|
||||
<UnsavedChangesProvider isDirty={isDirty}>
|
||||
<UnsavedChangesProvider isDirty={form.formState.isDirty}>
|
||||
<div className='flex items-center justify-between space-y-4 px-6'>
|
||||
<div className='space-y-2'>
|
||||
<h2 className='text-2xl font-bold tracking-tight text-balance scroll-m-2'>
|
||||
@ -90,13 +91,13 @@ export const CustomerCreate = () => {
|
||||
)}
|
||||
|
||||
<div className='flex flex-1 flex-col gap-4 p-4'>
|
||||
<CustomerEditForm
|
||||
formId={"customer-create-form"} // para que el botón del header pueda hacer submit
|
||||
initialValues={defaultCustomerFormData}
|
||||
onSubmit={handleSubmit}
|
||||
onError={handleError}
|
||||
onDirtyChange={setIsDirty}
|
||||
/>
|
||||
<FormProvider {...form}>
|
||||
<CustomerEditForm
|
||||
formId='customer-create-form'
|
||||
onSubmit={handleSubmit}
|
||||
onError={handleError}
|
||||
/>
|
||||
</FormProvider>
|
||||
</div>
|
||||
</UnsavedChangesProvider>
|
||||
</AppContent>
|
||||
|
||||
@ -3,7 +3,6 @@ import { useNavigate } from "react-router-dom";
|
||||
|
||||
import { FormCommitButtonGroup, UnsavedChangesProvider, useUrlParamId } from "@erp/core/hooks";
|
||||
import { showErrorToast, showSuccessToast } from "@repo/shadcn-ui/lib/utils";
|
||||
import { useState } from "react";
|
||||
import { FieldErrors } from "react-hook-form";
|
||||
import {
|
||||
CustomerEditForm,
|
||||
@ -11,15 +10,14 @@ import {
|
||||
ErrorAlert,
|
||||
NotFoundCard,
|
||||
} from "../../components";
|
||||
import { useCustomerQuery, useUpdateCustomerMutation } from "../../hooks";
|
||||
import { useCustomerForm, useCustomerQuery, useUpdateCustomerMutation } from "../../hooks";
|
||||
import { useTranslation } from "../../i18n";
|
||||
import { CreateCustomerFormData } from "../../schemas";
|
||||
import { CustomerFormData } from "../../schemas";
|
||||
|
||||
export const CustomerUpdate = () => {
|
||||
const customerId = useUrlParamId();
|
||||
const { t } = useTranslation();
|
||||
const navigate = useNavigate();
|
||||
const [isDirty, setIsDirty] = useState(false);
|
||||
|
||||
// 1) Estado de carga del cliente (query)
|
||||
const {
|
||||
@ -37,8 +35,13 @@ export const CustomerUpdate = () => {
|
||||
error: updateError,
|
||||
} = useUpdateCustomerMutation();
|
||||
|
||||
// 3) Form hook
|
||||
const form = useCustomerForm({
|
||||
initialValues: customerData,
|
||||
});
|
||||
|
||||
// 3) Submit con navegación condicionada por éxito
|
||||
const handleSubmit = (formData: CreateCustomerFormData) => {
|
||||
const handleSubmit = (formData: CustomerFormData) => {
|
||||
mutate(
|
||||
{ id: customerId!, data: formData },
|
||||
{
|
||||
@ -62,7 +65,7 @@ export const CustomerUpdate = () => {
|
||||
);
|
||||
};
|
||||
|
||||
const handleError = (errors: FieldErrors<CreateCustomerFormData>) => {
|
||||
const handleError = (errors: FieldErrors<CustomerFormData>) => {
|
||||
console.error("Errores en el formulario:", errors);
|
||||
// Aquí puedes manejar los errores, por ejemplo, mostrar un mensaje al usuario
|
||||
};
|
||||
|
||||
@ -1,15 +1,15 @@
|
||||
import * as z from "zod/v4";
|
||||
import { CreateCustomerFormSchema } from "./customer-create.form.schema";
|
||||
import { CustomerFormSchema } from "./customer.form.schema";
|
||||
|
||||
export const UpdateCustomerFormSchema = CreateCustomerFormSchema.extend({
|
||||
is_company: CreateCustomerFormSchema.shape.is_company.optional(),
|
||||
name: CreateCustomerFormSchema.shape.name.optional(),
|
||||
export const UpdateCustomerFormSchema = CustomerFormSchema.extend({
|
||||
is_company: CustomerFormSchema.shape.is_company.optional(),
|
||||
name: CustomerFormSchema.shape.name.optional(),
|
||||
default_taxes: z.array(z.string()).optional(),
|
||||
|
||||
country: CreateCustomerFormSchema.shape.country.optional(),
|
||||
country: CustomerFormSchema.shape.country.optional(),
|
||||
|
||||
language_code: CreateCustomerFormSchema.shape.language_code.optional(),
|
||||
currency_code: CreateCustomerFormSchema.shape.currency_code.optional(),
|
||||
language_code: CustomerFormSchema.shape.language_code.optional(),
|
||||
currency_code: CustomerFormSchema.shape.currency_code.optional(),
|
||||
});
|
||||
|
||||
export type UpdateCustomerFormData = z.infer<typeof UpdateCustomerFormSchema>;
|
||||
|
||||
@ -1,6 +1,6 @@
|
||||
import * as z from "zod/v4";
|
||||
|
||||
export const CreateCustomerFormSchema = z.object({
|
||||
export const CustomerFormSchema = z.object({
|
||||
reference: z.string().optional(),
|
||||
|
||||
is_company: z.enum(["true", "false"]),
|
||||
@ -55,9 +55,9 @@ export const CreateCustomerFormSchema = z.object({
|
||||
.default("EUR"),
|
||||
});
|
||||
|
||||
export type CreateCustomerFormData = z.infer<typeof CreateCustomerFormSchema>;
|
||||
export type CustomerFormData = z.infer<typeof CustomerFormSchema>;
|
||||
|
||||
export const defaultCustomerFormData: CreateCustomerFormData = {
|
||||
export const defaultCustomerFormData: CustomerFormData = {
|
||||
reference: "",
|
||||
|
||||
is_company: "true",
|
||||
@ -1,2 +1,2 @@
|
||||
export * from "./customer-create.form.schema";
|
||||
export * from "./customer.api.schema";
|
||||
export * from "./customer.form.schema";
|
||||
|
||||
16
modules/verifactu/package.json
Normal file
16
modules/verifactu/package.json
Normal file
@ -0,0 +1,16 @@
|
||||
{
|
||||
"name": "@erp/verifactu",
|
||||
"version": "0.0.1",
|
||||
"main": "src/index.ts",
|
||||
"types": "src/index.ts",
|
||||
"exports": {},
|
||||
"peerDependencies": {
|
||||
"sequelize": "^6.37.5"
|
||||
},
|
||||
"devDependencies": {},
|
||||
"dependencies": {
|
||||
"@erp/core": "workspace:*",
|
||||
"@repo/rdx-ddd": "workspace:*",
|
||||
"@repo/rdx-utils": "workspace:*"
|
||||
}
|
||||
}
|
||||
@ -1 +1 @@
|
||||
export * from "./send-invoice-verifactu.use-case";
|
||||
export * from "./send";
|
||||
|
||||
@ -1,7 +1,8 @@
|
||||
import { IPresenterRegistry, ITransactionManager } from "@erp/core/api";
|
||||
import { UniqueID } from "@repo/rdx-ddd";
|
||||
import { Result } from "@repo/rdx-utils";
|
||||
import { VerifactuRecordService } from "../../../domain/services/verifactu-record.service";
|
||||
import { Transaction } from "sequelize";
|
||||
import { VerifactuRecordService } from "../../../domain";
|
||||
|
||||
type SendInvoiceVerifactuUseCaseInput = {
|
||||
invoice_id: string;
|
||||
@ -24,7 +25,7 @@ export class SendInvoiceVerifactuUseCase {
|
||||
}
|
||||
|
||||
const invoiceId = idOrError.data;
|
||||
return this.transactionManager.complete(async (Transaction) => {
|
||||
return this.transactionManager.complete(async (transaction: Transaction) => {
|
||||
try {
|
||||
const invoiceOrError = await this.service.sendInvoiceToVerifactu(invoiceId, transaction);
|
||||
if (invoiceOrError.isFailure) {
|
||||
|
||||
3
modules/verifactu/src/api/domain/index.ts
Normal file
3
modules/verifactu/src/api/domain/index.ts
Normal file
@ -0,0 +1,3 @@
|
||||
export * from "./aggregates";
|
||||
export * from "./repositories";
|
||||
export * from "./services";
|
||||
1
modules/verifactu/src/api/domain/repositories/index.ts
Normal file
1
modules/verifactu/src/api/domain/repositories/index.ts
Normal file
@ -0,0 +1 @@
|
||||
export * from "./verifactu-repository.interface";
|
||||
1
modules/verifactu/src/api/domain/services/index.ts
Normal file
1
modules/verifactu/src/api/domain/services/index.ts
Normal file
@ -0,0 +1 @@
|
||||
export * from "./verifactu-record.service";
|
||||
161
modules/verifactu/src/api/infrastructure/dependencies.ts
Normal file
161
modules/verifactu/src/api/infrastructure/dependencies.ts
Normal file
@ -0,0 +1,161 @@
|
||||
// modules/invoice/infrastructure/invoice-dependencies.factory.ts
|
||||
|
||||
import type { IMapperRegistry, IPresenterRegistry, ModuleParams } from "@erp/core/api";
|
||||
|
||||
import {
|
||||
InMemoryMapperRegistry,
|
||||
InMemoryPresenterRegistry,
|
||||
SequelizeTransactionManager,
|
||||
} from "@erp/core/api";
|
||||
|
||||
import {
|
||||
CreateCustomerInvoiceUseCase,
|
||||
CustomerInvoiceFullPresenter,
|
||||
CustomerInvoiceItemsFullPresenter,
|
||||
CustomerInvoiceReportHTMLPresenter,
|
||||
CustomerInvoiceReportPDFPresenter,
|
||||
CustomerInvoiceReportPresenter,
|
||||
GetCustomerInvoiceUseCase,
|
||||
ListCustomerInvoicesPresenter,
|
||||
ListCustomerInvoicesUseCase,
|
||||
RecipientInvoiceFullPresenter,
|
||||
ReportCustomerInvoiceUseCase,
|
||||
} from "../application";
|
||||
|
||||
import { JsonTaxCatalogProvider, spainTaxCatalogProvider } from "@erp/core";
|
||||
import { CustomerInvoiceItemsReportPersenter } from "../application/presenters/queries/customer-invoice-items.report.presenter";
|
||||
import { CustomerInvoiceService } from "../domain";
|
||||
import { CustomerInvoiceDomainMapper, CustomerInvoiceListMapper } from "./mappers";
|
||||
import { CustomerInvoiceRepository } from "./sequelize";
|
||||
|
||||
export type CustomerInvoiceDeps = {
|
||||
transactionManager: SequelizeTransactionManager;
|
||||
mapperRegistry: IMapperRegistry;
|
||||
presenterRegistry: IPresenterRegistry;
|
||||
repo: CustomerInvoiceRepository;
|
||||
service: CustomerInvoiceService;
|
||||
catalogs: {
|
||||
taxes: JsonTaxCatalogProvider;
|
||||
};
|
||||
build: {
|
||||
list: () => ListCustomerInvoicesUseCase;
|
||||
get: () => GetCustomerInvoiceUseCase;
|
||||
create: () => CreateCustomerInvoiceUseCase;
|
||||
//update: () => UpdateCustomerInvoiceUseCase;
|
||||
//delete: () => DeleteCustomerInvoiceUseCase;
|
||||
report: () => ReportCustomerInvoiceUseCase;
|
||||
};
|
||||
};
|
||||
|
||||
export function buildCustomerInvoiceDependencies(params: ModuleParams): CustomerInvoiceDeps {
|
||||
const { database } = params;
|
||||
const transactionManager = new SequelizeTransactionManager(database);
|
||||
const catalogs = { taxes: spainTaxCatalogProvider };
|
||||
|
||||
// Mapper Registry
|
||||
const mapperRegistry = new InMemoryMapperRegistry();
|
||||
mapperRegistry
|
||||
.registerDomainMapper(
|
||||
{ resource: "customer-invoice" },
|
||||
new CustomerInvoiceDomainMapper({ taxCatalog: catalogs.taxes })
|
||||
)
|
||||
.registerQueryMappers([
|
||||
{
|
||||
key: { resource: "customer-invoice", query: "LIST" },
|
||||
mapper: new CustomerInvoiceListMapper(),
|
||||
},
|
||||
]);
|
||||
|
||||
// Repository & Services
|
||||
const repo = new CustomerInvoiceRepository({ mapperRegistry, database });
|
||||
const service = new CustomerInvoiceService(repo);
|
||||
|
||||
// Presenter Registry
|
||||
const presenterRegistry = new InMemoryPresenterRegistry();
|
||||
presenterRegistry.registerPresenters([
|
||||
{
|
||||
key: {
|
||||
resource: "customer-invoice-items",
|
||||
projection: "FULL",
|
||||
},
|
||||
presenter: new CustomerInvoiceItemsFullPresenter(presenterRegistry),
|
||||
},
|
||||
{
|
||||
key: {
|
||||
resource: "recipient-invoice",
|
||||
projection: "FULL",
|
||||
},
|
||||
presenter: new RecipientInvoiceFullPresenter(presenterRegistry),
|
||||
},
|
||||
{
|
||||
key: {
|
||||
resource: "customer-invoice",
|
||||
projection: "FULL",
|
||||
},
|
||||
presenter: new CustomerInvoiceFullPresenter(presenterRegistry),
|
||||
},
|
||||
{
|
||||
key: {
|
||||
resource: "customer-invoice",
|
||||
projection: "LIST",
|
||||
},
|
||||
presenter: new ListCustomerInvoicesPresenter(presenterRegistry),
|
||||
},
|
||||
{
|
||||
key: {
|
||||
resource: "customer-invoice",
|
||||
projection: "REPORT",
|
||||
format: "JSON",
|
||||
},
|
||||
presenter: new CustomerInvoiceReportPresenter(presenterRegistry),
|
||||
},
|
||||
{
|
||||
key: {
|
||||
resource: "customer-invoice-items",
|
||||
projection: "REPORT",
|
||||
format: "JSON",
|
||||
},
|
||||
presenter: new CustomerInvoiceItemsReportPersenter(presenterRegistry),
|
||||
},
|
||||
{
|
||||
key: {
|
||||
resource: "customer-invoice",
|
||||
projection: "REPORT",
|
||||
format: "HTML",
|
||||
},
|
||||
presenter: new CustomerInvoiceReportHTMLPresenter(presenterRegistry),
|
||||
},
|
||||
{
|
||||
key: {
|
||||
resource: "customer-invoice",
|
||||
projection: "REPORT",
|
||||
format: "PDF",
|
||||
},
|
||||
presenter: new CustomerInvoiceReportPDFPresenter(presenterRegistry),
|
||||
},
|
||||
]);
|
||||
|
||||
return {
|
||||
transactionManager,
|
||||
repo,
|
||||
mapperRegistry,
|
||||
presenterRegistry,
|
||||
service,
|
||||
catalogs,
|
||||
build: {
|
||||
list: () => new ListCustomerInvoicesUseCase(service, transactionManager, presenterRegistry),
|
||||
get: () => new GetCustomerInvoiceUseCase(service, transactionManager, presenterRegistry),
|
||||
create: () =>
|
||||
new CreateCustomerInvoiceUseCase(
|
||||
service,
|
||||
transactionManager,
|
||||
presenterRegistry,
|
||||
catalogs.taxes
|
||||
),
|
||||
// update: () => new UpdateCustomerInvoiceUseCase(service, transactionManager),
|
||||
// delete: () => new DeleteCustomerInvoiceUseCase(service, transactionManager),
|
||||
report: () =>
|
||||
new ReportCustomerInvoiceUseCase(service, transactionManager, presenterRegistry),
|
||||
},
|
||||
};
|
||||
}
|
||||
3
modules/verifactu/src/api/infrastructure/index.ts
Normal file
3
modules/verifactu/src/api/infrastructure/index.ts
Normal file
@ -0,0 +1,3 @@
|
||||
export * from "./mappers";
|
||||
export * from "./sequelize";
|
||||
export * from "./express";
|
||||
33
modules/verifactu/tsconfig.json
Normal file
33
modules/verifactu/tsconfig.json
Normal file
@ -0,0 +1,33 @@
|
||||
{
|
||||
"extends": "../../tsconfig.json",
|
||||
"compilerOptions": {
|
||||
"baseUrl": ".",
|
||||
"paths": {
|
||||
"@erp/customer-invoices/*": ["./src/*"]
|
||||
},
|
||||
|
||||
"tsBuildInfoFile": "./node_modules/.tmp/tsconfig.app.tsbuildinfo",
|
||||
"target": "ES2022",
|
||||
"useDefineForClassFields": true,
|
||||
"lib": ["ES2022", "DOM", "DOM.Iterable"],
|
||||
"module": "ESNext",
|
||||
"skipLibCheck": true,
|
||||
|
||||
/* Bundler mode */
|
||||
"moduleResolution": "bundler",
|
||||
"allowImportingTsExtensions": true,
|
||||
"isolatedModules": true,
|
||||
"moduleDetection": "force",
|
||||
"noEmit": true,
|
||||
"jsx": "react-jsx",
|
||||
|
||||
/* Linting */
|
||||
"strict": true,
|
||||
"noUnusedLocals": true,
|
||||
"noUnusedParameters": true,
|
||||
"noFallthroughCasesInSwitch": true,
|
||||
"noUncheckedSideEffectImports": true
|
||||
},
|
||||
"include": ["src"],
|
||||
"exclude": ["node_modules"]
|
||||
}
|
||||
@ -657,6 +657,21 @@ importers:
|
||||
specifier: ^3.2.4
|
||||
version: 3.2.4(@types/debug@4.1.12)(@types/node@24.0.3)(jiti@2.4.2)(less@4.3.0)(lightningcss@1.30.1)(sass@1.89.0)(stylus@0.62.0)(terser@5.40.0)(tsx@4.19.4)
|
||||
|
||||
modules/verifactu:
|
||||
dependencies:
|
||||
'@erp/core':
|
||||
specifier: workspace:*
|
||||
version: link:../core
|
||||
'@repo/rdx-ddd':
|
||||
specifier: workspace:*
|
||||
version: link:../../packages/rdx-ddd
|
||||
'@repo/rdx-utils':
|
||||
specifier: workspace:*
|
||||
version: link:../../packages/rdx-utils
|
||||
sequelize:
|
||||
specifier: ^6.37.5
|
||||
version: 6.37.7(mysql2@3.14.1)
|
||||
|
||||
packages/rdx-criteria:
|
||||
dependencies:
|
||||
'@codelytv/criteria':
|
||||
@ -12806,7 +12821,7 @@ snapshots:
|
||||
|
||||
wkx@0.5.0:
|
||||
dependencies:
|
||||
'@types/node': 24.0.3
|
||||
'@types/node': 22.15.32
|
||||
|
||||
wordwrap@1.0.0: {}
|
||||
|
||||
|
||||
Loading…
Reference in New Issue
Block a user