Skip to content

Commit 5aa095f

Browse files
committed
Fixing transformations
1 parent f7fa18e commit 5aa095f

File tree

3 files changed

+34
-10
lines changed

3 files changed

+34
-10
lines changed

sqlite_minutils/db.py

Lines changed: 20 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -954,6 +954,15 @@ def create_table(
954954
if transform and self[name].exists():
955955
table = cast(Table, self[name])
956956
should_transform = False
957+
# Has the primary key changed?
958+
current_pks = table.pks
959+
desired_pk = None
960+
if isinstance(pk, str):
961+
desired_pk = [pk]
962+
elif pk:
963+
desired_pk = list(pk)
964+
if desired_pk and current_pks != desired_pk:
965+
should_transform = True
957966
# First add missing columns and figure out columns to drop
958967
existing_columns = table.columns_dict
959968
missing_columns = dict(
@@ -964,6 +973,14 @@ def create_table(
964973
columns_to_drop = [
965974
column for column in existing_columns if column not in columns
966975
]
976+
# If no primary key was specified and id was added automatically, we prevent
977+
# it from being deleted here or Sqlite will complain that a primary key is
978+
# being dropped. We delete the ID column once a new PK has been set.
979+
delete_id_column = False
980+
if table.pks == ['id'] and 'id' in columns_to_drop:
981+
columns_to_drop.remove('id')
982+
delete_id_column = True
983+
967984
if columns_to_drop:
968985
for col_name in columns_to_drop: table.drop_column(col_name)
969986
if missing_columns:
@@ -977,15 +994,6 @@ def create_table(
977994
and list(existing_columns)[: len(column_order)] != column_order
978995
):
979996
should_transform = True
980-
# Has the primary key changed?
981-
current_pks = table.pks
982-
desired_pk = None
983-
if isinstance(pk, str):
984-
desired_pk = [pk]
985-
elif pk:
986-
desired_pk = list(pk)
987-
if desired_pk and current_pks != desired_pk:
988-
should_transform = True
989997
# Any not-null changes?
990998
current_not_null = {c.name for c in table.columns if c.notnull}
991999
desired_not_null = set(not_null) if not_null else set()
@@ -1003,6 +1011,9 @@ def create_table(
10031011
defaults=defaults,
10041012
pk=pk,
10051013
)
1014+
# Now it is safe to drop the ID column.
1015+
if delete_id_column:
1016+
table.drop_column('id')
10061017
return table
10071018
sql = self.create_table_sql(
10081019
name=name,

tests/test_create.py

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1368,3 +1368,4 @@ def test_create_strict(fresh_db, strict):
13681368
table = fresh_db["t"]
13691369
table.create({"id": int}, strict=strict)
13701370
assert table.strict == strict or not fresh_db.supports_strict
1371+

tests/test_transform.py

Lines changed: 13 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,4 @@
1-
from sqlite_minutils.db import ForeignKey
1+
from sqlite_minutils.db import ForeignKey, Database
22
from sqlite_minutils.utils import OperationalError
33
from sqlite3 import IntegrityError
44
import pytest
@@ -521,3 +521,15 @@ def test_transform_strict(fresh_db, strict):
521521
assert dogs.strict == strict or not fresh_db.supports_strict
522522
dogs.transform(not_null={"name"})
523523
assert dogs.strict == strict or not fresh_db.supports_strict
524+
525+
526+
def test_create_twice(fresh_db):
527+
columns = {'name': str}
528+
fresh_db['demo'].create(columns=columns)
529+
fresh_db['demo'].create(columns=columns, transform=True)
530+
531+
def test_create_twice_with_pk_change(fresh_db):
532+
columns = {'name': str}
533+
fresh_db['demo'].create(columns=columns)
534+
new_columns = {'name': str, 'age': int}
535+
fresh_db['demo'].create(columns=new_columns, transform=True, pk='age')

0 commit comments

Comments
 (0)