This happens in two different code paths, ultimately affecting
Options::_get_default_pk_class:
1. When AppConfigStub is supplied instead of AppConfig it is stripped from
most of the properties including default_auto_field.
2. When the first migration for a given app is applied, we don't get any
app config as it is lazily registered in StateApps::register_models. As
this is the first model for this app, the config is no there yet.
Here's modified configuration for polls app that demonstrates the issue:
mysite/settings.py:
{{{#!python
...
DATABASES = {
'default': {
'ENGINE': 'django.db.backends.postgresql',
'NAME': 'empty',
}
}
...
DEFAULT_AUTO_FIELD = 'django.db.models.AutoField'
}}}
mysite/polls/apps.py:
{{{#!python
...
class PollsConfig(AppConfig):
default_auto_field = 'django.db.models.BigAutoField'
name = 'polls'
}}}
mysite/polls/models.py:
{{{#!python
...
class KlassA(models.Model):
field_a = models.CharField(max_length=200)
class KlassB(models.Model):
field_b = models.CharField(max_length=200)
m2m_to_a = models.ManyToManyField(
KlassA, blank=True
)
}}}
Then run `makemigrations` and `sqlmigrate polls 0001_initial`:
{{{
BEGIN;
--
-- Create model KlassA
--
CREATE TABLE "polls_klassa" ("id" bigserial NOT NULL PRIMARY KEY,
"field_a" varchar(200) NOT NULL);
--
-- Create model KlassB
--
CREATE TABLE "polls_klassb" ("id" bigserial NOT NULL PRIMARY KEY,
"field_b" varchar(200) NOT NULL);
CREATE TABLE "polls_klassb_m2m_to_a" ("id" serial NOT NULL PRIMARY KEY,
"klassb_id" bigint NOT NULL, "klassa_id" bigint NOT NULL);
ALTER TABLE "polls_klassb_m2m_to_a" ADD CONSTRAINT
"polls_klassb_m2m_to_a_klassb_id_klassa_id_05b47d06_uniq" UNIQUE
("klassb_id", "klassa_id");
ALTER TABLE "polls_klassb_m2m_to_a" ADD CONSTRAINT
"polls_klassb_m2m_to_a_klassb_id_58ef37e1_fk_polls_klassb_id" FOREIGN KEY
("klassb_id") REFERENCES "polls_klassb" ("id") DEFERRABLE INITIALLY
DEFERRED;
ALTER TABLE "polls_klassb_m2m_to_a" ADD CONSTRAINT
"polls_klassb_m2m_to_a_klassa_id_b63f26b4_fk_polls_klassa_id" FOREIGN KEY
("klassa_id") REFERENCES "polls_klassa" ("id") DEFERRABLE INITIALLY
DEFERRED;
CREATE INDEX "polls_klassb_m2m_to_a_klassb_id_58ef37e1" ON
"polls_klassb_m2m_to_a" ("klassb_id");
CREATE INDEX "polls_klassb_m2m_to_a_klassa_id_b63f26b4" ON
"polls_klassb_m2m_to_a" ("klassa_id");
COMMIT;
}}}
Here we get `CREATE TABLE "polls_klassb_m2m_to_a" ("id" serial NOT NULL
PRIMARY KEY...`
If we change in settings.py `DEFAULT_AUTO_FIELD` to
`django.db.models.BigAutoField` we get `CREATE TABLE
"polls_klassb_m2m_to_a" ("id" bigserial NOT NULL PRIMARY KEY...`
I did a little bit of research and found out 2 probable causes affecting
Options::_get_default_pk_class:
1. When AppConfigStub is supplied instead of AppConfig it is stripped
from most of the properties including default_auto_field.
2. When the first migration for a given app is applied, we don't get
any app config as it is lazily registered in StateApps::register_models.
As this is the first model for this app, the config is no there yet.
--
Ticket URL: <https://code.djangoproject.com/ticket/33914>
Django <https://code.djangoproject.com/>
The Web framework for perfectionists with deadlines.
* status: new => closed
* resolution: => duplicate
* component: Migrations => Database layer (models, ORM)
Comment:
Duplicate of #32674, see also a note in
[https://docs.djangoproject.com/en/stable/ref/settings/#default-auto-field
DEFAULT_AUTO_FIELD docs].
--
Ticket URL: <https://code.djangoproject.com/ticket/33914#comment:1>
Comment (by Borislav Ivanov):
Replying to [comment:1 Mariusz Felisiak]:
> Duplicate of #32674, see also a note in
[https://docs.djangoproject.com/en/stable/ref/settings/#default-auto-field
DEFAULT_AUTO_FIELD docs].
I see your point here, however this is not exactly the same case.
#32674 refers to change in DEFAULT_AUTO_FIELD not being reflected in a
migration. This report refers to app level default_auto_field not taking
precedence over DEFAULT_AUTO_FIELD as stated in
https://docs.djangoproject.com/en/4.1/ref/models/fields/#primary-key.
Having said this I do understand this being postponed as feature request,
just wanted to be sure that the use case is clear enough.
--
Ticket URL: <https://code.djangoproject.com/ticket/33914#comment:2>
Comment (by Mariusz Felisiak):
Replying to [comment:2 Borislav Ivanov]:
> Replying to [comment:1 Mariusz Felisiak]:
> > Duplicate of #32674, see also a note in
[https://docs.djangoproject.com/en/stable/ref/settings/#default-auto-field
DEFAULT_AUTO_FIELD docs].
>
> I see your point here, however this is not exactly the same case.
>
> #32674 refers to change in DEFAULT_AUTO_FIELD not being reflected in a
migration. This report refers to app level default_auto_field not taking
precedence over DEFAULT_AUTO_FIELD as stated in
https://docs.djangoproject.com/en/4.1/ref/models/fields/#primary-key.
>
> Having said this I do understand this being postponed as feature
request, just wanted to be sure that the use case is clear enough.
As far as I'm aware fixing #32674 should also fix a precedence.
--
Ticket URL: <https://code.djangoproject.com/ticket/33914#comment:3>