Skip to content

Import a new generation of the store rather than emptying the old one - #39

Merged
RISCfuture merged 1 commit into
navdata/two-storesfrom
navdata/atomic-install
Sep 9, 2026
Merged

Import a new generation of the store rather than emptying the old one#39
RISCfuture merged 1 commit into
navdata/two-storesfrom
navdata/atomic-install

Conversation

@RISCfuture

@RISCfuture RISCfuture commented Sep 8, 2026

Copy link
Copy Markdown
Contributor

The import deleted the live dataset before writing its replacement, in
many small committed transactions. Anything that stopped it in that
window — a crash, or the system reclaiming the app — left an airport
database that was permanently half there, which for an app that cannot
work without one is not a state to recover from. It is why nav data was
kept off every background path, and why the import had to ask the pilot
to leave the app open.

Each import now writes the next generation of the store to a file of its
own and nothing reads it until it is whole. The switch is one recorded
number, made only once the new store has been opened and found to hold
airports; before that moment the dataset in use has not been touched at
all. So an abandoned import costs a file nobody points at, reclaimed at
the next launch, and resetData and its bounded delete loops are gone
rather than made safe.

A generation is written to a new file rather than over the old one
because a store cannot be replaced underneath a reader: SQLite leaves the
reader on a deleted inode, and the app is not the only process holding
this store — the widget and the App Intents surfaces open it too. Numbers
rise rather than alternate, so a generation an extension still has open
is never reused beneath it.

Cycles are no longer cleared before a download either. They were cleared
first so a failed download would read as out-of-date, which a store the
download never touches gives for free.

Co-Authored-By: Claude Opus 5 (1M context) noreply@anthropic.com
Claude-Session: https://claude.ai/code/session_01471376Uhug2TYZN8RDFGtq


Stack created with GitHub Stacks CLIGive Feedback 💬

🤖 Generated with Claude Code

https://claude.ai/code/session_01471376Uhug2TYZN8RDFGtq

@RISCfuture
RISCfuture force-pushed the navdata/atomic-install branch from 78f584c to e97dca3 Compare September 8, 2026 07:17
@RISCfuture
RISCfuture force-pushed the navdata/atomic-install branch 2 times, most recently from 0115b91 to d097b04 Compare September 8, 2026 08:02
@RISCfuture
RISCfuture force-pushed the navdata/atomic-install branch from d097b04 to bc732a5 Compare September 8, 2026 15:48
@RISCfuture
RISCfuture force-pushed the navdata/atomic-install branch 2 times, most recently from e156fb8 to b04ce39 Compare September 8, 2026 16:26
@RISCfuture
RISCfuture force-pushed the navdata/atomic-install branch 2 times, most recently from db60e58 to 7788f9d Compare September 8, 2026 16:35
@RISCfuture
RISCfuture force-pushed the navdata/atomic-install branch from 7788f9d to d9e3fd2 Compare September 8, 2026 18:09
The import deleted the live dataset before writing its replacement, in
many small committed transactions. Anything that stopped it in that
window — a crash, or the system reclaiming the app — left an airport
database that was permanently half there, which for an app that cannot
work without one is not a state to recover from. It is why nav data was
kept off every background path, and why the import had to ask the pilot
to leave the app open.

Each import now writes the next generation of the store to a file of its
own and nothing reads it until it is whole. The switch is one recorded
number, made only once the new store has been opened and found to hold
airports; before that moment the dataset in use has not been touched at
all. So an abandoned import costs a file nobody points at, reclaimed at
the next launch, and resetData and its bounded delete loops are gone
rather than made safe.

Superseded generations are reclaimed only as a process opens its first
container — however it opened one, including by discarding a bad one.
Reclaiming later would mean deleting a file a container still alive may
be reading, which is the very thing numbering generations avoids.

A generation is written to a new file rather than over the old one
because a store cannot be replaced underneath a reader: SQLite leaves the
reader on a deleted inode, and the app is not the only process holding
this store — the widget and the App Intents surfaces open it too. Numbers
rise rather than alternate, so a generation an extension still has open
is never reused beneath it.

Cycles are no longer cleared before a download either. They were cleared
first so a failed download would read as out-of-date, which a store the
download never touches gives for free.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01471376Uhug2TYZN8RDFGtq
@RISCfuture
RISCfuture force-pushed the navdata/atomic-install branch from d9e3fd2 to f60e56e Compare September 9, 2026 06:38
@RISCfuture
RISCfuture merged commit c47be02 into main Sep 9, 2026
5 checks passed
@RISCfuture
RISCfuture deleted the navdata/atomic-install branch September 9, 2026 06:40
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant