From 6a7ad76f901b030c67c67b9b23b67f98dd359b44 Mon Sep 17 00:00:00 2001 From: GeiserX <9169332+GeiserX@users.noreply.github.com> Date: Tue, 26 May 2026 18:07:54 +0200 Subject: [PATCH] fix(ui): correct FX casilla numbers to match Renta Web 2025 MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Renta Web uses 1633/1637 for FX transmission/acquisition values, not 1626/1631. The old numbers conflicted with Renta Web's date fields (1631=fecha transmisión, 1632=fecha adquisición). --- src/cli/index.ts | 8 ++++---- src/generators/csv.ts | 4 ++-- src/generators/pdf-web.ts | 6 +++--- src/i18n/locales/ca.ts | 2 +- src/i18n/locales/en.ts | 2 +- src/i18n/locales/es.ts | 2 +- src/i18n/locales/eu.ts | 2 +- src/i18n/locales/gl.ts | 2 +- src/types/tax.ts | 8 ++++---- src/web/casilla-detail.ts | 6 +++--- src/web/docs.html | 2 +- 11 files changed, 22 insertions(+), 22 deletions(-) diff --git a/src/cli/index.ts b/src/cli/index.ts index db4a5a0..c021b74 100644 --- a/src/cli/index.ts +++ b/src/cli/index.ts @@ -440,8 +440,8 @@ function formatReport(report: ReturnType) { "0027_intereses_cuentas": report.interest.earned.toFixed(2), "0327_valor_transmision": report.capitalGains.transmissionValue.toFixed(2), "0328_valor_adquisicion": report.capitalGains.acquisitionValue.toFixed(2), - "1626_valor_transmision_fx": report.fxGains.transmissionValue.toFixed(2), - "1631_valor_adquisicion_fx": report.fxGains.acquisitionValue.toFixed(2), + "1633_valor_transmision_fx": report.fxGains.transmissionValue.toFixed(2), + "1637_valor_adquisicion_fx": report.fxGains.acquisitionValue.toFixed(2), "0588_deduccion_doble_imposicion": report.doubleTaxation.deduction.toFixed(2), }, resumen: { @@ -515,8 +515,8 @@ function printSummary(report: ReturnType) { if (report.fxGains.disposals.length > 0) { console.error(""); console.error(" GANANCIAS FX — MONEDA EXTRANJERA (Art. 37.1.l)"); - console.error(` Casilla 1626 (Valor transmisión): ${report.fxGains.transmissionValue.toFixed(2)} EUR`); - console.error(` Casilla 1631 (Valor adquisición): ${report.fxGains.acquisitionValue.toFixed(2)} EUR`); + console.error(` Casilla 1633 (Valor transmisión): ${report.fxGains.transmissionValue.toFixed(2)} EUR`); + console.error(` Casilla 1637 (Valor adquisición): ${report.fxGains.acquisitionValue.toFixed(2)} EUR`); console.error(` Ganancia/Pérdida neta FX: ${report.fxGains.netGainLoss.toFixed(2)} EUR`); } console.error(""); diff --git a/src/generators/csv.ts b/src/generators/csv.ts index 6bfd15f..e1345fe 100644 --- a/src/generators/csv.ts +++ b/src/generators/csv.ts @@ -72,8 +72,8 @@ export function formatCsv(report: TaxSummary): string { lines.push("Casilla,Concepto,Valor_EUR"); lines.push(`0327,Valor de transmision,${report.capitalGains.transmissionValue.toFixed(2)}`); lines.push(`0328,Valor de adquisicion,${report.capitalGains.acquisitionValue.toFixed(2)}`); - lines.push(`1626,Valor de transmision FX,${report.fxGains.transmissionValue.toFixed(2)}`); - lines.push(`1631,Valor de adquisicion FX,${report.fxGains.acquisitionValue.toFixed(2)}`); + lines.push(`1633,Valor de transmision FX,${report.fxGains.transmissionValue.toFixed(2)}`); + lines.push(`1637,Valor de adquisicion FX,${report.fxGains.acquisitionValue.toFixed(2)}`); lines.push(`0029,Dividendos brutos,${report.dividends.grossIncome.toFixed(2)}`); lines.push(`—,Intereses pagados al broker (margen no deducible — informativo),${report.interest.paid.toFixed(2)}`); lines.push(`0027,Intereses de cuentas,${report.interest.earned.toFixed(2)}`); diff --git a/src/generators/pdf-web.ts b/src/generators/pdf-web.ts index a4568fd..8216298 100644 --- a/src/generators/pdf-web.ts +++ b/src/generators/pdf-web.ts @@ -103,10 +103,10 @@ export async function generatePdfWebReport( ["0588", t("casilla.double_taxation"), eur(report.doubleTaxation.deduction)], ]; - // FX gains (Casillas 1626/1631) — only shown when multi-currency FX events exist + // FX gains (Casillas 1633/1637) — only shown when multi-currency FX events exist if (report.fxGains.disposals.length > 0) { - casillasBody.push(["1626", t("casilla.fx_transmission_value"), eur(report.fxGains.transmissionValue)]); - casillasBody.push(["1631", t("casilla.fx_acquisition_value"), eur(report.fxGains.acquisitionValue)]); + casillasBody.push(["1633", t("casilla.fx_transmission_value"), eur(report.fxGains.transmissionValue)]); + casillasBody.push(["1637", t("casilla.fx_acquisition_value"), eur(report.fxGains.acquisitionValue)]); casillasBody.push(["", t("casilla.fx_net_gain_loss"), eur(report.fxGains.netGainLoss)]); } diff --git a/src/i18n/locales/ca.ts b/src/i18n/locales/ca.ts index 25ce3c5..110f73a 100644 --- a/src/i18n/locales/ca.ts +++ b/src/i18n/locales/ca.ts @@ -164,7 +164,7 @@ const ca: TranslationKeys = { "profile.phone_label": "Telèfon:", "profile.phone_placeholder": "600123456", "profile.monodivisa_label": "Mode simplificat (monodivisa EUR)", - "profile.monodivisa_detail": "No calcula guanys per tipus de canvi de forma separada (caselles 1626/1631). Compatible amb Autodeclaro, Taxdown i altres serveis que tracten totes les operacions com a moneda única EUR.", + "profile.monodivisa_detail": "No calcula guanys per tipus de canvi de forma separada (caselles 1633/1637). Compatible amb Autodeclaro, Taxdown i altres serveis que tracten totes les operacions com a moneda única EUR.", "profile.monodivisa_warning": "⚠ Aquest mode pot distorsionar els guanys patrimonials declarats (infraestimar o sobreestimar). El mode complet (per defecte) és més rigorós segons l'Art. 37.1.l LIRPF (DGT V2324-10).", "profile.saved": "Perfil desat", "profile.save_btn": "Desar perfil", diff --git a/src/i18n/locales/en.ts b/src/i18n/locales/en.ts index d886046..0c42921 100644 --- a/src/i18n/locales/en.ts +++ b/src/i18n/locales/en.ts @@ -165,7 +165,7 @@ const en: TranslationKeys = { "profile.phone_label": "Phone:", "profile.phone_placeholder": "600123456", "profile.monodivisa_label": "Simplified mode (single-currency EUR)", - "profile.monodivisa_detail": "Does not calculate FX gains separately (casillas 1626/1631). Compatible with Autodeclaro, Taxdown, and other services that treat all operations as single-currency EUR.", + "profile.monodivisa_detail": "Does not calculate FX gains separately (casillas 1633/1637). Compatible with Autodeclaro, Taxdown, and other services that treat all operations as single-currency EUR.", "profile.monodivisa_warning": "⚠ This mode may distort reported capital gains (understate or overstate). The full mode (default) is more rigorous per Art. 37.1.l LIRPF (DGT V2324-10).", "profile.saved": "Profile saved", "profile.save_btn": "Save profile", diff --git a/src/i18n/locales/es.ts b/src/i18n/locales/es.ts index e12fac0..dac29cc 100644 --- a/src/i18n/locales/es.ts +++ b/src/i18n/locales/es.ts @@ -176,7 +176,7 @@ const es = { "profile.phone_label": "Teléfono:", "profile.phone_placeholder": "600123456", "profile.monodivisa_label": "Modo simplificado (monodivisa EUR)", - "profile.monodivisa_detail": "No calcula ganancias por tipo de cambio de forma separada (casillas 1626/1631). Compatible con el enfoque de Autodeclaro, Taxdown y otros servicios que tratan todas las operaciones como moneda única EUR.", + "profile.monodivisa_detail": "No calcula ganancias por tipo de cambio de forma separada (casillas 1633/1637). Compatible con el enfoque de Autodeclaro, Taxdown y otros servicios que tratan todas las operaciones como moneda única EUR.", "profile.monodivisa_warning": "⚠ Este modo puede distorsionar las ganancias patrimoniales declaradas (infraestimar o sobreestimar). El modo completo (por defecto) es más riguroso según el Art. 37.1.l LIRPF (DGT V2324-10).", "profile.saved": "Perfil guardado", "profile.save_btn": "Guardar perfil", diff --git a/src/i18n/locales/eu.ts b/src/i18n/locales/eu.ts index f788d43..eb8f3cd 100644 --- a/src/i18n/locales/eu.ts +++ b/src/i18n/locales/eu.ts @@ -164,7 +164,7 @@ const eu: TranslationKeys = { "profile.phone_label": "Telefonoa:", "profile.phone_placeholder": "600123456", "profile.monodivisa_label": "Modu sinplifikatua (monodibisa EUR)", - "profile.monodivisa_detail": "Ez ditu kanbio-tasaren irabaziak bereizita kalkulatzen (1626/1631 laukitxoak). Autodeclaro, Taxdown eta eragiketa guztiak EUR moneta bakar gisa tratatzen dituzten beste zerbitzu batzuekin bateragarria.", + "profile.monodivisa_detail": "Ez ditu kanbio-tasaren irabaziak bereizita kalkulatzen (1633/1637 laukitxoak). Autodeclaro, Taxdown eta eragiketa guztiak EUR moneta bakar gisa tratatzen dituzten beste zerbitzu batzuekin bateragarria.", "profile.monodivisa_warning": "⚠ Modu honek adierazitako ondare-irabaziak distortsionatu ditzake (gutxietsi edo gehiegietsi). Modu osoa (lehenetsita) zorrotzagoa da 37.1.l Art. LIRPF (DGT V2324-10) arabera.", "profile.saved": "Profila gordeta", "profile.save_btn": "Profila gorde", diff --git a/src/i18n/locales/gl.ts b/src/i18n/locales/gl.ts index 8786d20..a6519b5 100644 --- a/src/i18n/locales/gl.ts +++ b/src/i18n/locales/gl.ts @@ -164,7 +164,7 @@ const gl: TranslationKeys = { "profile.phone_label": "Teléfono:", "profile.phone_placeholder": "600123456", "profile.monodivisa_label": "Modo simplificado (monodivisa EUR)", - "profile.monodivisa_detail": "Non calcula ganancias por tipo de cambio de forma separada (casillas 1626/1631). Compatible con Autodeclaro, Taxdown e outros servizos que tratan todas as operacións como moeda única EUR.", + "profile.monodivisa_detail": "Non calcula ganancias por tipo de cambio de forma separada (casillas 1633/1637). Compatible con Autodeclaro, Taxdown e outros servizos que tratan todas as operacións como moeda única EUR.", "profile.monodivisa_warning": "⚠ Este modo pode distorsionar as ganancias patrimoniais declaradas (infraestimar ou sobreestimar). O modo completo (por defecto) é máis rigoroso segundo o Art. 37.1.l LIRPF (DGT V2324-10).", "profile.saved": "Perfil gardado", "profile.save_btn": "Gardar perfil", diff --git a/src/types/tax.ts b/src/types/tax.ts index a24baa7..9fd1b4c 100644 --- a/src/types/tax.ts +++ b/src/types/tax.ts @@ -154,13 +154,13 @@ export interface TaxSummary { byCountry: Record; }; - /** FX gains: Ganancias/pérdidas por transmisión de moneda extranjera (Casillas 1626/1631) */ + /** FX gains: Ganancias/pérdidas por transmisión de moneda extranjera (Casillas 1633/1637) */ fxGains: { - /** Casilla 1626: Valor de transmisión (FX) */ + /** Casilla 1633: Valor de transmisión (FX) */ transmissionValue: Decimal; - /** Casilla 1631: Valor de adquisición (FX) */ + /** Casilla 1637: Valor de adquisición (FX) */ acquisitionValue: Decimal; - /** Net gain/loss (1626 - 1631) */ + /** Net gain/loss (1633 - 1637) */ netGainLoss: Decimal; /** Individual FX disposals */ disposals: FxDisposal[]; diff --git a/src/web/casilla-detail.ts b/src/web/casilla-detail.ts index 493d0f8..fc54f09 100644 --- a/src/web/casilla-detail.ts +++ b/src/web/casilla-detail.ts @@ -114,7 +114,7 @@ function renderDoubleTaxDetail(report: TaxSummary): string { `; } -/** Render a detail table of FX disposals for casilla 1626/1631 drill-down. */ +/** Render a detail table of FX disposals for casilla 1633/1637 drill-down. */ function renderFxDisposalsDetail(disposals: FxDisposal[], label: string): string { if (disposals.length === 0) return `

