v1.0.3 - 2 decimales en importes

This commit is contained in:
David Arranz 2024-10-25 11:49:10 +02:00
parent 6e236bba91
commit ee26a8bfa4
21 changed files with 165 additions and 139 deletions

View File

@ -1,7 +1,7 @@
{ {
"name": "@uecko-presupuestador/client", "name": "@uecko-presupuestador/client",
"private": true, "private": true,
"version": "1.0.2", "version": "1.0.3",
"author": "Rodax Software <dev@rodax-software.com>", "author": "Rodax Software <dev@rodax-software.com>",
"type": "module", "type": "module",
"scripts": { "scripts": {

View File

@ -10,7 +10,6 @@ export const CatalogList = () => {
<h2 className='text-2xl font-bold tracking-tight'> <h2 className='text-2xl font-bold tracking-tight'>
<Trans i18nKey='catalog.list.title' /> <Trans i18nKey='catalog.list.title' />
</h2> </h2>
<p className='text-muted-foreground'>descripción</p>
</div> </div>
</div> </div>

View File

@ -25,7 +25,7 @@ import { useToast } from "@/ui/use-toast";
import { IListQuotes_Response_DTO, UTCDateValue } from "@shared/contexts"; import { IListQuotes_Response_DTO, UTCDateValue } from "@shared/contexts";
import { ColumnDef, Row } from "@tanstack/react-table"; import { ColumnDef, Row } from "@tanstack/react-table";
import { t } from "i18next"; import { t } from "i18next";
import { FilePenLineIcon, MoreVerticalIcon } from "lucide-react"; import { FilePenLineIcon, MoreVerticalIcon, SendIcon } from "lucide-react";
import { useCallback, useEffect, useId, useMemo, useState } from "react"; import { useCallback, useEffect, useId, useMemo, useState } from "react";
import { useNavigate } from "react-router-dom"; import { useNavigate } from "react-router-dom";
import { useQuotes } from "../hooks"; import { useQuotes } from "../hooks";
@ -74,7 +74,6 @@ export const QuotesDataTable = ({
const handleEditQuote = useCallback( const handleEditQuote = useCallback(
(quote: IListQuotes_Response_DTO) => { (quote: IListQuotes_Response_DTO) => {
toast({ title: "Guardo => " + quote.id });
navigate(`/quotes/edit/${quote.id}`, { relative: "path" }); navigate(`/quotes/edit/${quote.id}`, { relative: "path" });
}, },
[navigate, toast] [navigate, toast]
@ -92,19 +91,25 @@ export const QuotesDataTable = ({
}: { }: {
row: { original: IListQuotes_Response_DTO }; row: { original: IListQuotes_Response_DTO };
renderValue: () => any; renderValue: () => any;
}) => ( }) => {
<Button const allowToSent = original?.status === "accepted" && !original?.date_sent;
size='sm' const isSent = Boolean(original?.status === "accepted" && original?.date_sent);
variant='link'
className='h-8 gap-1 px-0 text-left text-ellipsis' return (
onClick={(e) => { <Button
e.preventDefault(); size='sm'
handleEditQuote(original); variant='link'
}} disabled={allowToSent || isSent}
> className='h-8 gap-1 px-0 text-left text-ellipsis'
<div className=''>{renderValue()}</div> onClick={(e) => {
</Button> e.preventDefault();
), handleEditQuote(original);
}}
>
<div className=''>{renderValue()}</div>
</Button>
);
},
}, },
{ {
@ -116,16 +121,35 @@ export const QuotesDataTable = ({
<ColorBadge label={t(`quotes.status.${original.status}`)} /> <ColorBadge label={t(`quotes.status.${original.status}`)} />
), ),
}, },
{
id: "date_sent" as const,
accessor: "date_sent",
header: () => (
<div className='text-left text-ellipsis'>{t("quotes.list.columns.date_sent")}</div>
),
cell: ({ row: { original } }: { row: { original: IListQuotes_Response_DTO } }) => {
const quoteDate = UTCDateValue.create(original.date_sent);
return (
<div className='text-left text-ellipsis'>
{quoteDate.isSuccess ? (
<ColorBadge label={quoteDate.object.toLocaleDateString("es-ES")} />
) : (
<>-</>
)}
</div>
);
},
},
{ {
id: "date" as const, id: "date" as const,
accessor: "date", accessor: "date",
header: () => ( header: () => (
<div className='text-right text-ellipsis'>{t("quotes.list.columns.date")}</div> <div className='text-left text-ellipsis'>{t("quotes.list.columns.date")}</div>
), ),
cell: ({ row: { original } }: { row: { original: IListQuotes_Response_DTO } }) => { cell: ({ row: { original } }: { row: { original: IListQuotes_Response_DTO } }) => {
const quoteDate = UTCDateValue.create(original.date); const quoteDate = UTCDateValue.create(original.date);
return ( return (
<div className='text-right text-ellipsis'> <div className='text-left text-ellipsis'>
{quoteDate.isSuccess ? quoteDate.object.toLocaleDateString("es-ES") : "-"} {quoteDate.isSuccess ? quoteDate.object.toLocaleDateString("es-ES") : "-"}
</div> </div>
); );
@ -162,22 +186,7 @@ export const QuotesDataTable = ({
), ),
size: 600, size: 600,
}, },
{
id: "date_sent" as const,
accessor: "date_sent",
header: () => (
<div className='text-right text-ellipsis'>{t("quotes.list.columns.date_sent")}</div>
),
cell: ({ row: { original } }: { row: { original: IListQuotes_Response_DTO } }) => {
const quoteDate = UTCDateValue.create(original.date_sent);
return (
<div className='text-right text-ellipsis'>
{quoteDate.isSuccess}
{quoteDate.isSuccess ? quoteDate.object.toLocaleDateString("es-ES") : "-"}
</div>
);
},
},
/*{ /*{
id: "total_price" as const, id: "total_price" as const,
accessor: "total_price", accessor: "total_price",
@ -195,68 +204,77 @@ export const QuotesDataTable = ({
{ {
id: "row-actions", id: "row-actions",
header: () => null, header: () => null,
cell: ({ row: { original } }: { row: { original: IListQuotes_Response_DTO } }) => ( cell: ({ row: { original } }: { row: { original: IListQuotes_Response_DTO } }) => {
<ButtonGroup> const allowToSent = original?.status === "accepted" && !original?.date_sent;
<Tooltip> const isSent = original?.status === "accepted" && original?.date_sent;
<TooltipTrigger asChild>
{original.status === "accepted" && !original.date_sent ? (
<Button
size='sm'
variant='default'
className='h-8 gap-1'
onClick={(e) => {
e.preventDefault();
//handleSentToUecko(original);
}}
>
<FilePenLineIcon className='h-3.5 w-3.5' />
<span className='lg:sr-only xl:not-sr-only xl:whitespace-nowrap'>
{t("quotes.list.columns.actions.sent_to")}
</span>
</Button>
) : (
<Button
size='sm'
variant='outline'
className='h-8 gap-1'
onClick={(e) => {
e.preventDefault();
handleEditQuote(original);
}}
>
<FilePenLineIcon className='h-3.5 w-3.5' />
<span className='lg:sr-only xl:not-sr-only xl:whitespace-nowrap'>
{t("quotes.list.columns.actions.edit")}
</span>
</Button>
)}
</TooltipTrigger>
<TooltipContent>
<p>{t("quotes.list.columns.actions.sent_to_uecko")}</p>
</TooltipContent>
</Tooltip>
<DropdownMenu> return (
<DropdownMenuTrigger asChild> <ButtonGroup>
<Button size='icon' variant='outline' className='w-8 h-8'> <Tooltip>
<MoreVerticalIcon className='h-3.5 w-3.5' /> <TooltipTrigger asChild>
<span className='sr-only'>{t("common.more")}</span> <>
</Button> {allowToSent && !isSent && (
</DropdownMenuTrigger> <Button
<DropdownMenuContent align='end'> size='sm'
<DropdownMenuItem variant='default'
onClick={() => { className='h-8 gap-1'
download(original.id, getQuotePDFFilename(original)); onClick={(e) => {
}} e.preventDefault();
> //handleSentToUecko(original);
Download }}
</DropdownMenuItem> >
<DropdownMenuSeparator /> <SendIcon className='h-3.5 w-3.5' />
<DropdownMenuItem>{t("common.archive")}</DropdownMenuItem> <span className='lg:sr-only xl:not-sr-only xl:whitespace-nowrap'>
</DropdownMenuContent> {t("quotes.list.columns.actions.sent_to")}
</DropdownMenu> </span>
</ButtonGroup> </Button>
), )}
{!allowToSent && !isSent && (
<Button
size='sm'
variant='outline'
className='h-8 gap-1'
onClick={(e) => {
e.preventDefault();
handleEditQuote(original);
}}
>
<FilePenLineIcon className='h-3.5 w-3.5' />
<span className='lg:sr-only xl:not-sr-only xl:whitespace-nowrap'>
{t("quotes.list.columns.actions.edit")}
</span>
</Button>
)}
</>
</TooltipTrigger>
<TooltipContent>
<p>{t("quotes.list.columns.actions.sent_to_uecko")}</p>
</TooltipContent>
</Tooltip>
<DropdownMenu>
<DropdownMenuTrigger asChild>
<Button size='icon' variant='outline' className='w-8 h-8'>
<MoreVerticalIcon className='h-3.5 w-3.5' />
<span className='sr-only'>{t("common.more")}</span>
</Button>
</DropdownMenuTrigger>
<DropdownMenuContent align='end'>
<DropdownMenuItem
onClick={() => {
download(original.id, getQuotePDFFilename(original));
}}
>
Download
</DropdownMenuItem>
<DropdownMenuSeparator />
<DropdownMenuItem>{t("common.archive")}</DropdownMenuItem>
</DropdownMenuContent>
</DropdownMenu>
</ButtonGroup>
);
},
}, },
]; ];

View File

@ -111,7 +111,7 @@ export const QuoteDetailsCardEditor = ({
<FormCurrencyField <FormCurrencyField
currency={currency} currency={currency}
language={language} language={language}
scale={4} scale={2}
className='text-right' className='text-right'
{...register(`items.${index}.unit_price`)} {...register(`items.${index}.unit_price`)}
/> />
@ -129,7 +129,7 @@ export const QuoteDetailsCardEditor = ({
<FormCurrencyField <FormCurrencyField
currency={currency} currency={currency}
language={language} language={language}
scale={4} scale={2}
readOnly readOnly
className='text-right' className='text-right'
{...register(`items.${index}.subtotal_price`)} {...register(`items.${index}.subtotal_price`)}
@ -165,7 +165,7 @@ export const QuoteDetailsCardEditor = ({
variant='ghost' variant='ghost'
currency={currency} currency={currency}
language={language} language={language}
scale={4} scale={2}
readOnly readOnly
className='font-semibold text-right' className='font-semibold text-right'
{...register(`items.${index}.total_price`)} {...register(`items.${index}.total_price`)}

View File

@ -12,6 +12,7 @@ import {
} from "@/ui"; } from "@/ui";
import { IGetQuote_Response_DTO } from "@shared/contexts"; import { IGetQuote_Response_DTO } from "@shared/contexts";
import { t } from "i18next"; import { t } from "i18next";
import { SendIcon } from "lucide-react";
export const QuoteSentToEditor = ({ export const QuoteSentToEditor = ({
quote, quote,
@ -28,6 +29,7 @@ export const QuoteSentToEditor = ({
<AlertDialog> <AlertDialog>
<AlertDialogTrigger asChild> <AlertDialogTrigger asChild>
<Button size='sm' variant='default' className='h-8 gap-1'> <Button size='sm' variant='default' className='h-8 gap-1'>
<SendIcon className='h-3.5 w-3.5' />
{t("quotes.quote_sent_to_editor.trigger_button")} {t("quotes.quote_sent_to_editor.trigger_button")}
</Button> </Button>
</AlertDialogTrigger> </AlertDialogTrigger>

View File

@ -99,12 +99,12 @@ export const QuoteEdit = () => {
}, },
unit_price: { unit_price: {
amount: null, amount: null,
scale: 4, scale: 2,
currency_code: data?.currency_code ?? quoteCurrency.code, currency_code: data?.currency_code ?? quoteCurrency.code,
}, },
subtotal_price: { subtotal_price: {
amount: null, amount: null,
scale: 4, scale: 2,
currency_code: data?.currency_code ?? quoteCurrency.code, currency_code: data?.currency_code ?? quoteCurrency.code,
}, },
discount: { discount: {
@ -113,7 +113,7 @@ export const QuoteEdit = () => {
}, },
total_price: { total_price: {
amount: null, amount: null,
scale: 4, scale: 2,
currency_code: data?.currency_code ?? quoteCurrency.code, currency_code: data?.currency_code ?? quoteCurrency.code,
}, },
}, },
@ -266,7 +266,7 @@ export const QuoteEdit = () => {
<h1 className='flex-1 text-xl font-semibold tracking-tight shrink-0 whitespace-nowrap sm:grow-0'> <h1 className='flex-1 text-xl font-semibold tracking-tight shrink-0 whitespace-nowrap sm:grow-0'>
{t("quotes.edit.title")} {data.reference} {t("quotes.edit.title")} {data.reference}
</h1> </h1>
<ColorBadge label={data.status} className='ml-auto sm:ml-0' /> <ColorBadge label={t(`quotes.status.${data.status}`)} className='ml-auto sm:ml-0' />
<div className='items-center hidden gap-2 md:ml-auto md:flex'> <div className='items-center hidden gap-2 md:ml-auto md:flex'>
<CancelButton <CancelButton

View File

@ -40,7 +40,13 @@ function stringToColorPair(str: string) {
return [textColor, bgColor]; return [textColor, bgColor];
} }
export const ColorBadge = ({ label, className }: { label: string; className?: string }) => { export type ColorBadgeProps = {
label: string;
className?: string;
bgcolor?: string;
};
export const ColorBadge = ({ label, className }: ColorBadgeProps) => {
const [color, backgroundColor] = stringToColorPair(label); const [color, backgroundColor] = stringToColorPair(label);
return ( return (

View File

@ -14,7 +14,7 @@ export const LoadingOverlay = ({
return ( return (
<div <div
className={ className={
"fixed top-0 bottom-0 left-0 right-0 z-50 w-full h-screen overflow-hidden flex justify-center bg-secondary-foreground/85" "fixed top-0 bottom-0 left-0 right-0 z-50 w-full h-screen overflow-hidden flex justify-center"
} }
{...props} {...props}
> >

View File

@ -8,9 +8,9 @@ type ProctectRouteProps = {
export const ProtectedRoute = ({ children }: ProctectRouteProps) => { export const ProtectedRoute = ({ children }: ProctectRouteProps) => {
const { isSuccess, data: { authenticated, redirectTo } = {} } = useIsLoggedIn(); const { isSuccess, data: { authenticated, redirectTo } = {} } = useIsLoggedIn();
//const { data: profile, ...profileStatus } = useGetProfile(); /*const { data: profile, ...profileStatus } = useGetProfile();
/*const { i18n } = useTranslation(); const { i18n } = useTranslation();
const [langCode, setLangCode] = useState(i18n.language); const [langCode, setLangCode] = useState(i18n.language);
if (i18n.language !== langCode) { if (i18n.language !== langCode) {

View File

@ -63,7 +63,7 @@ export const calculateQuoteTotals = (quote: any, force: boolean = false) => {
export const calculateQuoteItemsTotals = (items: any[]) => { export const calculateQuoteItemsTotals = (items: any[]) => {
let totalPrice = MoneyValue.create({ let totalPrice = MoneyValue.create({
amount: 0, amount: 0,
scale: 4, scale: 2,
}).object; }).object;
items && items &&
@ -89,11 +89,11 @@ export const calculateQuoteItemTotals = (item: any) => {
}).object, }).object,
unitPrice: MoneyValue.create({ unitPrice: MoneyValue.create({
amount: unit_price_dto.amount, amount: unit_price_dto.amount,
scale: 4, scale: 2,
}).object, }).object,
subtotalPrice: MoneyValue.create({ subtotalPrice: MoneyValue.create({
amount: null, amount: null,
scale: 4, scale: 2,
}).object, }).object,
discount: Percentage.create({ discount: Percentage.create({
amount: discount_dto.amount, amount: discount_dto.amount,
@ -101,7 +101,7 @@ export const calculateQuoteItemTotals = (item: any) => {
}).object, }).object,
totalPrice: MoneyValue.create({ totalPrice: MoneyValue.create({
amount: null, amount: null,
scale: 4, scale: 2,
}).object, }).object,
}; };
} }

View File

@ -50,8 +50,8 @@ export const useCustomLocalization = (props: UseLocalizationProps) => {
const result = new Intl.NumberFormat("es", { const result = new Intl.NumberFormat("es", {
/*minimumSignificantDigits: scale, /*minimumSignificantDigits: scale,
maximumSignificantDigits: scale, maximumSignificantDigits: scale,*/
minimumFractionDigits: scale,*/ minimumFractionDigits: scale,
useGrouping: true, useGrouping: true,
}).format(amount === null ? 0 : adjustPrecision({ amount, scale })); }).format(amount === null ? 0 : adjustPrecision({ amount, scale }));

View File

@ -1,6 +1,6 @@
{ {
"name": "uecko-presupuestador", "name": "uecko-presupuestador",
"version": "1.0.2", "version": "1.0.3",
"author": "Rodax Software <dev@rodax-software.com>", "author": "Rodax Software <dev@rodax-software.com>",
"license": "ISC", "license": "ISC",
"private": true, "private": true,

View File

@ -1,7 +1,7 @@
{ {
"name": "@uecko-presupuestador/server", "name": "@uecko-presupuestador/server",
"private": true, "private": true,
"version": "1.0.0", "version": "1.0.3",
"author": "Rodax Software <dev@rodax-software.com>", "author": "Rodax Software <dev@rodax-software.com>",
"main": "./src/index.ts", "main": "./src/index.ts",
"scripts": { "scripts": {

View File

@ -20,10 +20,10 @@ class ArticleMapper
const id_article = this.mapsValue(source, "id_article", ArticleIdentifier.create); const id_article = this.mapsValue(source, "id_article", ArticleIdentifier.create);
const reference = this.mapsValue(source, "reference", Slug.create); const reference = this.mapsValue(source, "reference", Slug.create);
const points = this.mapsValue(source, "points", (value: any) => const points = this.mapsValue(source, "points", (value: any) =>
Quantity.create({ amount: value, scale: 4 }) Quantity.create({ amount: value, scale: 2 })
); );
const retail_price = this.mapsValue(source, "retail_price", (value: any) => const retail_price = this.mapsValue(source, "retail_price", (value: any) =>
UnitPrice.create({ amount: value, scale: 4 }) UnitPrice.create({ amount: value, scale: 2 })
); );
const language = this.mapsValue(source, "lang_code", Language.createFromCode); const language = this.mapsValue(source, "lang_code", Language.createFromCode);

View File

@ -92,9 +92,8 @@ export class Quote extends AggregateRoot<IQuoteProps> implements IQuote {
.toArray() .toArray()
.reduce<MoneyValue>( .reduce<MoneyValue>(
(accumulator, currentItem) => accumulator.add(currentItem.totalPrice), (accumulator, currentItem) => accumulator.add(currentItem.totalPrice),
MoneyValue.create({ amount: 0, scale: 4, currencyCode: this.currency.code }).object MoneyValue.create({ amount: 0, scale: 2, currencyCode: this.currency.code }).object
) );
.convertScale(2);
return result; return result;
}; };

View File

@ -54,7 +54,7 @@ export class QuoteItem extends Entity<IQuoteItemProps> implements IQuoteItem {
get subtotalPrice(): MoneyValue { get subtotalPrice(): MoneyValue {
return this.quantity.isNull() || this.unitPrice.isNull() return this.quantity.isNull() || this.unitPrice.isNull()
? MoneyValue.create({ amount: null, scale: 4 }).object ? MoneyValue.create({ amount: null, scale: 2 }).object
: this.unitPrice.multiply(this.quantity.toNumber()); : this.unitPrice.multiply(this.quantity.toNumber());
} }
@ -64,7 +64,7 @@ export class QuoteItem extends Entity<IQuoteItemProps> implements IQuoteItem {
get totalPrice(): MoneyValue { get totalPrice(): MoneyValue {
return this.subtotalPrice.isNull() return this.subtotalPrice.isNull()
? MoneyValue.create({ amount: null, scale: 4 }).object ? MoneyValue.create({ amount: null, scale: 2 }).object
: this.subtotalPrice.subtract(this.subtotalPrice.percentage(this.discount.toNumber())); : this.subtotalPrice.subtract(this.subtotalPrice.percentage(this.discount.toNumber()));
} }
} }

View File

@ -55,9 +55,9 @@ const quoteItemPresenter = (
id_article: item.idArticle.toString(), id_article: item.idArticle.toString(),
description: item.description.toString(), description: item.description.toString(),
quantity: item.quantity.convertScale(2).toObject(), quantity: item.quantity.convertScale(2).toObject(),
unit_price: item.unitPrice.convertScale(4).toObject(), unit_price: item.unitPrice.convertScale(2).toObject(),
subtotal_price: item.subtotalPrice.convertScale(4).toObject(), subtotal_price: item.subtotalPrice.convertScale(2).toObject(),
discount: item.discount.convertScale(2).toObject(), discount: item.discount.convertScale(2).toObject(),
total_price: item.totalPrice.convertScale(4).toObject(), total_price: item.totalPrice.convertScale(2).toObject(),
})) }))
: []; : [];

View File

@ -57,9 +57,9 @@ const quoteItemPresenter = (
id_article: item.idArticle.toString(), id_article: item.idArticle.toString(),
description: item.description.toString(), description: item.description.toString(),
quantity: item.quantity.convertScale(2).toObject(), quantity: item.quantity.convertScale(2).toObject(),
unit_price: item.unitPrice.convertScale(4).toObject(), unit_price: item.unitPrice.convertScale(2).toObject(),
subtotal_price: item.subtotalPrice.convertScale(4).toObject(), subtotal_price: item.subtotalPrice.convertScale(2).toObject(),
discount: item.discount.convertScale(2).toObject(), discount: item.discount.convertScale(2).toObject(),
total_price: item.totalPrice.convertScale(4).toObject(), total_price: item.totalPrice.convertScale(2).toObject(),
})) }))
: []; : [];

