feat(cartoes): exigir limite e bloquear lançamentos acima do disponível

- campo limite passa a ser NOT NULL DEFAULT 0 no schema (migration 0029)
- validação Zod com requiredDecimalSchema garante valor positivo no formulário
- validateCardLimit() em transactions/actions/core.ts bloqueia criação e edição
  de despesas em cartão que ultrapassem o limite disponível, retornando mensagem
  com o valor exato restante
- tipos Card.limit e Card.limitAvailable deixam de ser nullable
- branch "sem limite registrado" removido de card-item.tsx

Co-Authored-By: Claude Opus 4.7 <noreply@anthropic.com>
This commit is contained in:
Felipe Coutinho
2026-05-02 22:07:56 +00:00
parent 19b5aa00ee
commit 8389752172
11 changed files with 400 additions and 290 deletions

View File

@@ -118,6 +118,8 @@ export default async function Page({ params, searchParams }: PageProps) {
financialAccount.id === card.accountId,
)?.name ?? "Conta";
const limitAmount = Number(card.limit);
const cardDialogData: Card = {
id: card.id,
name: card.name,
@@ -127,19 +129,14 @@ export default async function Page({ params, searchParams }: PageProps) {
dueDay: card.dueDay,
note: card.note ?? null,
logo: card.logo,
limit:
card.limit !== null && card.limit !== undefined
? Number(card.limit)
: null,
limit: limitAmount,
accountId: card.accountId,
accountName,
limitInUse: 0,
limitAvailable: null,
limitAvailable: limitAmount,
};
const { totalAmount, invoiceStatus, paymentDate } = invoiceData;
const limitAmount =
card.limit !== null && card.limit !== undefined ? Number(card.limit) : null;
const periodLabel = `${monthName.charAt(0).toUpperCase()}${monthName.slice(
1,
@@ -163,6 +160,12 @@ export default async function Page({ params, searchParams }: PageProps) {
limitAmount={limitAmount}
invoiceStatus={invoiceStatus}
paymentDate={paymentDate}
defaultPaymentAccountId={card.accountId}
paymentAccountOptions={accountOptions.map((option) => ({
value: option.value,
label: option.label,
logo: option.logo ?? null,
}))}
logo={card.logo}
actions={
<CardDialog