${t("casilla.no_operations")}

`; return ` @@ -154,14 +154,14 @@ const CASILLAS: CasillaConfig[] = [ getDetail: (r) => renderDisposalsDetail(r.capitalGains.disposals, t("casilla.acquisition_value")), }, { - code: "1626", + code: "1633", i18nKey: "casilla.fx_transmission_value", getValue: (r) => r.fxGains.transmissionValue.toFixed(2), getClass: () => "", getDetail: (r) => renderFxDisposalsDetail(r.fxGains.disposals, t("casilla.fx_transmission_value")), }, { - code: "1631", + code: "1637", i18nKey: "casilla.fx_acquisition_value", getValue: (r) => r.fxGains.acquisitionValue.toFixed(2), getClass: () => "", diff --git a/src/web/docs.html b/src/web/docs.html index 26a03b0..8faa912 100644 --- a/src/web/docs.html +++ b/src/web/docs.html @@ -962,7 +962,7 @@

Forex (CASH) — Art. 37.1.l LIRPF

Las operaciones de compraventa de divisas tributan como ganancias y pérdidas patrimoniales (DGT V2324-10, Art. 37.1.l LIRPF). DeclaRenta implementa un motor FX FIFO independiente que genera dos eventos fiscales al operar en divisa extranjera:

  1. Ganancia/pérdida del valor (casillas 0327/0328): calculada sobre el precio del activo × tipo ECB en cada fecha.
  2. -
  3. Ganancia/pérdida FX (casillas 1626/1631): diferencia entre el tipo de cambio al adquirir la divisa y el tipo al disponer de ella.
  4. +
  5. Ganancia/pérdida FX (casillas 1633/1637): diferencia entre el tipo de cambio al adquirir la divisa y el tipo al disponer de ella.

Cada adquisición de divisa extranjera (depósito EUR→USD, venta de acciones que genera USD) crea un lote en la cola FIFO de esa divisa. Cada disposición (conversión USD→EUR, compra de acciones en USD) consume lotes por orden cronológico.

Las conversiones automáticas del broker para liquidación (FXCONV) se excluyen automáticamente — solo las operaciones de forex deliberadas generan eventos fiscales.