Commit Graph
2 Commits
Author SHA1 Message Date
rouggy 724e68b38d feat(sync): a stable identity per contact, indexed
Two PCs exchanging changes through a folder must be able to name the SAME
contact in both logs. "the QSO with M0ABC at 14:32" is a guess and the two
machines can disagree about which row that is, so an edit or a deletion cannot
be addressed at all without an identity that travels with the record.

A real indexed column, not a key inside extras_json: the identity is resolved
once per incoming change, and scanning JSON for it would turn every sync into a
full read of a 120 000-QSO logbook. A column costs one migration; the JSON would
cost a scan every time. That was the decision to confirm, and it is confirmed.

It follows the award_refs pattern — read in selectCols, absent from columnList,
written only through its own methods. So an ordinary edit cannot clobber it,
which matters: another machine addresses the contact by that id, and losing it
makes the same QSO arrive again as a new one. Pinned by a test that saves an
edit with the field deliberately blanked.

Existing contacts are stamped in batches inside one transaction rather than one
commit each — on a remote MySQL the round trip dominates, and 120 000 commits is
the difference between a minute and an afternoon. And a dedupe-key map lets two
machines that already hold the same imported log recognise each other's contacts
instead of copying 120 000 of them across.

MySQL nearly lost its logbook to this. It cannot index a TEXT column without a
prefix length: the migration would fail with error 1170 and fail again on every
startup, with no way out from the interface. The translator only emits VARCHAR
for names listed by hand in varcharColumns. sync_uid is now listed — and a test
reads the migrations, works out which indexed columns are TEXT, and fails if the
list does not cover them, so the next one cannot reach a shared logbook.
2026-08-16 23:16:52 +02:00
rouggy 9846354bf9 chore: release v0.23.2 2026-08-02 23:51:46 +02:00