View File

@ -55,9 +55,9 @@ const quoteItemPresenter = (
id_article: item.idArticle.toString(), id_article: item.idArticle.toString(),
description: item.description.toString(), description: item.description.toString(),
quantity: item.quantity.convertScale(2).toObject(), quantity: item.quantity.convertScale(2).toObject(),
unit_price: item.unitPrice.convertScale(4).toObject(), unit_price: item.unitPrice.convertScale(2).toObject(),
subtotal_price: item.subtotalPrice.convertScale(4).toObject(), subtotal_price: item.subtotalPrice.convertScale(2).toObject(),
discount: item.discount.convertScale(2).toObject(), discount: item.discount.convertScale(2).toObject(),
total_price: item.totalPrice.convertScale(4).toObject(), total_price: item.totalPrice.convertScale(2).toObject(),
})) }))
: []; : [];

View File

@ -38,7 +38,7 @@ class QuoteItemMapper
MoneyValue.create({ MoneyValue.create({
amount: unit_price, amount: unit_price,
currencyCode: sourceParent.currency_code, currencyCode: sourceParent.currency_code,
scale: 4, scale: 2,
}) })
), ),
@ -46,7 +46,7 @@ class QuoteItemMapper
MoneyValue.create({ MoneyValue.create({
amount: subtotal_price, amount: subtotal_price,
currencyCode: sourceParent.currency_code, currencyCode: sourceParent.currency_code,
scale: 4, scale: 2,
}) })
), ),
*/ */
@ -62,7 +62,7 @@ class QuoteItemMapper
MoneyValue.create({ MoneyValue.create({
amount: total_price, amount: total_price,
currencyCode: sourceParent.currency_code, currencyCode: sourceParent.currency_code,
scale: 4, scale: 2,
}) })
),*/ ),*/
}; };
@ -89,10 +89,10 @@ class QuoteItemMapper
id_article: source.idArticle.toPrimitive(), id_article: source.idArticle.toPrimitive(),
description: source.description.toPrimitive(), description: source.description.toPrimitive(),
quantity: source.quantity.convertScale(2).toPrimitive(), quantity: source.quantity.convertScale(2).toPrimitive(),
unit_price: source.unitPrice.convertScale(4).toPrimitive(), unit_price: source.unitPrice.convertScale(2).toPrimitive(),
subtotal_price: source.subtotalPrice.convertScale(4).toPrimitive(), subtotal_price: source.subtotalPrice.convertScale(2).toPrimitive(),
discount: source.discount.convertScale(2).toPrimitive(), discount: source.discount.convertScale(2).toPrimitive(),
total_price: source.totalPrice.convertScale(4).toPrimitive(), total_price: source.totalPrice.convertScale(2).toPrimitive(),
}; };
} }
} }

View File

@ -8,9 +8,11 @@ export interface IUnitPriceProps {
scale: number; scale: number;
} }
export const DEFAULT_UNIT_PRICE_SCALE = 2;
export class UnitPrice extends MoneyValue { export class UnitPrice extends MoneyValue {
public static create(props: IUnitPriceProps) { public static create(props: IUnitPriceProps) {
const { amount, currencyCode, scale = 4 } = props; const { amount, currencyCode, scale = DEFAULT_UNIT_PRICE_SCALE } = props;
const _unitPriceOrError = MoneyValue.create({ const _unitPriceOrError = MoneyValue.create({
amount, amount,
currencyCode, currencyCode,
@ -20,7 +22,7 @@ export class UnitPrice extends MoneyValue {
return _unitPriceOrError; return _unitPriceOrError;
} }
const _unitPrice = _unitPriceOrError.object.convertScale(4); const _unitPrice = _unitPriceOrError.object.convertScale(DEFAULT_UNIT_PRICE_SCALE);
return Result.ok<UnitPrice>(_unitPrice); return Result.ok<UnitPrice>(_unitPrice);
} }