Opened 4 years ago

Closed 3 years ago

#32205 closed Bug (invalid)

sqlmigrate crashes after removing squashed migrations.

Reported by: 老广 Owned by: nobody
Component: Database layer (models, ORM) Version: 3.1
Severity: Normal Keywords: sqlmigrate
Cc: ibuler@… Triage Stage: Accepted
Has patch: no Needs documentation: no
Needs tests: no Patch needs improvement: no
Easy pickings: no UI/UX: no

Description

After upgrade django 2.2 to 3.1, If migrations was squashed, then sqlmigrate cause error. If back to 2.2, error lost.

The migrate file error refer is in squash file.

Error stack

  File "/Users/guang/vm/py/py36/lib/python3.6/site-packages/django/core/management/commands/sqlmigrate.py", line 37, in handle
    loader = MigrationLoader(connection, replace_migrations=False)
  File "/Users/guang/vm/py/py36/lib/python3.6/site-packages/django/db/migrations/loader.py", line 53, in __init__
    self.build_graph()
  File "/Users/guang/vm/py/py36/lib/python3.6/site-packages/django/db/migrations/loader.py", line 255, in build_graph
    self.graph.validate_consistency()
  File "/Users/guang/vm/py/py36/lib/python3.6/site-packages/django/db/migrations/graph.py", line 195, in validate_consistency
    [n.raise_error() for n in self.node_map.values() if isinstance(n, DummyNode)]
  File "/Users/guang/vm/py/py36/lib/python3.6/site-packages/django/db/migrations/graph.py", line 195, in <listcomp>
    [n.raise_error() for n in self.node_map.values() if isinstance(n, DummyNode)]
  File "/Users/guang/vm/py/py36/lib/python3.6/site-packages/django/db/migrations/graph.py", line 58, in raise_error
    raise NodeNotFoundError(self.error_message, self.key, origin=self.origin)
django.db.migrations.exceptions.NodeNotFoundError: Migration assets.0020_auto_20180816_1652 dependencies reference nonexistent parent node ('assets', '0019_auto_20180816_1320')


Migrations

source code: https://github.com/jumpserver/jumpserver/blob/master/apps/assets/migrations/0020_auto_20180816_1652.py

# Generated by Django 2.0.7 on 2018-08-16 08:52

from django.db import migrations, models


class Migration(migrations.Migration):

    dependencies = [
        ('assets', '0019_auto_20180816_1320'),
    ]

    operations = [
        migrations.AlterField(
            model_name='adminuser',
            name='org_id',
            field=models.CharField(blank=True, db_index=True, default='', max_length=36, verbose_name='Organization'),
        ),

The squash migrations:

source code: https://github.com/jumpserver/jumpserver/blob/master/apps/assets/migrations/0010_auto_20180307_1749_squashed_0019_auto_20180816_1320.py

class Migration(migrations.Migration):

    replaces = [('assets', '0010_auto_20180307_1749'), ('assets', '0011_auto_20180326_0957'), ('assets', '0012_auto_20180404_1302'), ('assets', '0013_auto_20180411_1135'), ('assets', '0014_auto_20180427_1245'), ('assets', '0015_auto_20180510_1235'), ('assets', '0016_auto_20180511_1203'), ('assets', '0017_auto_20180702_1415'), ('assets', '0018_auto_20180807_1116'), ('assets', '0019_auto_20180816_1320')]

    dependencies = [
        ('assets', '0009_auto_20180307_1212'),
    ]

Attachments (1)

ticket_32205.tar (30.0 KB ) - added by Mariusz Felisiak 3 years ago.
Sample project.

Download all attachments as: .zip

Change History (9)

comment:1 by 老广, 4 years ago

Type: UncategorizedBug

comment:2 by Carlton Gibson, 4 years ago

Resolution: worksforme
Status: newclosed

Hi. Thanks for the report. — I can't reproduce this from the given info.

Steps taken:

  • Create new venv with Django 2.2.17
  • Create new project with simple model.
  • Add fields, creating new migrations.
  • Squash migrations
  • Update to Django 3.1.3.
  • Adjust model, create new migration (from squashed migration).

All worked as expected.

It's not clear what's going on in your case. If you can reduce it to a minimal example showing an issue in Django we can look again. Sorry. Thanks.

in reply to:  2 comment:3 by elonzh, 3 years ago

Replying to Carlton Gibson:

Hi. Thanks for the report. — I can't reproduce this from the given info.

Steps taken:

  • Create new venv with Django 2.2.17
  • Create new project with simple model.
  • Add fields, creating new migrations.
  • Squash migrations
  • Update to Django 3.1.3.
  • Adjust model, create new migration (from squashed migration).

All worked as expected.

It's not clear what's going on in your case. If you can reduce it to a minimal example showing an issue in Django we can look again. Sorry. Thanks.

This issue can be reproduced by removing the replaced migrations and the reported case above is just what I said.

As the squashmigrations said:

You should commit this migration but leave the old ones in place;

the new migration will be used for new installs. Once you are sure
all instances of the codebase have applied the migrations you squashed,
you can delete them.

This means deleting the replaced migrations is normal behavior and should not cause any exception like this issue.

Version 0, edited 3 years ago by elonzh (next)

comment:4 by elonzh, 3 years ago

Resolution: worksforme
Status: closednew

comment:5 by Mariusz Felisiak, 3 years ago

Resolution: needsinfo
Status: newclosed

I cannot reproduce this issue even if I remove squashed migrations. Can you provide a sample project?

by Mariusz Felisiak, 3 years ago

Attachment: ticket_32205.tar added

Sample project.

comment:6 by Mariusz Felisiak, 3 years ago

Resolution: needsinfo
Status: closednew
Summary: ORM migrations after squash, command sqlmigrate will be errorsqlmigrate crashes after removing squashed migrations.
Triage Stage: UnreviewedAccepted

OK, I can reproduce this issue and attached a sample project:

$ python manage.py sqlmigrate test_one 0008
....
  File "/django/django/db/migrations/graph.py", line 58, in raise_error
    raise NodeNotFoundError(self.error_message, self.key, origin=self.origin)
django.db.migrations.exceptions.NodeNotFoundError: Migration test_one.0006_mymodel_field_8 dependencies reference nonexistent parent node ('test_one', '0005_mymodel_field_7')

comment:7 by Stian Jensen, 3 years ago

What is not mentioned in the CLI output, but in the documentation is the following:

You must then transition the squashed migration to a normal migration by:

  • Deleting all the migration files it replaces.
  • Updating all migrations that depend on the deleted migrations to depend on the squashed migration instead.
  • Removing the replaces attribute in the Migration class of the squashed migration (this is how Django tells that it is a squashed migration).

https://docs.djangoproject.com/en/3.2/topics/migrations/#squashing-migrations

Did you also do that?

Maybe it should be better explained also from the CLI.

comment:8 by Mariusz Felisiak, 3 years ago

Resolution: invalid
Status: newclosed

Thanks Stian! I missed that it's already documented, the second point is crucial:

"Updating all migrations that depend on the deleted migrations to depend on the squashed migration instead."

Note: See TracTickets for help on using tickets.
Back to Top