From c76aad50aeec0bc78a7847bdcdb87f3afa616c5b Mon Sep 17 00:00:00 2001 From: Claude Date: Sat, 4 Jul 2026 18:47:08 +0000 Subject: [PATCH] Correct applied_at type annotation to str _AppliedMigration.applied_at was annotated datetime.datetime but the value is the TEXT timestamp read straight from the _sqlite_migrations table - always a string, matching the format written by both this module and the older sqlite-migrate package. Added a test pinning the runtime type. Co-Authored-By: Claude Fable 5 Claude-Session: https://claude.ai/code/session_01UnLnhsH25Nnv7LHhekUfPd --- sqlite_utils/migrations.py | 4 +++- tests/test_migrations.py | 12 ++++++++++++ 2 files changed, 15 insertions(+), 1 deletion(-) diff --git a/sqlite_utils/migrations.py b/sqlite_utils/migrations.py index 8af0784..20572af 100644 --- a/sqlite_utils/migrations.py +++ b/sqlite_utils/migrations.py @@ -19,7 +19,9 @@ class Migrations: @dataclass class _AppliedMigration: name: str - applied_at: datetime.datetime + # A string timestamp such as "2026-07-04 12:00:00.000000+00:00" - + # stored as TEXT in the _sqlite_migrations table + applied_at: str def __init__(self, name: str): """ diff --git a/tests/test_migrations.py b/tests/test_migrations.py index 34741a5..c190fd5 100644 --- a/tests/test_migrations.py +++ b/tests/test_migrations.py @@ -80,6 +80,18 @@ def test_order_does_not_matter(migrations, migrations_not_ordered_alphabetically assert db1.schema == db2.schema +def test_applied_at_is_a_string(migrations): + db = sqlite_utils.Database(memory=True) + migrations.apply(db) + applied = migrations.applied(db) + assert len(applied) == 2 + for migration in applied: + # applied_at is the TEXT timestamp straight from the + # _sqlite_migrations table, e.g. "2026-07-04 12:00:00.000000+00:00" + assert isinstance(migration.applied_at, str) + assert migration.applied_at.endswith("+00:00") + + def test_failing_migration_rolls_back(migrations): @migrations() def m003(db):