Skip to content

Commit b46282a

Browse files
erikcedmattbennett
authored andcommitted
Add primary key constraint name comparison (#12)
* Add primary key constraint name comparison Change usage of SQLAlchemy's get_primary_keys to get_pk_constraint which returns a dict with 'constrained_columns' containing the primary key fields and optionally 'name' with the name of the pk constraint. Update get_primary_keys_info to compare the entire dicts and apply ignores on the constraint name rather than the key names if a 'name' field exists. If 'name' does not exist, the primary key columns are compared instead. * Check for None in pk constraint names
1 parent f54fe4c commit b46282a

File tree

2 files changed

+75
-16
lines changed

2 files changed

+75
-16
lines changed

sqlalchemydiff/comparer.py

Lines changed: 24 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -292,21 +292,35 @@ def _get_foreign_keys(inspector, table_name):
292292
def _get_primary_keys_info(
293293
left_inspector, right_inspector, table_name, ignores
294294
):
295-
left_pk_list = _get_primary_keys(left_inspector, table_name)
296-
right_pk_list = _get_primary_keys(right_inspector, table_name)
297-
298-
left_pk_list = _discard_ignores(left_pk_list, ignores)
299-
right_pk_list = _discard_ignores(right_pk_list, ignores)
300-
301-
# process into dict
302-
left_pk = dict((elem, elem) for elem in left_pk_list)
303-
right_pk = dict((elem, elem) for elem in right_pk_list)
295+
left_pk_constraint = _get_primary_keys(left_inspector, table_name)
296+
right_pk_constraint = _get_primary_keys(right_inspector, table_name)
297+
298+
pk_constraint_has_name = ('name' in left_pk_constraint and
299+
left_pk_constraint['name'] is not None)
300+
301+
if pk_constraint_has_name:
302+
left_pk = ({left_pk_constraint['name']: left_pk_constraint}
303+
if _discard_ignores_by_name([left_pk_constraint], ignores)
304+
else {})
305+
right_pk = ({right_pk_constraint['name']: right_pk_constraint}
306+
if _discard_ignores_by_name([right_pk_constraint], ignores)
307+
else {})
308+
else:
309+
left_pk_list = left_pk_constraint['constrained_columns']
310+
right_pk_list = right_pk_constraint['constrained_columns']
311+
312+
left_pk_list = _discard_ignores(left_pk_list, ignores)
313+
right_pk_list = _discard_ignores(right_pk_list, ignores)
314+
315+
# process into dict
316+
left_pk = dict((elem, elem) for elem in left_pk_list)
317+
right_pk = dict((elem, elem) for elem in right_pk_list)
304318

305319
return _diff_dicts(left_pk, right_pk)
306320

307321

308322
def _get_primary_keys(inspector, table_name):
309-
return inspector.get_primary_keys(table_name)
323+
return inspector.get_pk_constraint(table_name)
310324

311325

312326
def _get_indexes_info(left_inspector, right_inspector, table_name, ignores):

test/unit/test_comparer.py

Lines changed: 51 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -450,8 +450,8 @@ def test__get_foreign_keys(self):
450450
def test__get_primary_keys_info(
451451
self, _diff_dicts_mock, _get_primary_keys_mock):
452452
_get_primary_keys_mock.side_effect = [
453-
['pk_left_1', 'pk_left_2'],
454-
['pk_right_1']
453+
{'constrained_columns': ['pk_left_1', 'pk_left_2']},
454+
{'constrained_columns': ['pk_right_1']}
455455
]
456456
left_inspector, right_inspector = Mock(), Mock()
457457

@@ -468,8 +468,8 @@ def test__get_primary_keys_info(
468468
def test__get_primary_keys_info_ignores(
469469
self, _diff_dicts_mock, _get_primary_keys_mock):
470470
_get_primary_keys_mock.side_effect = [
471-
['pk_left_1', 'pk_left_2'],
472-
['pk_right_1', 'pk_right_2']
471+
{'constrained_columns': ['pk_left_1', 'pk_left_2']},
472+
{'constrained_columns': ['pk_right_1', 'pk_right_2']},
473473
]
474474
left_inspector, right_inspector = Mock(), Mock()
475475
ignores = ['pk_left_1', 'pk_right_2']
@@ -484,13 +484,58 @@ def test__get_primary_keys_info_ignores(
484484

485485
assert _diff_dicts_mock.return_value == result
486486

487+
def test__get_primary_keys_info_with_pk_constraint_name(
488+
self, _diff_dicts_mock, _get_primary_keys_mock):
489+
_get_primary_keys_mock.side_effect = [
490+
{'name': 'left', 'constrained_columns': ['pk_left_1']},
491+
{'name': 'right', 'constrained_columns': ['pk_right_1']}
492+
]
493+
left_inspector, right_inspector = Mock(), Mock()
494+
495+
result = _get_primary_keys_info(
496+
left_inspector, right_inspector, 'table_A', [])
497+
498+
_diff_dicts_mock.assert_called_once_with(
499+
{
500+
'left': {'name': 'left',
501+
'constrained_columns': ['pk_left_1']}
502+
},
503+
{
504+
'right': {'name': 'right',
505+
'constrained_columns': ['pk_right_1']}
506+
}
507+
)
508+
assert _diff_dicts_mock.return_value == result
509+
510+
def test__get_primary_keys_info_ignores_with_pk_constraint_name(
511+
self, _diff_dicts_mock, _get_primary_keys_mock):
512+
_get_primary_keys_mock.side_effect = [
513+
{'name': 'left_1', 'constrained_columns': ['pk_left_1']},
514+
{'name': 'right_1', 'constrained_columns': ['pk_right_1']},
515+
]
516+
left_inspector, right_inspector = Mock(), Mock()
517+
ignores = ['left_1', 'left_2', 'right_2']
518+
519+
result = _get_primary_keys_info(
520+
left_inspector, right_inspector, 'table_A', ignores)
521+
522+
_diff_dicts_mock.assert_called_once_with(
523+
dict(),
524+
{
525+
'right_1': {'name': 'right_1',
526+
'constrained_columns': ['pk_right_1']},
527+
}
528+
)
529+
530+
assert _diff_dicts_mock.return_value == result
531+
487532
def test__get_primary_keys(self):
488533
inspector = Mock()
489534

490535
result = _get_primary_keys(inspector, 'table_A')
491536

492-
inspector.get_primary_keys.assert_called_once_with('table_A')
493-
assert inspector.get_primary_keys.return_value == result
537+
inspector.get_pk_constraint.assert_called_once_with('table_A')
538+
assert inspector.get_pk_constraint.return_value == result
494539

495540
def test__get_indexes_info(
496541
self, _diff_dicts_mock, _get_indexes_mock):

0 commit comments

Comments
 (0)