1

I'm trying to populate the data in the database for the Employee Model Also, I'm not going to use Foreign Key ID's as given below

Example 1:

- model: employee.employee
  pk: 1
  fields: 
    user: 1
    manager: NULL
    department: 1
    job_level: 5
    created_at: '2021-06-03'
    updated_at: '2021-06-03'

Instead, I'm going to Use Unique values of the respective Model as given below

Example 2:

- model: employee.employee
  pk: 1
  fields: 
    user: [manager.finance]
    manager: NULL
    department: [Finance]
    job_level: [MNGR]
    created_at: '2021-06-03'
    updated_at: '2021-06-03'

models.py File

from django.db import models
from django.conf import settings
from django.db.models import Q



class TimestampedModel(models.Model):
    created_at = models.DateField(auto_now_add=True)
    updated_at = models.DateField(auto_now=True)

    class Meta:
        abstract = True


class DepartmentManager(models.Manager):
    def get_by_natural_key(self, name):
        return self.get(name=name)


class Department(TimestampedModel):
    name = models.CharField(max_length=128, unique=True)

    objects = DepartmentManager()

    class Meta:
        db_table = 'tc_departments'

    def __str__(self):
        return f'{self.name}'


class JobLevelManager(models.Manager):
    def get_by_natural_key(self, handle):
        return self.get(handle=handle)


class JobLevel(models.Model):
    handle = models.CharField(max_length=32, unique=True)
    display_name = models.CharField(max_length=64, null=True, blank=True)
    
    objects = JobLevelManager()

    class Meta:
        db_table = 'tc_job_levels'

    def __str__(self):
        return f'{self.handle} and {self.display_name}'





class EmployeeManager(models.Manager):
    def get_by_natural_key(self, user):
        return self.get(user=user)


class Employee(TimestampedModel):
    user = models.OneToOneField(settings.AUTH_USER_MODEL, on_delete=models.PROTECT)
    manager = models.ForeignKey('self', on_delete=models.CASCADE,
        limit_choices_to={'manager__isnull': True}, null=True, blank=True)
    department = models.ForeignKey(Department, on_delete=models.CASCADE)
    job_level = models.ForeignKey(JobLevel, on_delete=models.CASCADE)
    profile_pic = models.ImageField(upload_to='photos/%Y/%m/%d', max_length=128,
        null=True,
        blank=True)
    
    objects = EmployeeManager()

    class Meta:
        db_table = 'tc_employees'
        unique_together = [['department', 'job_level']]

    def __str__(self):
        return f'{self.user}'


class Asset(TimestampedModel):

    class DeviceType(models.TextChoices):
        PHONE = 'PH', 'Phone'
        TABLET = 'TB', 'Tablet'
        LAPTOP = 'LP', 'Laptop'
        DESKTOP = 'DS', 'Desktop'

    device_type = models.CharField(max_length=2,
                                   choices=DeviceType.choices,
                                   default=DeviceType.LAPTOP)
    serial_number = models.CharField(max_length=32, unique=True)
    assigned_to = models.ForeignKey(Employee, on_delete=models.PROTECT)
    assigned_on = models.DateTimeField()
    returned_on = models.DateTimeField(blank=True, null=True)

    class Meta:
        db_table = 'tc_assets'

    def __str__(self):
        return f'{self.device_type.label} serial: {self.serial_number}'

Let's consider Example 2 I'm going to populate data as like in Example 2 To do that

We can use the user field from Employee Model because the user field is unique

If I use the below YAML file I'm getting an error

Example 3:

- model: employee.employee
  pk: 1
  fields: 
    user: [manager.finance]
    manager: NULL
    department: [Finance]
    job_level: [MNGR]
    created_at: '2021-06-03'
    updated_at: '2021-06-03'
- model: employee.employee
  pk: 2
  fields: 
    user: [team_leader.finance]
    manager: [manager.finance]
    department: [Finance]
    job_level: [LEAD]
    created_at: '2021-06-03'
    updated_at: '2021-06-03'

Error

Traceback (most recent call last):
  File "/home/selvaganesh/.virtualenvs/mtest/lib/python3.8/site-packages/django/db/models/fields/__init__.py", line 1823, in get_prep_value
    return int(value)
ValueError: invalid literal for int() with base 10: 'manager.finance'

The above exception was the direct cause of the following exception:

