replaceIdEverywhere method
Updates all references to an old ID with a new ID after server ID negotiation. This method must update:
- The sync queue item's modelId
- The model table record's ID
- All foreign key references in related models
- Mark ID negotiation as complete
Implementation
Future<void> replaceIdEverywhere({
required int taskId,
required String oldId,
required String newId,
required String modelType,
}) async {
await _db.transaction(() async {
// 1. Update the sync queue item
await _db.customUpdate(
'''
UPDATE sync_queue_items
SET model_id = ?, id_negotiation_status = ?
WHERE id = ?
''',
variables: [
Variable.withString(newId),
Variable.withString(IdNegotiationStatus.completed.name),
Variable.withInt(taskId),
],
);
// 2. Update the model table record
final tableName = modelTypeToTableName(modelType);
final modelTable = _getCachedTable(tableName);
await _db.customUpdate(
'UPDATE $tableName SET id = ? WHERE id = ?',
variables: [
Variable.withString(newId),
Variable.withString(oldId),
],
updates: modelTable != null ? {modelTable} : null,
updateKind: modelTable != null ? UpdateKind.update : null,
);
// 3. Update foreign key references using dedicated service
final foreignKeyService = ForeignKeyUpdateService(_db, _tryGetTable);
await foreignKeyService.updateForeignKeyReferences(
oldId,
newId,
modelType,
);
// 4. Update pending payloads referencing the old ID
await _db.customUpdate(
'''
UPDATE sync_queue_items
SET payload = REPLACE(payload, ?, ?)
WHERE payload LIKE ?
''',
variables: [
Variable.withString(oldId),
Variable.withString(newId),
Variable.withString('%$oldId%'),
],
);
_log.info(
'Replaced ID $oldId with $newId for $modelType in task $taskId',
);
});
}