CheckColumns Constraint (#730)
* feat: add check columns class * feat: write document of check columns part * test: write a test for check columns constraints * fix: debuging test exception raise mysql * fix: set pragma no cover to ignore cov * fix: ignore pytest raise in python 3.x not 10 * feat: set constraint name for check columns * refactor: support index and check overwrites * fix: debuging check constraint arguments * fix: debug coverage all code tests * fix: pass the map of type constraint to counter * refactor: edit check name replace sapce underline * refactor: write new function copy constraints * test: write test for invalid constraint type * fix: debug text cluase replaced names * fix: set pragma no cover for result returned * refactor: no coverage for main if statement * perf: change get constraint copy func code * fix: fix bug in mypy typing check
This commit is contained in:
@ -298,7 +298,7 @@ def populate_meta_sqlalchemy_table_if_required(meta: "ModelMeta") -> None:
|
||||
|
||||
def set_constraint_names(meta: "ModelMeta") -> None:
|
||||
"""
|
||||
Populates the names on IndexColumn and UniqueColumns constraints.
|
||||
Populates the names on IndexColumns and UniqueColumns and CheckColumns constraints.
|
||||
|
||||
:param meta: Meta class of the Model without sqlalchemy table constructed
|
||||
:type meta: Model class Meta
|
||||
@ -317,6 +317,9 @@ def set_constraint_names(meta: "ModelMeta") -> None:
|
||||
f"ix_{meta.tablename}_"
|
||||
f'{"_".join([col for col in constraint._pending_colargs])}'
|
||||
)
|
||||
elif isinstance(constraint, sqlalchemy.CheckConstraint) and not constraint.name:
|
||||
sql_condition: str = str(constraint.sqltext).replace(" ", "_")
|
||||
constraint.name = f"check_{meta.tablename}_{sql_condition}"
|
||||
|
||||
|
||||
def update_column_definition(
|
||||
|
||||
@ -9,6 +9,7 @@ from typing import (
|
||||
Type,
|
||||
Union,
|
||||
cast,
|
||||
Callable,
|
||||
)
|
||||
|
||||
import databases
|
||||
@ -18,6 +19,7 @@ from sqlalchemy.sql.schema import ColumnCollectionConstraint
|
||||
|
||||
import ormar # noqa I100
|
||||
import ormar.fields.constraints
|
||||
from ormar.fields.constraints import UniqueColumns, IndexColumns, CheckColumns
|
||||
from ormar import ModelDefinitionError # noqa I100
|
||||
from ormar.exceptions import ModelError
|
||||
from ormar.fields import BaseField
|
||||
@ -186,7 +188,7 @@ def verify_constraint_names(
|
||||
for column_set in constraints_columns:
|
||||
if any(x not in old_aliases.values() for x in column_set):
|
||||
raise ModelDefinitionError(
|
||||
f"Unique columns constraint "
|
||||
f"Column constraints "
|
||||
f"{column_set} "
|
||||
f"has column names "
|
||||
f"that are not in the model fields."
|
||||
@ -195,6 +197,33 @@ def verify_constraint_names(
|
||||
)
|
||||
|
||||
|
||||
def get_constraint_copy(
|
||||
constraint: ColumnCollectionConstraint,
|
||||
) -> Union[UniqueColumns, IndexColumns, CheckColumns]:
|
||||
"""
|
||||
Copy the constraint and unpacking it's values
|
||||
|
||||
:raises ValueError: if non subclass of ColumnCollectionConstraint
|
||||
:param value: an instance of the ColumnCollectionConstraint class
|
||||
:type value: Instance of ColumnCollectionConstraint child
|
||||
:return: copy ColumnCollectionConstraint ormar constraints
|
||||
:rtype: Union[UniqueColumns, IndexColumns, CheckColumns]
|
||||
"""
|
||||
|
||||
constraints = {
|
||||
sqlalchemy.UniqueConstraint: lambda x: UniqueColumns(*x._pending_colargs),
|
||||
sqlalchemy.Index: lambda x: IndexColumns(*x._pending_colargs),
|
||||
sqlalchemy.CheckConstraint: lambda x: CheckColumns(x.sqltext),
|
||||
}
|
||||
checks = (key if isinstance(constraint, key) else None for key in constraints)
|
||||
target_class = next((target for target in checks if target is not None), None)
|
||||
constructor: Optional[Callable] = constraints.get(target_class)
|
||||
if not constructor:
|
||||
raise ValueError(f"{constraint} must be a ColumnCollectionMixin!")
|
||||
|
||||
return constructor(constraint)
|
||||
|
||||
|
||||
def update_attrs_from_base_meta( # noqa: CCR001
|
||||
base_class: "Model", attrs: Dict, model_fields: Dict
|
||||
) -> None:
|
||||
@ -222,10 +251,7 @@ def update_attrs_from_base_meta( # noqa: CCR001
|
||||
model_fields=model_fields,
|
||||
parent_value=parent_value,
|
||||
)
|
||||
parent_value = [
|
||||
ormar.fields.constraints.UniqueColumns(*x._pending_colargs)
|
||||
for x in parent_value
|
||||
]
|
||||
parent_value = [get_constraint_copy(value) for value in parent_value]
|
||||
if isinstance(current_value, list):
|
||||
current_value.extend(parent_value)
|
||||
else:
|
||||
|
||||
Reference in New Issue
Block a user