def stamp_unstamped_records(
self,
clock: HybridLogicalClock,
model_order: list[str] | None = None,
) -> int:
from django_spire.contrib.sync.django.queryset import sync_bypass # noqa: PLC0415
from django_spire.contrib.sync.django.sequence import ( # noqa: PLC0415
SyncSequenceAllocator,
)
total = 0
labels = model_order or sorted(self._models.keys())
self._ensure_sync_columns(labels)
self._reconcile_counter(labels)
with sync_bypass():
for model_label in labels:
if model_label not in self._models:
continue
model = self._models[model_label]
connection = connections[
router.db_for_write(model) or
'default'
]
quote = connection.ops.quote_name
table = quote(model._meta.db_table)
id_field = model._meta.get_field(self._identity_field)
id_column = quote(id_field.column)
with connection.cursor() as cursor:
cursor.execute(
self._build_zero_field_count_sql(
table,
'sync_field_sequence',
),
)
sequence_count = cursor.fetchone()[0]
cursor.execute(
self._build_zero_field_count_sql(
table,
'sync_field_last_modified',
),
)
timestamp_count = cursor.fetchone()[0]
if sequence_count == 0 and timestamp_count == 0:
continue
stamp_timestamp = clock.now()
stamp_field_names = (
list(model.get_syncable_field_names()) +
list(model.get_syncable_many_to_many_names())
)
stamp_timestamps_json = json.dumps(
dict.fromkeys(
stamp_field_names,
stamp_timestamp
)
)
sequence_first = 0
with transaction.atomic():
if sequence_count > 0:
sequence_first = SyncSequenceAllocator().allocate(sequence_count).value_first
with connection.cursor() as cursor:
cursor.execute(
self._build_assign_sequence_sql(
table,
id_column,
),
[sequence_first],
)
if timestamp_count > 0:
with connection.cursor() as cursor:
cursor.execute(
self._build_stamp_modified_sql(table),
[stamp_timestamp, stamp_timestamps_json],
)
stamped = max(sequence_count, timestamp_count)
logger.info(
'Stamped %s in %s '
'(%d sequences from %d, %d timestamps, ts=%d)',
stamped,
model_label,
sequence_count,
sequence_first,
timestamp_count,
stamp_timestamp,
)
total += stamped
return total