Opened 4 hours ago

Last modified 93 minutes ago

#36092 new Bug

Composite primary key wrongly allows non-local fields to be referenced

Reported by: Jacob Walls Owned by:
Component: Database layer (models, ORM) Version: dev
Severity: Release blocker Keywords:
Cc: Triage Stage: Accepted
Has patch: no Needs documentation: no
Needs tests: no Patch needs improvement: no
Easy pickings: no UI/UX: no

Description

(As ever, let me know if this is a known/deferred issue--just trying to report anything I noticed while taking a look around.)


With these models:

class CoffeeProduct(models.Model):
    whole_bean = models.BooleanField()


class SpecialtyCoffeeProduct(CoffeeProduct):
    pk = models.CompositePrimaryKey("whole_bean", "varietal")
    varietal = models.CharField()

This migration is generated on sqlite:

BEGIN;
--
-- Create model CoffeeProduct
--
CREATE TABLE "appName_coffeeproduct" ("id" integer NOT NULL PRIMARY KEY AUTOINCREMENT, "whole_bean" bool NOT NULL);
--
-- Create model SpecialtyCoffeeProduct
--
CREATE TABLE "appName_specialtycoffeeproduct" ("coffeeproduct_ptr_id" bigint NOT NULL UNIQUE REFERENCES "appName_coffeeproduct" ("id") DEFERRABLE INITIALLY DEFERRED, "varietal" varchar NOT NULL, PRIMARY KEY ("whole_bean", "varietal"));
COMMIT;

And fails when executed:

  File "/Users/<user>/django/django/db/backends/sqlite3/base.py", line 356, in execute
    return super().execute(query)
           ^^^^^^^^^^^^^^^^^^^^^^
django.db.utils.OperationalError: expressions prohibited in PRIMARY KEY and UNIQUE constraints

Change History (1)

comment:1 by Simon Charette, 93 minutes ago

Summary: Composite primary key creates invalid migration when one of its fields is inheritedComposite primary key wrongly allows non-local fields to be referenced
Triage Stage: UnreviewedAccepted

The crux of the issue here is that CompositePrimaryKey allows non-local field to be referenced. Fields inherited from an abstract based should be allowed to be referenced but ones from a concrete base (aka non-local / defined on a referenced table) should not.

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