Back to News & Insights
Web Development October 12, 2026 · 12 min read

Modelling Swedish intestate succession in TypeScript

Three classes of heirs, per-stirpes representation, a spouse who inherits first, and exact fractions instead of floats.

Modelling Swedish intestate succession in TypeScript

When someone in Sweden dies without a will, the Inheritance Code (ärvdabalken, SFS 1958:637) decides who gets what. The rules fit on two printed pages. They are also a small, well-defined algorithm: a walk over a family tree with a fixed priority order, equal splits per branch, and a couple of special cases for spouses.

I wrote that algorithm in TypeScript for a free calculator that answers "who inherits?" for Swedish users. This post explains the law for developers who do not read Swedish, and shows how each rule maps to code. The identifiers are Swedish because the output is Swedish, so I translate them as they come up.

The engine is one pure function, vemArver(input) ("who inherits"). No DOM, no I/O. It runs in the browser and under node:test.

Chapter 2 of ärvdabalken defines three classes of relatives (arvsklasser). A class only inherits if every class above it is empty. First class (2 kap. 1 §). The deceased's descendants. Children take equal shares. If a child is dead, that child's descendants step into its place, and each branch takes an equal share. This is called istadarätt, the right of representation. English legal texts call it per stirpes. Second class (2 kap. 2 §). Parents take half each. If a parent is dead, the deceased's siblings share that parent's half, and a dead sibling's descendants step into its place. If there are no siblings or descendants of siblings, a living parent takes everything. Third class (2 kap. 3 §). Grandparents take a quarter each. A dead grandparent's share goes to that grandparent's children (the deceased's aunts and uncles). If there are none, the other grandparent on the same side takes it. If one side has nobody, the other side takes everything.

Then two short rules close it off. 2 kap. 4 § says no other relatives inherit. Cousins get nothing. And 5 kap. 1 § says that if there is no heir under these rules, the estate goes to Allmänna arvsfonden, the state inheritance fund.

Chapter 3 then adds the surviving spouse, who inherits ahead of the children in most cases. More on that below, because it is where most of the interesting logic is.

Before any tree walking, one decision shapes everything else. Shares are fractions, and the answer the user needs is "1/6", not "0.16666666666666666".

Floats fail here in two ways. First, display: a grandchild who takes one sixth must see one sixth. Second, invariants: the shares must sum to exactly 1, and with floats 1/3 + 1/3 + 1/6 + 1/6 is not reliably equal to 1. You end up with epsilon comparisons in your tests, and an epsilon test cannot tell a rounding artefact from a real bug where a branch got the wrong lot.

So the engine carries a tiny rational type and normalises on every construction:

Because every value is reduced and the sign lives in the numerator, equality is a plain field comparison. frac(2, 6) and frac(1, 3) are the same object shape, so eq and deepEqual both work without a custom comparator.

Plain number is enough here. Input counts are clamped to 50 per branch, and the deepest split is roughly a quarter divided by a sibling count, so numerators and denominators stay tiny. If your domain can nest arbitrarily, use bigint for the same code.

Each heir in the result is a line, not a person. A dead child with three children produces one line with antal: 3 (count), a share per person (var) and a share for the whole branch (totalt):

Two details matter. lagrum (the legal citation) travels with every line, so the UI can show "2 kap. 1 § 2 st ärvdabalken (istadarätt)" next to the number. A user, or a lawyer they show it to, can check where each share came from. And key is stable (barn-3, syskon-2), which is what lets the same people be merged when two rules hand them shares.

The first class is a single pass. A child who is alive is a branch. A dead child with living children is a branch. A dead child with no children is not a branch at all, and its share silently goes to the others, because the law divides among branches that exist.

The filter is the whole of the representation rule. Count the branches first, then divide. Two living children and one dead child with two kids gives three branches: 1/3, 1/3, and 1/3 split into 1/6 each. If you divide by the number of children instead of the number of live branches, a childless dead child keeps eating a share that belongs to its siblings.

The second class is easier to reason about if you stop thinking "parents first, then siblings" and start thinking "two halves of the estate, one per parent". Each half is resolved independently: the parent is alive: the parent takes the half the parent is dead: the siblings who share that parent split the half, with representation for dead siblings nobody is left on that side: the half moves to the other side

That framing makes half siblings fall out naturally. 2 kap. 2 § 3 st says half siblings take part only in the share that would have gone to their own parent. A full sibling shares both parents, so a full sibling appears in both halves. A half sibling on the father's side appears only in the father's half.

(mor is mother, far is father, hel is full sibling, halvMor and halvFar are half siblings through the mother or father.)

Want to discuss this further?

Book a free strategy call with our team to see how these insights apply to your specific business goals.

Book a consultation