Traceback (most recent call last):
  File "/home/selvaganesh/.virtualenvs/mtest/lib/python3.8/site-packages/django/core/serializers/python.py", line 134, in Deserializer
    value = base.deserialize_fk_value(field, field_value, using, handle_forward_references)
  File "/home/selvaganesh/.virtualenvs/mtest/lib/python3.8/site-packages/django/core/serializers/base.py", line 310, in deserialize_fk_value
    obj = default_manager.db_manager(using).get_by_natural_key(*field_value)
  File "/home/selvaganesh/models/mtest/employee/models.py", line 67, in get_by_natural_key
    return self.get(user=user)
  File "/home/selvaganesh/.virtualenvs/mtest/lib/python3.8/site-packages/django/db/models/manager.py", line 85, in manager_method
    return getattr(self.get_queryset(), name)(*args, **kwargs)
  File "/home/selvaganesh/.virtualenvs/mtest/lib/python3.8/site-packages/django/db/models/query.py", line 424, in get
    clone = self._chain() if self.query.combinator else self.filter(*args, **kwargs)
  File "/home/selvaganesh/.virtualenvs/mtest/lib/python3.8/site-packages/django/db/models/query.py", line 941, in filter
    return self._filter_or_exclude(False, args, kwargs)
  File "/home/selvaganesh/.virtualenvs/mtest/lib/python3.8/site-packages/django/db/models/query.py", line 961, in _filter_or_exclude
    clone._filter_or_exclude_inplace(negate, args, kwargs)
  File "/home/selvaganesh/.virtualenvs/mtest/lib/python3.8/site-packages/django/db/models/query.py", line 968, in _filter_or_exclude_inplace
    self._query.add_q(Q(*args, **kwargs))
  File "/home/selvaganesh/.virtualenvs/mtest/lib/python3.8/site-packages/django/db/models/sql/query.py", line 1391, in add_q
    clause, _ = self._add_q(q_object, self.used_aliases)
  File "/home/selvaganesh/.virtualenvs/mtest/lib/python3.8/site-packages/django/db/models/sql/query.py", line 1410, in _add_q
    child_clause, needed_inner = self.build_filter(
  File "/home/selvaganesh/.virtualenvs/mtest/lib/python3.8/site-packages/django/db/models/sql/query.py", line 1345, in build_filter
    condition = self.build_lookup(lookups, col, value)
  File "/home/selvaganesh/.virtualenvs/mtest/lib/python3.8/site-packages/django/db/models/sql/query.py", line 1191, in build_lookup
    lookup = lookup_class(lhs, rhs)
  File "/home/selvaganesh/.virtualenvs/mtest/lib/python3.8/site-packages/django/db/models/lookups.py", line 25, in __init__
    self.rhs = self.get_prep_lookup()
  File "/home/selvaganesh/.virtualenvs/mtest/lib/python3.8/site-packages/django/db/models/fields/related_lookups.py", line 117, in get_prep_lookup
    self.rhs = target_field.get_prep_value(self.rhs)
  File "/home/selvaganesh/.virtualenvs/mtest/lib/python3.8/site-packages/django/db/models/fields/__init__.py", line 1825, in get_prep_value
    raise e.__class__(
ValueError: Field 'id' expected a number but got 'manager.finance'.

During handling of the above exception, another exception occurred:

Traceback (most recent call last):
  File "manage.py", line 22, in <module>
    main()
  File "manage.py", line 18, in main
    execute_from_command_line(sys.argv)
  File "/home/selvaganesh/.virtualenvs/mtest/lib/python3.8/site-packages/django/core/management/__init__.py", line 419, in execute_from_command_line
    utility.execute()
  File "/home/selvaganesh/.virtualenvs/mtest/lib/python3.8/site-packages/django/core/management/__init__.py", line 413, in execute
    self.fetch_command(subcommand).run_from_argv(self.argv)
  File "/home/selvaganesh/.virtualenvs/mtest/lib/python3.8/site-packages/django/core/management/base.py", line 354, in run_from_argv
    self.execute(*args, **cmd_options)
  File "/home/selvaganesh/.virtualenvs/mtest/lib/python3.8/site-packages/django/core/management/base.py", line 398, in execute
    output = self.handle(*args, **options)
  File "/home/selvaganesh/.virtualenvs/mtest/lib/python3.8/site-packages/django/core/management/commands/loaddata.py", line 78, in handle
    self.loaddata(fixture_labels)
  File "/home/selvaganesh/.virtualenvs/mtest/lib/python3.8/site-packages/django/core/management/commands/loaddata.py", line 123, in loaddata
    self.load_label(fixture_label)
  File "/home/selvaganesh/.virtualenvs/mtest/lib/python3.8/site-packages/django/core/management/commands/loaddata.py", line 181, in load_label
    for obj in objects:
  File "/home/selvaganesh/.virtualenvs/mtest/lib/python3.8/site-packages/django/core/serializers/pyyaml.py", line 76, in Deserializer
    yield from PythonDeserializer(yaml.load(stream, Loader=SafeLoader), **options)
  File "/home/selvaganesh/.virtualenvs/mtest/lib/python3.8/site-packages/django/core/serializers/python.py", line 136, in Deserializer
    raise base.DeserializationError.WithData(e, d['model'], d.get('pk'), field_value)
django.core.serializers.base.DeserializationError: Problem installing fixture '/home/selvaganesh/models/mtest/employee/fixtures/employee.yaml': Field 'id' expected a number but got 'manager.finance'.: (employee.employee:pk=2) field_value was '['manager.finance']'

The problem I'm facing is only because of the pk: 2, manager field in Example 3

Example 2 is working Fine

Other Foreign Key Fields user, department, job_level everything working fine

If I use manager: NULL working fine But If I use manager: [manager.fianance] I'm getting an Error

How to resolve this Problem manager: [manager.finance] Please help me out

0 Answers0