mirror of
https://github.com/jazzband/django-eav2.git
synced 2026-03-16 22:40:26 +00:00
feat: Provide UUIDField option for pk field and a natural key feature for serialization (#428)
This commit is contained in:
parent
964f77dc54
commit
3b1be10e9b
12 changed files with 478 additions and 65 deletions
13
CHANGELOG.md
13
CHANGELOG.md
|
|
@ -10,6 +10,11 @@ We follow [Semantic Versions](https://semver.org/) starting at the `0.14.0` rele
|
|||
|
||||
- Fixes querying with multiple eav kwargs [#395](https://github.com/jazzband/django-eav2/issues/395)
|
||||
|
||||
### Features
|
||||
|
||||
- Support for many type of primary key (UUIDField, BigAutoField)
|
||||
- Support for natural key use for some models for serialization (EnumValue, EnumGroup, Attribute, Value)
|
||||
|
||||
## 1.4.0 (2023-07-07)
|
||||
|
||||
### Features
|
||||
|
|
@ -46,6 +51,7 @@ We follow [Semantic Versions](https://semver.org/) starting at the `0.14.0` rele
|
|||
- Make Read the Docs dependencies all optional
|
||||
|
||||
## 1.2.2 (2022-08-13)
|
||||
|
||||
### Bug Fixes
|
||||
|
||||
- Fixes AttributeError when using CSVFormField [#187](https://github.com/jazzband/django-eav2/issues/187)
|
||||
|
|
@ -53,6 +59,7 @@ We follow [Semantic Versions](https://semver.org/) starting at the `0.14.0` rele
|
|||
- Migrates Attribute.slug to django.db.models.SlugField() [#223](https://github.com/jazzband/django-eav2/issues/223)
|
||||
|
||||
## 1.2.1 (2022-02-08)
|
||||
|
||||
### Bug Fixes
|
||||
|
||||
- Fixes FieldError when filtering on foreign keys [#163](https://github.com/jazzband/django-eav2/issues/163)
|
||||
|
|
@ -83,7 +90,7 @@ We follow [Semantic Versions](https://semver.org/) starting at the `0.14.0` rele
|
|||
|
||||
- Bumps min python version to `3.6.2`
|
||||
|
||||
**Full Changelog**: https://github.com/jazzband/django-eav2/compare/1.0.0...1.1.0
|
||||
**Full Changelog**: <https://github.com/jazzband/django-eav2/compare/1.0.0...1.1.0>
|
||||
|
||||
## 1.0.0 (2021-10-21)
|
||||
|
||||
|
|
@ -104,7 +111,7 @@ We follow [Semantic Versions](https://semver.org/) starting at the `0.14.0` rele
|
|||
- Revamps all tooling, including moving to `poetry`, `pytest`, and `black`
|
||||
- Adds Github Actions and Dependabot
|
||||
|
||||
**Full Changelog**: https://github.com/jazzband/django-eav2/compare/0.14.0...1.0.0
|
||||
**Full Changelog**: <https://github.com/jazzband/django-eav2/compare/0.14.0...1.0.0>
|
||||
|
||||
## 0.14.0 (2021-04-23)
|
||||
|
||||
|
|
@ -113,6 +120,6 @@ We follow [Semantic Versions](https://semver.org/) starting at the `0.14.0` rele
|
|||
- This release will be the last to support this range of Django versions: 1.11, 2.0, 2.1, 2.2, 3.0. SInce all of their extended support was ended by Django Project.
|
||||
- From the next release only will be supported 2.2 LTS, 3.1, and 3.2 LTS (eventually 4.x)
|
||||
|
||||
**Full Changelog**: https://github.com/jazzband/django-eav2/compare/0.13.0...0.14.0
|
||||
**Full Changelog**: <https://github.com/jazzband/django-eav2/compare/0.13.0...0.14.0>
|
||||
|
||||
(Anything before 0.14.0 was not recorded.)
|
||||
|
|
|
|||
39
README.md
39
README.md
|
|
@ -83,6 +83,7 @@ However, it is important to note that:
|
|||
|
||||
In some use-cases, JSONB (binary JSON data) datatype (Postgres 9.4+ and analogous in other RDMSs) can be used as an alternative to EAV. JSONB supports indexing, which amortizes performance trade-off. It's important to keep in mind that JSONB is not RDMS-agnostic solution and has it's own problems, such as typing.
|
||||
|
||||
|
||||
## Installation
|
||||
|
||||
Install with pip
|
||||
|
|
@ -102,6 +103,44 @@ INSTALLED_APPS = [
|
|||
]
|
||||
```
|
||||
|
||||
Add `django.db.models.UUIDField` or `django.db.models.BigAutoField` as value of `EAV2_PRIMARY_KEY_FIELD` in your settings
|
||||
|
||||
``` python
|
||||
EAV2_PRIMARY_KEY_FIELD = "django.db.models.UUIDField" # as exemple
|
||||
```
|
||||
|
||||
### Note: Primary key mandatory modification field
|
||||
|
||||
If the primary key of eav models are to be modified (UUIDField -> BigAutoField, BigAutoField -> UUIDField) in the middle of the project when the migrations are already done, you have to change the value of `EAV2_PRIMARY_KEY_FIELD` in your settings.
|
||||
|
||||
##### Step 1
|
||||
Change the value of `EAV2_PRIMARY_KEY_FIELD` into `django.db.models.CharField` in your settings.
|
||||
|
||||
```python
|
||||
EAV2_PRIMARY_KEY_FIELD = "django.db.models.CharField"
|
||||
```
|
||||
|
||||
Run the migrations
|
||||
|
||||
```bash
|
||||
python manage.py makemigrations
|
||||
python manage.py migrate
|
||||
```
|
||||
|
||||
##### Step 2
|
||||
Change the value of `EAV2_PRIMARY_KEY_FIELD` into the desired value (`django.db.models.BigAutoField` or `django.db.models.UUIDField`) in your settings.
|
||||
|
||||
```python
|
||||
EAV2_PRIMARY_KEY_FIELD = "django.db.models.BigAutoField" # as exemple
|
||||
```
|
||||
|
||||
Run again the migrations.
|
||||
|
||||
```bash
|
||||
python manage.py makemigrations
|
||||
python manage.py migrate
|
||||
```
|
||||
|
||||
### Note: Django 2.2 Users
|
||||
|
||||
Since `models.JSONField()` isn't supported in Django 2.2, we use [django-jsonfield-backport](https://github.com/laymonage/django-jsonfield-backport) to provide [JSONField](https://docs.djangoproject.com/en/dev/releases/3.1/#jsonfield-for-all-supported-database-backends) functionality.
|
||||
|
|
|
|||
|
|
@ -21,6 +21,10 @@ class EavDatatypeField(models.CharField):
|
|||
if not instance.pk:
|
||||
return
|
||||
|
||||
# added
|
||||
if not type(instance).objects.filter(pk=instance.pk).exists():
|
||||
return
|
||||
|
||||
if type(instance).objects.get(pk=instance.pk).datatype == instance.datatype:
|
||||
return
|
||||
|
||||
|
|
|
|||
97
eav/logic/managers.py
Normal file
97
eav/logic/managers.py
Normal file
|
|
@ -0,0 +1,97 @@
|
|||
from django.db import models
|
||||
|
||||
|
||||
class EnumValueManager(models.Manager):
|
||||
"""
|
||||
Custom manager for `EnumValue` model.
|
||||
|
||||
This manager adds utility methods specific to the `EnumValue` model.
|
||||
"""
|
||||
|
||||
def get_by_natural_key(self, value):
|
||||
"""
|
||||
Retrieves an EnumValue instance using its `value` as a natural key.
|
||||
|
||||
Args:
|
||||
value (str): The value of the EnumValue instance.
|
||||
|
||||
Returns:
|
||||
EnumValue: The instance matching the provided value.
|
||||
"""
|
||||
return self.get(value=value)
|
||||
|
||||
|
||||
class EnumGroupManager(models.Manager):
|
||||
"""
|
||||
Custom manager for `EnumGroup` model.
|
||||
|
||||
This manager adds utility methods specific to the `EnumGroup` model.
|
||||
"""
|
||||
|
||||
def get_by_natural_key(self, name):
|
||||
"""
|
||||
Retrieves an EnumGroup instance using its `name` as a natural key.
|
||||
|
||||
Args:
|
||||
name (str): The name of the EnumGroup instance.
|
||||
|
||||
Returns:
|
||||
EnumGroup: The instance matching the provided name.
|
||||
"""
|
||||
return self.get(name=name)
|
||||
|
||||
|
||||
class AttributeManager(models.Manager):
|
||||
"""
|
||||
Custom manager for `Attribute` model.
|
||||
|
||||
This manager adds utility methods specific to the `Attribute` model.
|
||||
"""
|
||||
|
||||
def get_by_natural_key(self, name, slug):
|
||||
"""
|
||||
Retrieves an Attribute instance using its `name` and `slug` as natural keys.
|
||||
|
||||
Args:
|
||||
name (str): The name of the Attribute instance.
|
||||
slug (str): The slug of the Attribute instance.
|
||||
|
||||
Returns:
|
||||
Attribute: The instance matching the provided name and slug.
|
||||
"""
|
||||
return self.get(name=name, slug=slug)
|
||||
|
||||
|
||||
class ValueManager(models.Manager):
|
||||
"""
|
||||
Custom manager for `Value` model.
|
||||
|
||||
This manager adds utility methods specific to the `Value` model.
|
||||
"""
|
||||
|
||||
def get_by_natural_key(self, attribute, entity_id, entity_uuid):
|
||||
"""
|
||||
Retrieve a Value instance using multiple natural keys.
|
||||
|
||||
This method utilizes a combination of an `attribute` (defined by its
|
||||
name and slug), `entity_id`, and `entity_uuid` to retrieve a unique
|
||||
Value instance.
|
||||
|
||||
Args:
|
||||
attribute (tuple): A tuple containing the name and slug of the
|
||||
Attribute instance.
|
||||
entity_id (int): The ID of the associated entity.
|
||||
entity_uuid (str): The UUID of the associated entity.
|
||||
|
||||
Returns:
|
||||
Value: The instance matching the provided keys.
|
||||
"""
|
||||
from eav.models import Attribute
|
||||
|
||||
attribute = Attribute.objects.get(name=attribute[0], slug=attribute[1])
|
||||
|
||||
return self.get(
|
||||
attribute=attribute,
|
||||
entity_id=entity_id,
|
||||
entity_uuid=entity_uuid,
|
||||
)
|
||||
45
eav/logic/object_pk.py
Normal file
45
eav/logic/object_pk.py
Normal file
|
|
@ -0,0 +1,45 @@
|
|||
import uuid
|
||||
from functools import partial
|
||||
from typing import Type
|
||||
|
||||
from django.conf import settings
|
||||
from django.db import models
|
||||
|
||||
#: Constants
|
||||
_DEFAULT_CHARFIELD_LEN: int = 40
|
||||
|
||||
_FIELD_MAPPING = {
|
||||
"django.db.models.UUIDField": partial(
|
||||
models.UUIDField,
|
||||
primary_key=True,
|
||||
editable=False,
|
||||
default=uuid.uuid4,
|
||||
),
|
||||
"django.db.models.CharField": partial(
|
||||
models.CharField,
|
||||
primary_key=True,
|
||||
editable=False,
|
||||
max_length=_DEFAULT_CHARFIELD_LEN,
|
||||
),
|
||||
}
|
||||
|
||||
|
||||
def get_pk_format() -> Type[models.Field]:
|
||||
"""
|
||||
Get the primary key field format based on the Django settings.
|
||||
|
||||
This function returns a field factory function that corresponds to the
|
||||
primary key format specified in Django settings. If the primary key
|
||||
format is not recognized, it defaults to using BigAutoField.
|
||||
|
||||
Returns:
|
||||
Type[models.Field]: A field factory function that can be used to
|
||||
create the primary key field instance.
|
||||
"""
|
||||
field_factory = _FIELD_MAPPING.get(
|
||||
settings.EAV2_PRIMARY_KEY_FIELD,
|
||||
partial(models.BigAutoField, primary_key=True, editable=False),
|
||||
)
|
||||
|
||||
# Create and return the field instance
|
||||
return field_factory()
|
||||
48
eav/migrations/0010_dynamic_pk_type_for_models.py
Normal file
48
eav/migrations/0010_dynamic_pk_type_for_models.py
Normal file
|
|
@ -0,0 +1,48 @@
|
|||
from django.db import migrations, models
|
||||
|
||||
|
||||
class Migration(migrations.Migration):
|
||||
"""Migration to use BigAutoField as default for all models."""
|
||||
|
||||
dependencies = [
|
||||
('eav', '0009_enchance_naming'),
|
||||
]
|
||||
|
||||
operations = [
|
||||
migrations.AlterField(
|
||||
model_name='attribute',
|
||||
name='id',
|
||||
field=models.BigAutoField(
|
||||
editable=False,
|
||||
primary_key=True,
|
||||
serialize=False,
|
||||
),
|
||||
),
|
||||
migrations.AlterField(
|
||||
model_name='enumgroup',
|
||||
name='id',
|
||||
field=models.BigAutoField(
|
||||
editable=False,
|
||||
primary_key=True,
|
||||
serialize=False,
|
||||
),
|
||||
),
|
||||
migrations.AlterField(
|
||||
model_name='enumvalue',
|
||||
name='id',
|
||||
field=models.BigAutoField(
|
||||
editable=False,
|
||||
primary_key=True,
|
||||
serialize=False,
|
||||
),
|
||||
),
|
||||
migrations.AlterField(
|
||||
model_name='value',
|
||||
name='id',
|
||||
field=models.BigAutoField(
|
||||
editable=False,
|
||||
primary_key=True,
|
||||
serialize=False,
|
||||
),
|
||||
),
|
||||
]
|
||||
|
|
@ -10,6 +10,7 @@ optional metaclass for each eav model class.
|
|||
"""
|
||||
|
||||
from copy import copy
|
||||
from typing import Tuple
|
||||
|
||||
from django.contrib.contenttypes import fields as generic
|
||||
from django.contrib.contenttypes.models import ContentType
|
||||
|
|
@ -24,6 +25,13 @@ from eav import register
|
|||
from eav.exceptions import IllegalAssignmentException
|
||||
from eav.fields import CSVField, EavDatatypeField
|
||||
from eav.logic.entity_pk import get_entity_pk_type
|
||||
from eav.logic.managers import (
|
||||
AttributeManager,
|
||||
EnumGroupManager,
|
||||
EnumValueManager,
|
||||
ValueManager,
|
||||
)
|
||||
from eav.logic.object_pk import get_pk_format
|
||||
from eav.logic.slug import SLUGFIELD_MAX_LENGTH, generate_slug
|
||||
from eav.validators import (
|
||||
validate_bool,
|
||||
|
|
@ -73,10 +81,14 @@ class EnumValue(models.Model):
|
|||
the same *Yes* and *No* *EnumValues* for both *EnumGroups*.
|
||||
"""
|
||||
|
||||
objects = EnumValueManager()
|
||||
|
||||
class Meta:
|
||||
verbose_name = _('EnumValue')
|
||||
verbose_name_plural = _('EnumValues')
|
||||
|
||||
id = get_pk_format()
|
||||
|
||||
value = models.CharField(
|
||||
_('Value'),
|
||||
db_index=True,
|
||||
|
|
@ -84,9 +96,23 @@ class EnumValue(models.Model):
|
|||
max_length=SLUGFIELD_MAX_LENGTH,
|
||||
)
|
||||
|
||||
def natural_key(self) -> Tuple[str]:
|
||||
"""
|
||||
Retrieve the natural key for the EnumValue instance.
|
||||
|
||||
The natural key for an EnumValue is defined by its `value`. This method returns
|
||||
the value of the instance as a single-element tuple.
|
||||
|
||||
Returns:
|
||||
tuple: A tuple containing the value of the EnumValue instance.
|
||||
"""
|
||||
return (self.value,)
|
||||
|
||||
def __str__(self):
|
||||
"""String representation of `EnumValue` instance."""
|
||||
return str(self.value)
|
||||
return str(
|
||||
self.value,
|
||||
)
|
||||
|
||||
def __repr__(self):
|
||||
"""String representation of `EnumValue` object."""
|
||||
|
|
@ -102,10 +128,14 @@ class EnumGroup(models.Model):
|
|||
See :class:`EnumValue` for an example.
|
||||
"""
|
||||
|
||||
objects = EnumGroupManager()
|
||||
|
||||
class Meta:
|
||||
verbose_name = _('EnumGroup')
|
||||
verbose_name_plural = _('EnumGroups')
|
||||
|
||||
id = get_pk_format()
|
||||
|
||||
name = models.CharField(
|
||||
unique=True,
|
||||
max_length=CHARFIELD_LENGTH,
|
||||
|
|
@ -116,6 +146,18 @@ class EnumGroup(models.Model):
|
|||
verbose_name=_('Enum group'),
|
||||
)
|
||||
|
||||
def natural_key(self) -> Tuple[str]:
|
||||
"""
|
||||
Retrieve the natural key for the EnumGroup instance.
|
||||
|
||||
The natural key for an EnumGroup is defined by its `name`. This method
|
||||
returns the name of the instance as a single-element tuple.
|
||||
|
||||
Returns:
|
||||
tuple: A tuple containing the name of the EnumGroup instance.
|
||||
"""
|
||||
return (self.name,)
|
||||
|
||||
def __str__(self):
|
||||
"""String representation of `EnumGroup` instance."""
|
||||
return str(self.name)
|
||||
|
|
@ -177,6 +219,8 @@ class Attribute(models.Model):
|
|||
change it's datatype.
|
||||
"""
|
||||
|
||||
objects = AttributeManager()
|
||||
|
||||
class Meta:
|
||||
ordering = ['name']
|
||||
verbose_name = _('Attribute')
|
||||
|
|
@ -205,6 +249,7 @@ class Attribute(models.Model):
|
|||
)
|
||||
|
||||
# Core attributes
|
||||
id = get_pk_format()
|
||||
|
||||
datatype = EavDatatypeField(
|
||||
choices=DATATYPE_CHOICES,
|
||||
|
|
@ -288,6 +333,21 @@ class Attribute(models.Model):
|
|||
verbose_name=_('Created'),
|
||||
)
|
||||
|
||||
def natural_key(self) -> Tuple[str, str]:
|
||||
"""
|
||||
Retrieve the natural key for the Attribute instance.
|
||||
|
||||
The natural key for an Attribute is defined by its `name` and `slug`. This method
|
||||
returns a tuple containing these two attributes of the instance.
|
||||
|
||||
Returns:
|
||||
tuple: A tuple containing the name and slug of the Attribute instance.
|
||||
"""
|
||||
return (
|
||||
self.name,
|
||||
self.slug,
|
||||
)
|
||||
|
||||
@property
|
||||
def help_text(self):
|
||||
return self.description
|
||||
|
|
@ -435,10 +495,14 @@ class Value(models.Model): # noqa: WPS110
|
|||
# = <Value: crazy_dev_user - Fav Drink: "red bull">
|
||||
"""
|
||||
|
||||
objects = ValueManager()
|
||||
|
||||
class Meta:
|
||||
verbose_name = _('Value')
|
||||
verbose_name_plural = _('Values')
|
||||
|
||||
id = get_pk_format()
|
||||
|
||||
# Direct foreign keys
|
||||
attribute = models.ForeignKey(
|
||||
Attribute,
|
||||
|
|
@ -560,11 +624,23 @@ class Value(models.Model): # noqa: WPS110
|
|||
fk_field='generic_value_id',
|
||||
)
|
||||
|
||||
def natural_key(self) -> Tuple[Tuple[str, str], int, str]:
|
||||
"""
|
||||
Retrieve the natural key for the Value instance.
|
||||
|
||||
The natural key for a Value is a combination of its `attribute` natural key,
|
||||
`entity_id`, and `entity_uuid`. This method returns a tuple containing these
|
||||
three elements.
|
||||
|
||||
Returns:
|
||||
tuple: A tuple containing the natural key of the attribute, entity ID,
|
||||
and entity UUID of the Value instance.
|
||||
"""
|
||||
return (self.attribute.natural_key(), self.entity_id, self.entity_uuid)
|
||||
|
||||
def __str__(self):
|
||||
"""String representation of a Value."""
|
||||
entity = self.entity_pk_int
|
||||
if self.entity_uuid:
|
||||
entity = self.entity_pk_uuid
|
||||
entity = self.entity_pk_uuid if self.entity_uuid else self.entity_pk_int
|
||||
return '{0}: "{1}" ({2})'.format(
|
||||
self.attribute.name,
|
||||
self.value,
|
||||
|
|
@ -573,13 +649,11 @@ class Value(models.Model): # noqa: WPS110
|
|||
|
||||
def __repr__(self):
|
||||
"""Representation of Value object."""
|
||||
entity = self.entity_pk_int
|
||||
if self.entity_uuid:
|
||||
entity = self.entity_pk_uuid
|
||||
entity = self.entity_pk_uuid if self.entity_uuid else self.entity_pk_int
|
||||
return '{0}: "{1}" ({2})'.format(
|
||||
self.attribute.name,
|
||||
self.value,
|
||||
entity.pk,
|
||||
entity,
|
||||
)
|
||||
|
||||
def save(self, *args, **kwargs):
|
||||
|
|
|
|||
107
poetry.lock
generated
107
poetry.lock
generated
|
|
@ -339,62 +339,63 @@ testing = ["flake8", "pytest", "pytest-cov", "pytest-virtualenv", "pytest-xdist"
|
|||
|
||||
[[package]]
|
||||
name = "coverage"
|
||||
version = "7.1.0"
|
||||
version = "7.3.2"
|
||||
description = "Code coverage measurement for Python"
|
||||
optional = false
|
||||
python-versions = ">=3.7"
|
||||
python-versions = ">=3.8"
|
||||
files = [
|
||||
{file = "coverage-7.1.0-cp310-cp310-macosx_10_9_x86_64.whl", hash = "sha256:3b946bbcd5a8231383450b195cfb58cb01cbe7f8949f5758566b881df4b33baf"},
|
||||
{file = "coverage-7.1.0-cp310-cp310-macosx_11_0_arm64.whl", hash = "sha256:ec8e767f13be637d056f7e07e61d089e555f719b387a7070154ad80a0ff31801"},
|
||||
{file = "coverage-7.1.0-cp310-cp310-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:d4a5a5879a939cb84959d86869132b00176197ca561c664fc21478c1eee60d75"},
|
||||
{file = "coverage-7.1.0-cp310-cp310-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:b643cb30821e7570c0aaf54feaf0bfb630b79059f85741843e9dc23f33aaca2c"},
|
||||
{file = "coverage-7.1.0-cp310-cp310-manylinux_2_5_x86_64.manylinux1_x86_64.manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:32df215215f3af2c1617a55dbdfb403b772d463d54d219985ac7cd3bf124cada"},
|
||||
{file = "coverage-7.1.0-cp310-cp310-musllinux_1_1_aarch64.whl", hash = "sha256:33d1ae9d4079e05ac4cc1ef9e20c648f5afabf1a92adfaf2ccf509c50b85717f"},
|
||||
{file = "coverage-7.1.0-cp310-cp310-musllinux_1_1_i686.whl", hash = "sha256:29571503c37f2ef2138a306d23e7270687c0efb9cab4bd8038d609b5c2393a3a"},
|
||||
{file = "coverage-7.1.0-cp310-cp310-musllinux_1_1_x86_64.whl", hash = "sha256:63ffd21aa133ff48c4dff7adcc46b7ec8b565491bfc371212122dd999812ea1c"},
|
||||
{file = "coverage-7.1.0-cp310-cp310-win32.whl", hash = "sha256:4b14d5e09c656de5038a3f9bfe5228f53439282abcab87317c9f7f1acb280352"},
|
||||
{file = "coverage-7.1.0-cp310-cp310-win_amd64.whl", hash = "sha256:8361be1c2c073919500b6601220a6f2f98ea0b6d2fec5014c1d9cfa23dd07038"},
|
||||
{file = "coverage-7.1.0-cp311-cp311-macosx_10_9_x86_64.whl", hash = "sha256:da9b41d4539eefd408c46725fb76ecba3a50a3367cafb7dea5f250d0653c1040"},
|
||||
{file = "coverage-7.1.0-cp311-cp311-macosx_11_0_arm64.whl", hash = "sha256:c5b15ed7644ae4bee0ecf74fee95808dcc34ba6ace87e8dfbf5cb0dc20eab45a"},
|
||||
{file = "coverage-7.1.0-cp311-cp311-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:d12d076582507ea460ea2a89a8c85cb558f83406c8a41dd641d7be9a32e1274f"},
|
||||
{file = "coverage-7.1.0-cp311-cp311-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:e2617759031dae1bf183c16cef8fcfb3de7617f394c813fa5e8e46e9b82d4222"},
|
||||
{file = "coverage-7.1.0-cp311-cp311-manylinux_2_5_x86_64.manylinux1_x86_64.manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:c4e4881fa9e9667afcc742f0c244d9364d197490fbc91d12ac3b5de0bf2df146"},
|
||||
{file = "coverage-7.1.0-cp311-cp311-musllinux_1_1_aarch64.whl", hash = "sha256:9d58885215094ab4a86a6aef044e42994a2bd76a446dc59b352622655ba6621b"},
|
||||
{file = "coverage-7.1.0-cp311-cp311-musllinux_1_1_i686.whl", hash = "sha256:ffeeb38ee4a80a30a6877c5c4c359e5498eec095878f1581453202bfacc8fbc2"},
|
||||
{file = "coverage-7.1.0-cp311-cp311-musllinux_1_1_x86_64.whl", hash = "sha256:3baf5f126f30781b5e93dbefcc8271cb2491647f8283f20ac54d12161dff080e"},
|
||||
{file = "coverage-7.1.0-cp311-cp311-win32.whl", hash = "sha256:ded59300d6330be27bc6cf0b74b89ada58069ced87c48eaf9344e5e84b0072f7"},
|
||||
{file = "coverage-7.1.0-cp311-cp311-win_amd64.whl", hash = "sha256:6a43c7823cd7427b4ed763aa7fb63901ca8288591323b58c9cd6ec31ad910f3c"},
|
||||
{file = "coverage-7.1.0-cp37-cp37m-macosx_10_9_x86_64.whl", hash = "sha256:7a726d742816cb3a8973c8c9a97539c734b3a309345236cd533c4883dda05b8d"},
|
||||
{file = "coverage-7.1.0-cp37-cp37m-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:bc7c85a150501286f8b56bd8ed3aa4093f4b88fb68c0843d21ff9656f0009d6a"},
|
||||
{file = "coverage-7.1.0-cp37-cp37m-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:f5b4198d85a3755d27e64c52f8c95d6333119e49fd001ae5798dac872c95e0f8"},
|
||||
{file = "coverage-7.1.0-cp37-cp37m-manylinux_2_5_x86_64.manylinux1_x86_64.manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:ddb726cb861c3117a553f940372a495fe1078249ff5f8a5478c0576c7be12050"},
|
||||
{file = "coverage-7.1.0-cp37-cp37m-musllinux_1_1_aarch64.whl", hash = "sha256:51b236e764840a6df0661b67e50697aaa0e7d4124ca95e5058fa3d7cbc240b7c"},
|
||||
{file = "coverage-7.1.0-cp37-cp37m-musllinux_1_1_i686.whl", hash = "sha256:7ee5c9bb51695f80878faaa5598040dd6c9e172ddcf490382e8aedb8ec3fec8d"},
|
||||
{file = "coverage-7.1.0-cp37-cp37m-musllinux_1_1_x86_64.whl", hash = "sha256:c31b75ae466c053a98bf26843563b3b3517b8f37da4d47b1c582fdc703112bc3"},
|
||||
{file = "coverage-7.1.0-cp37-cp37m-win32.whl", hash = "sha256:3b155caf3760408d1cb903b21e6a97ad4e2bdad43cbc265e3ce0afb8e0057e73"},
|
||||
{file = "coverage-7.1.0-cp37-cp37m-win_amd64.whl", hash = "sha256:2a60d6513781e87047c3e630b33b4d1e89f39836dac6e069ffee28c4786715f5"},
|
||||
{file = "coverage-7.1.0-cp38-cp38-macosx_10_9_x86_64.whl", hash = "sha256:f2cba5c6db29ce991029b5e4ac51eb36774458f0a3b8d3137241b32d1bb91f06"},
|
||||
{file = "coverage-7.1.0-cp38-cp38-macosx_11_0_arm64.whl", hash = "sha256:beeb129cacea34490ffd4d6153af70509aa3cda20fdda2ea1a2be870dfec8d52"},
|
||||
{file = "coverage-7.1.0-cp38-cp38-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:0c45948f613d5d18c9ec5eaa203ce06a653334cf1bd47c783a12d0dd4fd9c851"},
|
||||
{file = "coverage-7.1.0-cp38-cp38-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:ef382417db92ba23dfb5864a3fc9be27ea4894e86620d342a116b243ade5d35d"},
|
||||
{file = "coverage-7.1.0-cp38-cp38-manylinux_2_5_x86_64.manylinux1_x86_64.manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:7c7c0d0827e853315c9bbd43c1162c006dd808dbbe297db7ae66cd17b07830f0"},
|
||||
{file = "coverage-7.1.0-cp38-cp38-musllinux_1_1_aarch64.whl", hash = "sha256:e5cdbb5cafcedea04924568d990e20ce7f1945a1dd54b560f879ee2d57226912"},
|
||||
{file = "coverage-7.1.0-cp38-cp38-musllinux_1_1_i686.whl", hash = "sha256:9817733f0d3ea91bea80de0f79ef971ae94f81ca52f9b66500c6a2fea8e4b4f8"},
|
||||
{file = "coverage-7.1.0-cp38-cp38-musllinux_1_1_x86_64.whl", hash = "sha256:218fe982371ac7387304153ecd51205f14e9d731b34fb0568181abaf7b443ba0"},
|
||||
{file = "coverage-7.1.0-cp38-cp38-win32.whl", hash = "sha256:04481245ef966fbd24ae9b9e537ce899ae584d521dfbe78f89cad003c38ca2ab"},
|
||||
{file = "coverage-7.1.0-cp38-cp38-win_amd64.whl", hash = "sha256:8ae125d1134bf236acba8b83e74c603d1b30e207266121e76484562bc816344c"},
|
||||
{file = "coverage-7.1.0-cp39-cp39-macosx_10_9_x86_64.whl", hash = "sha256:2bf1d5f2084c3932b56b962a683074a3692bce7cabd3aa023c987a2a8e7612f6"},
|
||||
{file = "coverage-7.1.0-cp39-cp39-macosx_11_0_arm64.whl", hash = "sha256:98b85dd86514d889a2e3dd22ab3c18c9d0019e696478391d86708b805f4ea0fa"},
|
||||
{file = "coverage-7.1.0-cp39-cp39-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:38da2db80cc505a611938d8624801158e409928b136c8916cd2e203970dde4dc"},
|
||||
{file = "coverage-7.1.0-cp39-cp39-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:3164d31078fa9efe406e198aecd2a02d32a62fecbdef74f76dad6a46c7e48311"},
|
||||
{file = "coverage-7.1.0-cp39-cp39-manylinux_2_5_x86_64.manylinux1_x86_64.manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:db61a79c07331e88b9a9974815c075fbd812bc9dbc4dc44b366b5368a2936063"},
|
||||
{file = "coverage-7.1.0-cp39-cp39-musllinux_1_1_aarch64.whl", hash = "sha256:9ccb092c9ede70b2517a57382a601619d20981f56f440eae7e4d7eaafd1d1d09"},
|
||||
{file = "coverage-7.1.0-cp39-cp39-musllinux_1_1_i686.whl", hash = "sha256:33ff26d0f6cc3ca8de13d14fde1ff8efe1456b53e3f0273e63cc8b3c84a063d8"},
|
||||
{file = "coverage-7.1.0-cp39-cp39-musllinux_1_1_x86_64.whl", hash = "sha256:d47dd659a4ee952e90dc56c97d78132573dc5c7b09d61b416a9deef4ebe01a0c"},
|
||||
{file = "coverage-7.1.0-cp39-cp39-win32.whl", hash = "sha256:d248cd4a92065a4d4543b8331660121b31c4148dd00a691bfb7a5cdc7483cfa4"},
|
||||
{file = "coverage-7.1.0-cp39-cp39-win_amd64.whl", hash = "sha256:7ed681b0f8e8bcbbffa58ba26fcf5dbc8f79e7997595bf071ed5430d8c08d6f3"},
|
||||
{file = "coverage-7.1.0-pp37.pp38.pp39-none-any.whl", hash = "sha256:755e89e32376c850f826c425ece2c35a4fc266c081490eb0a841e7c1cb0d3bda"},
|
||||
{file = "coverage-7.1.0.tar.gz", hash = "sha256:10188fe543560ec4874f974b5305cd1a8bdcfa885ee00ea3a03733464c4ca265"},
|
||||
{file = "coverage-7.3.2-cp310-cp310-macosx_10_9_x86_64.whl", hash = "sha256:d872145f3a3231a5f20fd48500274d7df222e291d90baa2026cc5152b7ce86bf"},
|
||||
{file = "coverage-7.3.2-cp310-cp310-macosx_11_0_arm64.whl", hash = "sha256:310b3bb9c91ea66d59c53fa4989f57d2436e08f18fb2f421a1b0b6b8cc7fffda"},
|
||||
{file = "coverage-7.3.2-cp310-cp310-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:f47d39359e2c3779c5331fc740cf4bce6d9d680a7b4b4ead97056a0ae07cb49a"},
|
||||
{file = "coverage-7.3.2-cp310-cp310-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:aa72dbaf2c2068404b9870d93436e6d23addd8bbe9295f49cbca83f6e278179c"},
|
||||
{file = "coverage-7.3.2-cp310-cp310-manylinux_2_5_x86_64.manylinux1_x86_64.manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:beaa5c1b4777f03fc63dfd2a6bd820f73f036bfb10e925fce067b00a340d0f3f"},
|
||||
{file = "coverage-7.3.2-cp310-cp310-musllinux_1_1_aarch64.whl", hash = "sha256:dbc1b46b92186cc8074fee9d9fbb97a9dd06c6cbbef391c2f59d80eabdf0faa6"},
|
||||
{file = "coverage-7.3.2-cp310-cp310-musllinux_1_1_i686.whl", hash = "sha256:315a989e861031334d7bee1f9113c8770472db2ac484e5b8c3173428360a9148"},
|
||||
{file = "coverage-7.3.2-cp310-cp310-musllinux_1_1_x86_64.whl", hash = "sha256:d1bc430677773397f64a5c88cb522ea43175ff16f8bfcc89d467d974cb2274f9"},
|
||||
{file = "coverage-7.3.2-cp310-cp310-win32.whl", hash = "sha256:a889ae02f43aa45032afe364c8ae84ad3c54828c2faa44f3bfcafecb5c96b02f"},
|
||||
{file = "coverage-7.3.2-cp310-cp310-win_amd64.whl", hash = "sha256:c0ba320de3fb8c6ec16e0be17ee1d3d69adcda99406c43c0409cb5c41788a611"},
|
||||
{file = "coverage-7.3.2-cp311-cp311-macosx_10_9_x86_64.whl", hash = "sha256:ac8c802fa29843a72d32ec56d0ca792ad15a302b28ca6203389afe21f8fa062c"},
|
||||
{file = "coverage-7.3.2-cp311-cp311-macosx_11_0_arm64.whl", hash = "sha256:89a937174104339e3a3ffcf9f446c00e3a806c28b1841c63edb2b369310fd074"},
|
||||
{file = "coverage-7.3.2-cp311-cp311-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:e267e9e2b574a176ddb983399dec325a80dbe161f1a32715c780b5d14b5f583a"},
|
||||
{file = "coverage-7.3.2-cp311-cp311-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:2443cbda35df0d35dcfb9bf8f3c02c57c1d6111169e3c85fc1fcc05e0c9f39a3"},
|
||||
{file = "coverage-7.3.2-cp311-cp311-manylinux_2_5_x86_64.manylinux1_x86_64.manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:4175e10cc8dda0265653e8714b3174430b07c1dca8957f4966cbd6c2b1b8065a"},
|
||||
{file = "coverage-7.3.2-cp311-cp311-musllinux_1_1_aarch64.whl", hash = "sha256:0cbf38419fb1a347aaf63481c00f0bdc86889d9fbf3f25109cf96c26b403fda1"},
|
||||
{file = "coverage-7.3.2-cp311-cp311-musllinux_1_1_i686.whl", hash = "sha256:5c913b556a116b8d5f6ef834038ba983834d887d82187c8f73dec21049abd65c"},
|
||||
{file = "coverage-7.3.2-cp311-cp311-musllinux_1_1_x86_64.whl", hash = "sha256:1981f785239e4e39e6444c63a98da3a1db8e971cb9ceb50a945ba6296b43f312"},
|
||||
{file = "coverage-7.3.2-cp311-cp311-win32.whl", hash = "sha256:43668cabd5ca8258f5954f27a3aaf78757e6acf13c17604d89648ecc0cc66640"},
|
||||
{file = "coverage-7.3.2-cp311-cp311-win_amd64.whl", hash = "sha256:e10c39c0452bf6e694511c901426d6b5ac005acc0f78ff265dbe36bf81f808a2"},
|
||||
{file = "coverage-7.3.2-cp312-cp312-macosx_10_9_x86_64.whl", hash = "sha256:4cbae1051ab791debecc4a5dcc4a1ff45fc27b91b9aee165c8a27514dd160836"},
|
||||
{file = "coverage-7.3.2-cp312-cp312-macosx_11_0_arm64.whl", hash = "sha256:12d15ab5833a997716d76f2ac1e4b4d536814fc213c85ca72756c19e5a6b3d63"},
|
||||
{file = "coverage-7.3.2-cp312-cp312-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:3c7bba973ebee5e56fe9251300c00f1579652587a9f4a5ed8404b15a0471f216"},
|
||||
{file = "coverage-7.3.2-cp312-cp312-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:fe494faa90ce6381770746077243231e0b83ff3f17069d748f645617cefe19d4"},
|
||||
{file = "coverage-7.3.2-cp312-cp312-manylinux_2_5_x86_64.manylinux1_x86_64.manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:f6e9589bd04d0461a417562649522575d8752904d35c12907d8c9dfeba588faf"},
|
||||
{file = "coverage-7.3.2-cp312-cp312-musllinux_1_1_aarch64.whl", hash = "sha256:d51ac2a26f71da1b57f2dc81d0e108b6ab177e7d30e774db90675467c847bbdf"},
|
||||
{file = "coverage-7.3.2-cp312-cp312-musllinux_1_1_i686.whl", hash = "sha256:99b89d9f76070237975b315b3d5f4d6956ae354a4c92ac2388a5695516e47c84"},
|
||||
{file = "coverage-7.3.2-cp312-cp312-musllinux_1_1_x86_64.whl", hash = "sha256:fa28e909776dc69efb6ed975a63691bc8172b64ff357e663a1bb06ff3c9b589a"},
|
||||
{file = "coverage-7.3.2-cp312-cp312-win32.whl", hash = "sha256:289fe43bf45a575e3ab10b26d7b6f2ddb9ee2dba447499f5401cfb5ecb8196bb"},
|
||||
{file = "coverage-7.3.2-cp312-cp312-win_amd64.whl", hash = "sha256:7dbc3ed60e8659bc59b6b304b43ff9c3ed858da2839c78b804973f613d3e92ed"},
|
||||
{file = "coverage-7.3.2-cp38-cp38-macosx_10_9_x86_64.whl", hash = "sha256:f94b734214ea6a36fe16e96a70d941af80ff3bfd716c141300d95ebc85339738"},
|
||||
{file = "coverage-7.3.2-cp38-cp38-macosx_11_0_arm64.whl", hash = "sha256:af3d828d2c1cbae52d34bdbb22fcd94d1ce715d95f1a012354a75e5913f1bda2"},
|
||||
{file = "coverage-7.3.2-cp38-cp38-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:630b13e3036e13c7adc480ca42fa7afc2a5d938081d28e20903cf7fd687872e2"},
|
||||
{file = "coverage-7.3.2-cp38-cp38-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:c9eacf273e885b02a0273bb3a2170f30e2d53a6d53b72dbe02d6701b5296101c"},
|
||||
{file = "coverage-7.3.2-cp38-cp38-manylinux_2_5_x86_64.manylinux1_x86_64.manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:d8f17966e861ff97305e0801134e69db33b143bbfb36436efb9cfff6ec7b2fd9"},
|
||||
{file = "coverage-7.3.2-cp38-cp38-musllinux_1_1_aarch64.whl", hash = "sha256:b4275802d16882cf9c8b3d057a0839acb07ee9379fa2749eca54efbce1535b82"},
|
||||
{file = "coverage-7.3.2-cp38-cp38-musllinux_1_1_i686.whl", hash = "sha256:72c0cfa5250f483181e677ebc97133ea1ab3eb68645e494775deb6a7f6f83901"},
|
||||
{file = "coverage-7.3.2-cp38-cp38-musllinux_1_1_x86_64.whl", hash = "sha256:cb536f0dcd14149425996821a168f6e269d7dcd2c273a8bff8201e79f5104e76"},
|
||||
{file = "coverage-7.3.2-cp38-cp38-win32.whl", hash = "sha256:307adb8bd3abe389a471e649038a71b4eb13bfd6b7dd9a129fa856f5c695cf92"},
|
||||
{file = "coverage-7.3.2-cp38-cp38-win_amd64.whl", hash = "sha256:88ed2c30a49ea81ea3b7f172e0269c182a44c236eb394718f976239892c0a27a"},
|
||||
{file = "coverage-7.3.2-cp39-cp39-macosx_10_9_x86_64.whl", hash = "sha256:b631c92dfe601adf8f5ebc7fc13ced6bb6e9609b19d9a8cd59fa47c4186ad1ce"},
|
||||
{file = "coverage-7.3.2-cp39-cp39-macosx_11_0_arm64.whl", hash = "sha256:d3d9df4051c4a7d13036524b66ecf7a7537d14c18a384043f30a303b146164e9"},
|
||||
{file = "coverage-7.3.2-cp39-cp39-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:5f7363d3b6a1119ef05015959ca24a9afc0ea8a02c687fe7e2d557705375c01f"},
|
||||
{file = "coverage-7.3.2-cp39-cp39-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:2f11cc3c967a09d3695d2a6f03fb3e6236622b93be7a4b5dc09166a861be6d25"},
|
||||
{file = "coverage-7.3.2-cp39-cp39-manylinux_2_5_x86_64.manylinux1_x86_64.manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:149de1d2401ae4655c436a3dced6dd153f4c3309f599c3d4bd97ab172eaf02d9"},
|
||||
{file = "coverage-7.3.2-cp39-cp39-musllinux_1_1_aarch64.whl", hash = "sha256:3a4006916aa6fee7cd38db3bfc95aa9c54ebb4ffbfc47c677c8bba949ceba0a6"},
|
||||
{file = "coverage-7.3.2-cp39-cp39-musllinux_1_1_i686.whl", hash = "sha256:9028a3871280110d6e1aa2df1afd5ef003bab5fb1ef421d6dc748ae1c8ef2ebc"},
|
||||
{file = "coverage-7.3.2-cp39-cp39-musllinux_1_1_x86_64.whl", hash = "sha256:9f805d62aec8eb92bab5b61c0f07329275b6f41c97d80e847b03eb894f38d083"},
|
||||
{file = "coverage-7.3.2-cp39-cp39-win32.whl", hash = "sha256:d1c88ec1a7ff4ebca0219f5b1ef863451d828cccf889c173e1253aa84b1e07ce"},
|
||||
{file = "coverage-7.3.2-cp39-cp39-win_amd64.whl", hash = "sha256:b4767da59464bb593c07afceaddea61b154136300881844768037fd5e859353f"},
|
||||
{file = "coverage-7.3.2-pp38.pp39.pp310-none-any.whl", hash = "sha256:ae97af89f0fbf373400970c0a21eef5aa941ffeed90aee43650b81f7d7f47637"},
|
||||
{file = "coverage-7.3.2.tar.gz", hash = "sha256:be32ad29341b0170e795ca590e1c07e81fc061cb5b10c74ce7203491484404ef"},
|
||||
]
|
||||
|
||||
[package.dependencies]
|
||||
|
|
|
|||
|
|
@ -32,6 +32,7 @@ INSTALLED_APPS = [
|
|||
'eav',
|
||||
]
|
||||
|
||||
|
||||
MIDDLEWARE = [
|
||||
'django.middleware.security.SecurityMiddleware',
|
||||
'django.contrib.sessions.middleware.SessionMiddleware',
|
||||
|
|
@ -69,7 +70,9 @@ DATABASES = {
|
|||
},
|
||||
}
|
||||
|
||||
|
||||
DEFAULT_AUTO_FIELD = 'django.db.models.AutoField'
|
||||
EAV2_PRIMARY_KEY_FIELD = 'django.db.models.AutoField'
|
||||
|
||||
|
||||
# Password validation
|
||||
|
|
|
|||
|
|
@ -1,10 +1,12 @@
|
|||
import uuid
|
||||
import string
|
||||
|
||||
from django.core.exceptions import ValidationError
|
||||
from django.test import TestCase
|
||||
from hypothesis import given, settings
|
||||
from hypothesis import strategies as st
|
||||
from hypothesis.extra import django
|
||||
from django.conf import settings as django_settings
|
||||
from hypothesis import strategies as st
|
||||
from hypothesis.strategies import just
|
||||
|
||||
import eav
|
||||
|
|
@ -14,6 +16,14 @@ from eav.registry import EavConfig
|
|||
from test_project.models import Doctor, Encounter, Patient, RegisterTestModel
|
||||
|
||||
|
||||
if django_settings.EAV2_PRIMARY_KEY_FIELD == "django.db.models.UUIDField":
|
||||
auto_field_strategy = st.builds(uuid.uuid4, version=4, max_length=32)
|
||||
elif django_settings.EAV2_PRIMARY_KEY_FIELD == "django.db.models.CharField":
|
||||
auto_field_strategy = st.text(min_size=1, max_size=255)
|
||||
else:
|
||||
auto_field_strategy = st.integers(min_value=1, max_value=32)
|
||||
|
||||
|
||||
class Attributes(TestCase):
|
||||
def setUp(self):
|
||||
class EncounterEavConfig(EavConfig):
|
||||
|
|
@ -123,6 +133,7 @@ class TestAttributeModel(django.TestCase):
|
|||
@given(
|
||||
django.from_model(
|
||||
Attribute,
|
||||
id=auto_field_strategy,
|
||||
datatype=just(Attribute.TYPE_TEXT),
|
||||
enum_group=just(None),
|
||||
),
|
||||
|
|
|
|||
51
tests/test_natural_keys.py
Normal file
51
tests/test_natural_keys.py
Normal file
|
|
@ -0,0 +1,51 @@
|
|||
from django.test import TestCase
|
||||
from eav.models import Attribute, EnumGroup, EnumValue, Value
|
||||
from test_project.models import Patient
|
||||
import eav
|
||||
|
||||
|
||||
class ModelTest(TestCase):
|
||||
def setUp(self):
|
||||
eav.register(Patient)
|
||||
Attribute.objects.create(name='age', datatype=Attribute.TYPE_INT)
|
||||
Attribute.objects.create(name='height', datatype=Attribute.TYPE_FLOAT)
|
||||
Attribute.objects.create(name='weight', datatype=Attribute.TYPE_FLOAT)
|
||||
Attribute.objects.create(name='color', datatype=Attribute.TYPE_TEXT)
|
||||
|
||||
EnumGroup.objects.create(name='Yes / No')
|
||||
EnumValue.objects.create(value='yes')
|
||||
EnumValue.objects.create(value='no')
|
||||
EnumValue.objects.create(value='unknown')
|
||||
|
||||
def test_attr_natural_keys(self):
|
||||
attr = Attribute.objects.get(name='age')
|
||||
attr_natural_key = attr.natural_key()
|
||||
attr_retrieved_model = Attribute.objects.get_by_natural_key(*attr_natural_key)
|
||||
self.assertEqual(attr_retrieved_model, attr)
|
||||
|
||||
def test_value_natural_keys(self):
|
||||
p = Patient.objects.create(name='Jon')
|
||||
p.eav.age = 5
|
||||
p.save()
|
||||
|
||||
val = p.eav_values.first()
|
||||
|
||||
value_natural_key = val.natural_key()
|
||||
value_retrieved_model = Value.objects.get_by_natural_key(*value_natural_key)
|
||||
self.assertEqual(value_retrieved_model, val)
|
||||
|
||||
def test_enum_group_natural_keys(self):
|
||||
enum_group = EnumGroup.objects.first()
|
||||
enum_group_natural_key = enum_group.natural_key()
|
||||
enum_group_retrieved_model = EnumGroup.objects.get_by_natural_key(
|
||||
*enum_group_natural_key
|
||||
)
|
||||
self.assertEqual(enum_group_retrieved_model, enum_group)
|
||||
|
||||
def test_enum_value_natural_keys(self):
|
||||
enum_value = EnumValue.objects.first()
|
||||
enum_value_natural_key = enum_value.natural_key()
|
||||
enum_value_retrieved_model = EnumValue.objects.get_by_natural_key(
|
||||
*enum_value_natural_key
|
||||
)
|
||||
self.assertEqual(enum_value_retrieved_model, enum_value)
|
||||
33
tests/test_primary_key_format.py
Normal file
33
tests/test_primary_key_format.py
Normal file
|
|
@ -0,0 +1,33 @@
|
|||
import uuid
|
||||
|
||||
import pytest
|
||||
from django.db import models
|
||||
|
||||
from eav.logic.object_pk import get_pk_format
|
||||
|
||||
|
||||
def test_get_uuid_primary_key(settings) -> None:
|
||||
settings.EAV2_PRIMARY_KEY_FIELD = "django.db.models.UUIDField"
|
||||
primary_field = get_pk_format()
|
||||
assert isinstance(primary_field, models.UUIDField)
|
||||
assert primary_field.primary_key
|
||||
assert not primary_field.editable
|
||||
assert primary_field.default == uuid.uuid4
|
||||
|
||||
|
||||
def test_get_char_primary_key(settings) -> None:
|
||||
settings.EAV2_PRIMARY_KEY_FIELD = "django.db.models.CharField"
|
||||
primary_field = get_pk_format()
|
||||
assert isinstance(primary_field, models.CharField)
|
||||
assert primary_field.primary_key
|
||||
assert not primary_field.editable
|
||||
assert primary_field.max_length == 40
|
||||
|
||||
|
||||
def test_get_default_primary_key(settings) -> None:
|
||||
# This test covers the default case for "BigAutoField"
|
||||
settings.EAV2_PRIMARY_KEY_FIELD = "AnyOtherField"
|
||||
primary_field = get_pk_format()
|
||||
assert isinstance(primary_field, models.BigAutoField)
|
||||
assert primary_field.primary_key
|
||||
assert not primary_field.editable
|
||||
Loading…
Reference in a new issue