* feat(packs): konteringspaket as validated data files, ported losslessly The 26 system booking templates lived inside migration 20260413160000. Under the never-modify-a-shipped-migration rule that froze them: correcting a wrong BAS account or a Swedish typo needed a whole new migration, and nothing checked that a seeded account existed in the chart or that a template balanced. #1321 was exactly that failure with seeded chart names. They are now one YAML file per pattern under packs/, with a Zod contract and a CI gate. A correction becomes a one-line edit plus a green run. The port is proven lossless, not asserted. The test fixture was read out of a Postgres with all 548 migrations applied, so it is the exact JSONB production holds; lib/packs/__tests__/port-is-lossless.test.ts asserts the YAML reproduces it by value. Phase 2b can swap the seeded rows for the loader as a no-op. The gate checks what makes a pack CORRECT, not just well-formed, because #1321 was structurally valid and still wrong: every account must exist in BAS 2026, and every pack must balance at five probe amounts through the real applyTemplate() rather than a reimplementation. Account numbers validate through lib/invariants, so a pack cannot disagree with the API or the SIE importer about what an account number is. Doing that immediately found four pre-existing breakages in the shipped templates: loneutbetalning debits total 1.42x the amount against a 1.0 credit: it can never post periodiseringsfond-avsattning-ab account 2113 is not in BAS 2026 and is not periodiseringsfond-aterforing-ab seeded into any company chart preliminar-f-skatt-ef account 2012, same problem These are quarantined in KNOWN_BROKEN, not fixed and not hidden: a quarantined pack's findings are warnings, any NEW finding fails the build, and the validator fails if a quarantined pack turns out to be clean, so the list may only shrink. Each is a Swedish accounting content change to a user-facing template, which deserves its own review rather than riding along inside a file-format change. Five shipped descriptions contain em dashes, preserved verbatim and pinned by a test: a lossless port must not silently rewrite user-visible strings. js-yaml is promoted from a transitive dependency to a declared one (MIT, already in node_modules), so the catalogue does not depend on it by accident. Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com> * fix(deps): regenerate package-lock.json with npm 10 to match CI `npm ci` failed on every job with "Missing: @swc/helpers@0.5.23 from lock file". The lockfile was written by local npm 11.6.0; CI runs npm 10.8.2 on node 20, and npm 11 emits a tree npm 10 reads as out of sync. Regenerated with `npx npm@10 install --package-lock-only`, which cuts the diff from a sprawling rewrite down to the three entries this branch actually adds (js-yaml, @types/js-yaml, and the @swc/helpers entry npm 11 had dropped). Verified with `npx npm@10 ci --dry-run`. This is the documented gotcha for this repo: regenerate lockfiles with npx npm@10, never with a local npm 11. Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com> --------- Co-authored-by: Jakob Wennberg <311770904+jakobwennberg-oss@users.noreply.github.com> Co-authored-by: Claude Opus 5 (1M context) <noreply@anthropic.com>
631 lines
15 KiB
JSON
631 lines
15 KiB
JSON
[
|
|
{
|
|
"name": "Försäljning EU-tjänster (B2B)",
|
|
"description": "Tjänsteförsäljning till annat EU-land (B2B). Ingen moms — kunden redovisar omvänd skattskyldighet.",
|
|
"category": "eu_trade",
|
|
"entity_type": "all",
|
|
"lines": [
|
|
{
|
|
"side": "debit",
|
|
"type": "settlement",
|
|
"label": "Kundfordringar",
|
|
"ratio": 1.0,
|
|
"account": "1510"
|
|
},
|
|
{
|
|
"side": "credit",
|
|
"type": "business",
|
|
"label": "Försäljning tjänster EU",
|
|
"ratio": 1.0,
|
|
"account": "3308"
|
|
}
|
|
]
|
|
},
|
|
{
|
|
"name": "Försäljning export (utanför EU)",
|
|
"description": "Försäljning till land utanför EU. Momsfritt.",
|
|
"category": "eu_trade",
|
|
"entity_type": "all",
|
|
"lines": [
|
|
{
|
|
"side": "debit",
|
|
"type": "settlement",
|
|
"label": "Kundfordringar",
|
|
"ratio": 1.0,
|
|
"account": "1510"
|
|
},
|
|
{
|
|
"side": "credit",
|
|
"type": "business",
|
|
"label": "Försäljning export",
|
|
"ratio": 1.0,
|
|
"account": "3305"
|
|
}
|
|
]
|
|
},
|
|
{
|
|
"name": "Inköp EU-tjänster, omvänd moms 25%",
|
|
"description": "Köp av tjänster från annat EU-land. Omvänd skattskyldighet — du redovisar både utgående och ingående moms.",
|
|
"category": "eu_trade",
|
|
"entity_type": "all",
|
|
"lines": [
|
|
{
|
|
"side": "debit",
|
|
"type": "business",
|
|
"label": "IT-tjänster",
|
|
"ratio": 1.0,
|
|
"account": "6540"
|
|
},
|
|
{
|
|
"side": "credit",
|
|
"type": "vat",
|
|
"label": "Utgående moms omvänd skattskyldighet 25%",
|
|
"account": "2614",
|
|
"vat_rate": 0.25
|
|
},
|
|
{
|
|
"side": "debit",
|
|
"type": "vat",
|
|
"label": "Beräknad ingående moms 25%",
|
|
"account": "2645",
|
|
"vat_rate": 0.25
|
|
},
|
|
{
|
|
"side": "credit",
|
|
"type": "settlement",
|
|
"label": "Företagskonto",
|
|
"ratio": 1.0,
|
|
"account": "1930"
|
|
}
|
|
]
|
|
},
|
|
{
|
|
"name": "Inköp EU-varor, omvänd moms 25%",
|
|
"description": "Köp av varor från annat EU-land. Omvänd skattskyldighet — du redovisar både utgående och ingående moms.",
|
|
"category": "eu_trade",
|
|
"entity_type": "all",
|
|
"lines": [
|
|
{
|
|
"side": "debit",
|
|
"type": "business",
|
|
"label": "Varuinköp",
|
|
"ratio": 1.0,
|
|
"account": "4010"
|
|
},
|
|
{
|
|
"side": "credit",
|
|
"type": "vat",
|
|
"label": "Utgående moms omvänd skattskyldighet 25%",
|
|
"account": "2614",
|
|
"vat_rate": 0.25
|
|
},
|
|
{
|
|
"side": "debit",
|
|
"type": "vat",
|
|
"label": "Beräknad ingående moms 25%",
|
|
"account": "2645",
|
|
"vat_rate": 0.25
|
|
},
|
|
{
|
|
"side": "credit",
|
|
"type": "settlement",
|
|
"label": "Företagskonto",
|
|
"ratio": 1.0,
|
|
"account": "1930"
|
|
}
|
|
]
|
|
},
|
|
{
|
|
"name": "Bankavgift",
|
|
"description": "Månadsavgift eller transaktionsavgift från banken.",
|
|
"category": "financial",
|
|
"entity_type": "all",
|
|
"lines": [
|
|
{
|
|
"side": "debit",
|
|
"type": "business",
|
|
"label": "Bankkostnader",
|
|
"ratio": 1.0,
|
|
"account": "6570"
|
|
},
|
|
{
|
|
"side": "credit",
|
|
"type": "settlement",
|
|
"label": "Företagskonto",
|
|
"ratio": 1.0,
|
|
"account": "1930"
|
|
}
|
|
]
|
|
},
|
|
{
|
|
"name": "Ränteintäkt",
|
|
"description": "Ränta från sparkonto eller bank.",
|
|
"category": "financial",
|
|
"entity_type": "all",
|
|
"lines": [
|
|
{
|
|
"side": "debit",
|
|
"type": "settlement",
|
|
"label": "Företagskonto",
|
|
"ratio": 1.0,
|
|
"account": "1930"
|
|
},
|
|
{
|
|
"side": "credit",
|
|
"type": "business",
|
|
"label": "Ränteintäkter",
|
|
"ratio": 1.0,
|
|
"account": "8311"
|
|
}
|
|
]
|
|
},
|
|
{
|
|
"name": "Räntekostnad",
|
|
"description": "Ränta på lån eller kredit.",
|
|
"category": "financial",
|
|
"entity_type": "all",
|
|
"lines": [
|
|
{
|
|
"side": "debit",
|
|
"type": "business",
|
|
"label": "Räntekostnader",
|
|
"ratio": 1.0,
|
|
"account": "8410"
|
|
},
|
|
{
|
|
"side": "credit",
|
|
"type": "settlement",
|
|
"label": "Företagskonto",
|
|
"ratio": 1.0,
|
|
"account": "1930"
|
|
}
|
|
]
|
|
},
|
|
{
|
|
"name": "Aktieägarlån — insättning",
|
|
"description": "Ägaren sätter in pengar som lån till bolaget.",
|
|
"category": "private_transfer",
|
|
"entity_type": "aktiebolag",
|
|
"lines": [
|
|
{
|
|
"side": "debit",
|
|
"type": "settlement",
|
|
"label": "Företagskonto",
|
|
"ratio": 1.0,
|
|
"account": "1930"
|
|
},
|
|
{
|
|
"side": "credit",
|
|
"type": "business",
|
|
"label": "Skuld till aktieägare",
|
|
"ratio": 1.0,
|
|
"account": "2893"
|
|
}
|
|
]
|
|
},
|
|
{
|
|
"name": "Aktieägarlån — återbetalning",
|
|
"description": "Bolaget betalar tillbaka lån till ägaren.",
|
|
"category": "private_transfer",
|
|
"entity_type": "aktiebolag",
|
|
"lines": [
|
|
{
|
|
"side": "debit",
|
|
"type": "business",
|
|
"label": "Skuld till aktieägare",
|
|
"ratio": 1.0,
|
|
"account": "2893"
|
|
},
|
|
{
|
|
"side": "credit",
|
|
"type": "settlement",
|
|
"label": "Företagskonto",
|
|
"ratio": 1.0,
|
|
"account": "1930"
|
|
}
|
|
]
|
|
},
|
|
{
|
|
"name": "Eget insättning",
|
|
"description": "Privat insättning till företagskontot (enskild firma).",
|
|
"category": "private_transfer",
|
|
"entity_type": "enskild_firma",
|
|
"lines": [
|
|
{
|
|
"side": "debit",
|
|
"type": "settlement",
|
|
"label": "Företagskonto",
|
|
"ratio": 1.0,
|
|
"account": "1930"
|
|
},
|
|
{
|
|
"side": "credit",
|
|
"type": "business",
|
|
"label": "Egna insättningar",
|
|
"ratio": 1.0,
|
|
"account": "2018"
|
|
}
|
|
]
|
|
},
|
|
{
|
|
"name": "Eget uttag",
|
|
"description": "Privat uttag från företagskontot (enskild firma).",
|
|
"category": "private_transfer",
|
|
"entity_type": "enskild_firma",
|
|
"lines": [
|
|
{
|
|
"side": "debit",
|
|
"type": "business",
|
|
"label": "Egna uttag",
|
|
"ratio": 1.0,
|
|
"account": "2013"
|
|
},
|
|
{
|
|
"side": "credit",
|
|
"type": "settlement",
|
|
"label": "Företagskonto",
|
|
"ratio": 1.0,
|
|
"account": "1930"
|
|
}
|
|
]
|
|
},
|
|
{
|
|
"name": "Utdelning till aktieägare",
|
|
"description": "Utbetalning av beslutad utdelning till aktieägare.",
|
|
"category": "private_transfer",
|
|
"entity_type": "aktiebolag",
|
|
"lines": [
|
|
{
|
|
"side": "debit",
|
|
"type": "business",
|
|
"label": "Outtagen utdelning",
|
|
"ratio": 1.0,
|
|
"account": "2898"
|
|
},
|
|
{
|
|
"side": "credit",
|
|
"type": "settlement",
|
|
"label": "Företagskonto",
|
|
"ratio": 1.0,
|
|
"account": "1930"
|
|
}
|
|
]
|
|
},
|
|
{
|
|
"name": "Representation (avdragsgill, 25% moms)",
|
|
"description": "Extern representation med avdragsgill moms. Max 300 kr/person exkl. moms.",
|
|
"category": "representation",
|
|
"entity_type": "all",
|
|
"lines": [
|
|
{
|
|
"side": "debit",
|
|
"type": "business",
|
|
"label": "Representation avdragsgill",
|
|
"ratio": 0.8,
|
|
"account": "6072"
|
|
},
|
|
{
|
|
"side": "debit",
|
|
"type": "vat",
|
|
"label": "Ingående moms",
|
|
"account": "2641",
|
|
"vat_rate": 0.25
|
|
},
|
|
{
|
|
"side": "credit",
|
|
"type": "settlement",
|
|
"label": "Företagskonto",
|
|
"ratio": 1.0,
|
|
"account": "1930"
|
|
}
|
|
]
|
|
},
|
|
{
|
|
"name": "Arbetsgivaravgifter",
|
|
"description": "Bokföring av arbetsgivaravgifter (31,42% av bruttolön).",
|
|
"category": "salary",
|
|
"entity_type": "aktiebolag",
|
|
"lines": [
|
|
{
|
|
"side": "debit",
|
|
"type": "business",
|
|
"label": "Arbetsgivaravgifter",
|
|
"ratio": 1.0,
|
|
"account": "7510"
|
|
},
|
|
{
|
|
"side": "credit",
|
|
"type": "business",
|
|
"label": "Avräkning sociala avgifter",
|
|
"ratio": 1.0,
|
|
"account": "2731"
|
|
}
|
|
]
|
|
},
|
|
{
|
|
"name": "Löneutbetalning",
|
|
"description": "Utbetalning av nettolön till anställd.",
|
|
"category": "salary",
|
|
"entity_type": "aktiebolag",
|
|
"lines": [
|
|
{
|
|
"side": "debit",
|
|
"type": "business",
|
|
"label": "Personalskatt",
|
|
"ratio": 0.3,
|
|
"account": "2710"
|
|
},
|
|
{
|
|
"side": "debit",
|
|
"type": "business",
|
|
"label": "Upplupna semesterlöner",
|
|
"ratio": 0.12,
|
|
"account": "2920"
|
|
},
|
|
{
|
|
"side": "debit",
|
|
"type": "business",
|
|
"label": "Löner",
|
|
"ratio": 1.0,
|
|
"account": "7010"
|
|
},
|
|
{
|
|
"side": "credit",
|
|
"type": "settlement",
|
|
"label": "Företagskonto",
|
|
"ratio": 1.0,
|
|
"account": "1930"
|
|
}
|
|
]
|
|
},
|
|
{
|
|
"name": "Arbetsgivaravgifter via skattekonto",
|
|
"description": "Arbetsgivaravgifter som dras från skattekontot.",
|
|
"category": "tax_account",
|
|
"entity_type": "all",
|
|
"lines": [
|
|
{
|
|
"side": "debit",
|
|
"type": "business",
|
|
"label": "Avräkning sociala avgifter",
|
|
"ratio": 1.0,
|
|
"account": "2731"
|
|
},
|
|
{
|
|
"side": "credit",
|
|
"type": "settlement",
|
|
"label": "Skattekonto",
|
|
"ratio": 1.0,
|
|
"account": "1630"
|
|
}
|
|
]
|
|
},
|
|
{
|
|
"name": "Insättning skattekonto",
|
|
"description": "Betalning från företagskonto till skattekontot hos Skatteverket.",
|
|
"category": "tax_account",
|
|
"entity_type": "all",
|
|
"lines": [
|
|
{
|
|
"side": "debit",
|
|
"type": "business",
|
|
"label": "Skattekonto",
|
|
"ratio": 1.0,
|
|
"account": "1630"
|
|
},
|
|
{
|
|
"side": "credit",
|
|
"type": "settlement",
|
|
"label": "Företagskonto",
|
|
"ratio": 1.0,
|
|
"account": "1930"
|
|
}
|
|
]
|
|
},
|
|
{
|
|
"name": "Momsbetalning via skattekonto",
|
|
"description": "Moms som dras från skattekontot efter momsdeklaration.",
|
|
"category": "tax_account",
|
|
"entity_type": "all",
|
|
"lines": [
|
|
{
|
|
"side": "debit",
|
|
"type": "business",
|
|
"label": "Redovisningskonto moms",
|
|
"ratio": 1.0,
|
|
"account": "2650"
|
|
},
|
|
{
|
|
"side": "credit",
|
|
"type": "settlement",
|
|
"label": "Skattekonto",
|
|
"ratio": 1.0,
|
|
"account": "1630"
|
|
}
|
|
]
|
|
},
|
|
{
|
|
"name": "Preliminär F-skatt (AB)",
|
|
"description": "Betalning av preliminär bolagsskatt från skattekontot.",
|
|
"category": "tax_account",
|
|
"entity_type": "aktiebolag",
|
|
"lines": [
|
|
{
|
|
"side": "debit",
|
|
"type": "business",
|
|
"label": "Betald F-skatt",
|
|
"ratio": 1.0,
|
|
"account": "2518"
|
|
},
|
|
{
|
|
"side": "credit",
|
|
"type": "settlement",
|
|
"label": "Skattekonto",
|
|
"ratio": 1.0,
|
|
"account": "1630"
|
|
}
|
|
]
|
|
},
|
|
{
|
|
"name": "Preliminär F-skatt (EF)",
|
|
"description": "Betalning av preliminär F-skatt från skattekontot (enskild firma).",
|
|
"category": "tax_account",
|
|
"entity_type": "enskild_firma",
|
|
"lines": [
|
|
{
|
|
"side": "debit",
|
|
"type": "business",
|
|
"label": "Egna skatter",
|
|
"ratio": 1.0,
|
|
"account": "2012"
|
|
},
|
|
{
|
|
"side": "credit",
|
|
"type": "settlement",
|
|
"label": "Skattekonto",
|
|
"ratio": 1.0,
|
|
"account": "1630"
|
|
}
|
|
]
|
|
},
|
|
{
|
|
"name": "Skatteåterbäring",
|
|
"description": "Återbetalning från skattekontot till företagskonto.",
|
|
"category": "tax_account",
|
|
"entity_type": "all",
|
|
"lines": [
|
|
{
|
|
"side": "debit",
|
|
"type": "settlement",
|
|
"label": "Företagskonto",
|
|
"ratio": 1.0,
|
|
"account": "1930"
|
|
},
|
|
{
|
|
"side": "credit",
|
|
"type": "business",
|
|
"label": "Skattekonto",
|
|
"ratio": 1.0,
|
|
"account": "1630"
|
|
}
|
|
]
|
|
},
|
|
{
|
|
"name": "Momsredovisning (nettning)",
|
|
"description": "Nettning av momskonton vid momsdeklaration. Justera konton och belopp efter din deklaration.",
|
|
"category": "vat",
|
|
"entity_type": "all",
|
|
"lines": [
|
|
{
|
|
"side": "debit",
|
|
"type": "business",
|
|
"label": "Utgående moms 25%",
|
|
"ratio": 0.5,
|
|
"account": "2611"
|
|
},
|
|
{
|
|
"side": "credit",
|
|
"type": "business",
|
|
"label": "Ingående moms",
|
|
"ratio": 0.3,
|
|
"account": "2641"
|
|
},
|
|
{
|
|
"side": "credit",
|
|
"type": "business",
|
|
"label": "Redovisningskonto moms",
|
|
"ratio": 0.2,
|
|
"account": "2650"
|
|
}
|
|
]
|
|
},
|
|
{
|
|
"name": "Beräknad bolagsskatt",
|
|
"description": "Bokföring av beräknad inkomstskatt vid bokslut.",
|
|
"category": "year_end",
|
|
"entity_type": "aktiebolag",
|
|
"lines": [
|
|
{
|
|
"side": "debit",
|
|
"type": "business",
|
|
"label": "Skatt på årets resultat",
|
|
"ratio": 1.0,
|
|
"account": "8910"
|
|
},
|
|
{
|
|
"side": "credit",
|
|
"type": "business",
|
|
"label": "Beräknad inkomstskatt",
|
|
"ratio": 1.0,
|
|
"account": "2512"
|
|
}
|
|
]
|
|
},
|
|
{
|
|
"name": "Periodiseringsfond avsättning (AB)",
|
|
"description": "Avsättning till periodiseringsfond vid bokslut. Max 25% av överskottet.",
|
|
"category": "year_end",
|
|
"entity_type": "aktiebolag",
|
|
"lines": [
|
|
{
|
|
"side": "debit",
|
|
"type": "business",
|
|
"label": "Avsättning periodiseringsfond",
|
|
"ratio": 1.0,
|
|
"account": "8811"
|
|
},
|
|
{
|
|
"side": "credit",
|
|
"type": "business",
|
|
"label": "Periodiseringsfond",
|
|
"ratio": 1.0,
|
|
"account": "2113"
|
|
}
|
|
]
|
|
},
|
|
{
|
|
"name": "Periodiseringsfond återföring (AB)",
|
|
"description": "Återföring av periodiseringsfond (senast efter 6 år).",
|
|
"category": "year_end",
|
|
"entity_type": "aktiebolag",
|
|
"lines": [
|
|
{
|
|
"side": "debit",
|
|
"type": "business",
|
|
"label": "Periodiseringsfond",
|
|
"ratio": 1.0,
|
|
"account": "2113"
|
|
},
|
|
{
|
|
"side": "credit",
|
|
"type": "business",
|
|
"label": "Återföring periodiseringsfond",
|
|
"ratio": 1.0,
|
|
"account": "8819"
|
|
}
|
|
]
|
|
},
|
|
{
|
|
"name": "Överavskrivning inventarier",
|
|
"description": "Bokföring av överavskrivning (skillnad räkenskapsenlig vs planenlig).",
|
|
"category": "year_end",
|
|
"entity_type": "aktiebolag",
|
|
"lines": [
|
|
{
|
|
"side": "debit",
|
|
"type": "business",
|
|
"label": "Förändring överavskrivning",
|
|
"ratio": 1.0,
|
|
"account": "8850"
|
|
},
|
|
{
|
|
"side": "credit",
|
|
"type": "business",
|
|
"label": "Ackumulerade överavskrivningar",
|
|
"ratio": 1.0,
|
|
"account": "2150"
|
|
}
|
|
]
|
|
}
|
|
]
|