Migrations fail with order_with_respect_to and ForeignKey to self
|Reported by:||Jonas||Owned by:||andrewgodwin|
|Severity:||Release blocker||Keywords:||migrations order_with_respect_to|
|Cc:||Jonas, shai, jezevec, beathan||Triage Stage:||Accepted|
|Has patch:||no||Needs documentation:||no|
|Needs tests:||no||Patch needs improvement:||no|
Initial migrations for an app with this kind of model setup will fail when running ./manage.py migrate:
class Parent(models.Model): spouse = models.ForeignKey('self') class Child(models.Model): parent = models.ForeignKey(Parent) class Meta: order_with_respect_to = 'parent'
This is the resulting traceback:
File "./manage.py", line 10, in <module> execute_from_command_line(sys.argv) File "/home/jonas/temp/django/django/core/management/__init__.py", line 427, in execute_from_command_line utility.execute() File "/home/jonas/temp/django/django/core/management/__init__.py", line 419, in execute self.fetch_command(subcommand).run_from_argv(self.argv) File "/home/jonas/temp/django/django/core/management/base.py", line 288, in run_from_argv self.execute(*args, **options.__dict__) File "/home/jonas/temp/django/django/core/management/base.py", line 337, in execute output = self.handle(*args, **options) File "/home/jonas/temp/django/django/core/management/commands/migrate.py", line 145, in handle executor.migrate(targets, plan, fake=options.get("fake", False)) File "/home/jonas/temp/django/django/db/migrations/executor.py", line 60, in migrate self.apply_migration(migration, fake=fake) File "/home/jonas/temp/django/django/db/migrations/executor.py", line 88, in apply_migration if self.detect_soft_applied(migration): File "/home/jonas/temp/django/django/db/migrations/executor.py", line 132, in detect_soft_applied apps = project_state.render() File "/home/jonas/temp/django/django/db/migrations/state.py", line 48, in render model.render(self.apps) File "/home/jonas/temp/django/django/db/migrations/state.py", line 232, in render body, File "/home/jonas/temp/django/django/db/models/base.py", line 298, in __new__ new_class._prepare() File "/home/jonas/temp/django/django/db/models/base.py", line 322, in _prepare opts._prepare(cls) File "/home/jonas/temp/django/django/db/models/options.py", line 180, in _prepare self.order_with_respect_to = self.get_field(self.order_with_respect_to) File "/home/jonas/temp/django/django/db/models/options.py", line 397, in get_field raise FieldDoesNotExist('%s has no field named %r' % (self.object_name, name)) django.db.models.fields.FieldDoesNotExist: Child has no field named 'parent'
makemigrations creates three migrations:
- The first migration creates the Child model without the parent field as well as the Parent model without the spouse field.
- The second migration adds the spouse field to Parent.
- The third migration adds parent to Child.
The error occurs in the first migration, when the _prepare() wants to access the parent field for order_with_respect_to and can't, as it doesn't exist yet.
I tried adding a test in Django proper but wasn't able to. Will keep trying but support is appreciated.
Change History (11)
comment:1 Changed 2 years ago by Jonas
- Cc Jonas added
- Needs documentation unset
- Needs tests unset
- Patch needs improvement unset
comment:2 Changed 2 years ago by timo
- Severity changed from Normal to Release blocker
- Triage Stage changed from Unreviewed to Accepted
comment:3 Changed 2 years ago by andrewgodwin
- Owner changed from nobody to andrewgodwin
- Status changed from new to assigned
comment:10 Changed 23 months ago by Andrew Godwin <andrew@…>
- Resolution set to fixed
- Status changed from assigned to closed