Issue Description
Migrating from Stalwart 0.16.27 using stalwart-migrate 1.0.3 fails during final verification with:
647 mismatches, 643 not explained by earlier reports
The verification report contains numerous contactCard mismatches with the message:
differs in the target: vcard
The final copy itself succeeds, but the migration is not marked as done. The same issue occurred previously with stalwart-migrate 1.0.1.
Environment
Source: Stalwart 0.16.27
Migration tool: stalwart-migrate 1.0.3
Deployment: Docker Compose on Linux
Accounts: 3
Separate source, target and migration-state volumes
Target path mapping: /var/lib/stalwart=/var/lib/stalwart-v1
Steps to reproduce
Run prepare and complete the migration configuration.
Run the initial copy:
docker compose run --rm --interactive stalwart-migrate run
–source /etc/stalwart/config.json
–target /etc/stalwart-v1/config.json
–state /var/lib/stalwart-migrate
–target-path-map /var/lib/stalwart=/var/lib/stalwart-v1
Review the four reported errors concerning missing spam-training blobs, which I am willing to accept as losses.
Stop the source Stalwart instance.
Run the final copy with full verification:
docker compose run --rm --interactive stalwart-migrate run
–final
–source /etc/stalwart/config.json
–target /etc/stalwart-v1/config.json
–state /var/lib/stalwart-migrate
–target-path-map /var/lib/stalwart=/var/lib/stalwart-v1
–allow-errors
–verify-full
Inspect the verification report:
docker compose run --rm stalwart-migrate report
–state /var/lib/stalwart-migrate
–run 3
–severity verify
Actual result
The initial copy transfers all three accounts, but reports four missing source blobs associated with x:SpamTrainingSample objects:
326360430759015936
326360430761113600
326360430761114112
326360430763211776
Each reports:
blob is missing in the source; the object was not copied
These four missing training samples are acceptable losses. They appear to account for the four explained verification mismatches.
The subsequent final copy succeeds:
2026-10-28T19:03:05.591795Z INFO migrate::orchestrator: run finished run_id=2 status=ok
Its counters include:
accounts_delta=1
accounts_unchanged=2
accounts_failed=0
errors=0
However, verification fails:
2026-10-28T19:06:20.475035Z INFO migrate::orchestrator::verify: verify finished run_id=3 status=failed accounts_checked=3 mismatches=647 unexplained=643
2026-10-28T19:06:20.475174Z ERROR migrate::orchestrator: finalize completed but verification failed: the final run is not marked done; fix the reported mismatches and repeat the command (run --final, or rollback with the same --state)
The verification report includes:
run severity category account object id message
3 verify mismatch 1 contactCard 767 differs in the target: vcard
3 verify mismatch 1 contactCard 768 differs in the target: vcard
3 verify mismatch 1 - - 543 more contactCard mismatches are not listed
The report prints 105 rows, including the summary of additional contact-card mismatches.
Expected Behavior
Contact cards should be converted to the target representation and pass semantic vCard verification.
If conversion necessarily changes or drops contact data, I would expect the migration report to identify those changes and explain the resulting verification differences.
Actual Behavior
The verification report contains numerous contactCard mismatches with the message:
differs in the target: vcard
Stalwart Version
v0.16.x
Installation Method
Docker
Database Backend
RocksDB
Blob Storage
RocksDB
Search Engine
Internal
Directory Backend
Internal
I have reviewed the documentation and FAQ and confirm that my issue is NOT addressed there.
on
I have searched this support forum (open and closed topics) and confirm this is not a duplicate.
on
I understand that topics in this category are triaged by a bot first but a human reply will follow up. If I’d prefer a human-only reply, I’ll add the no-ai tag to my topic.
on