-
-
Notifications
You must be signed in to change notification settings - Fork 7
Description
Describe the bug
var queryParam = fieldName + "__id__exact"; |
DALF assumes that the related model must have .id
field.
To Reproduce
Start from the test project in tests/testproject
of this repository.
cd $(mktemp -d)
git clone https://github.com/vigo/django-admin-list-filter
cd django-admin-list-filter
cd test/testproject
python -m venv venv
. ./venv/bin/activate
pip install 'django==5.1.5' ../..
vim testapp/models.py
# Edit the models file to use `uuid` as PK, see full contents below
./manage makemigrations && ./manage.py migrate
./manage.py createsuperuser --username demo --email demo@demo.com # Provide any password
./manage.py shell -c 'from testapp.models import Category; Category.objects.create(name="Foo")'
./manage.py runserver
Now visit the live server URL with /admin
appended in any browser, sign in and navigate to the Post model (http://localhost:8000/admin/testapp/post/). Try to select "Foo" category in the filter. Observe url change to .../?e=1
, which indicates incorrect lookup fields. Try to select it again to observe a "database error" message.
Here's the full content of new models.py
that can be copy&paste'd directly:
import uuid
from django.conf import settings
from django.db import models
class Category(models.Model):
uuid = models.UUIDField(primary_key=True, default=uuid.uuid4, editable=False)
name = models.CharField(max_length=255)
def __str__(self):
return self.name
class Tag(models.Model):
uuid = models.UUIDField(primary_key=True, default=uuid.uuid4, editable=False)
name = models.CharField(max_length=255)
def __str__(self):
return self.name
class AudienceChoices(models.TextChoices):
BEGINNER = 'beginner', 'Beginer'
INTERMEDIATE = 'intermediate', 'Intermediate'
PRO = 'pro', 'Pro'
class Post(models.Model):
uuid = models.UUIDField(primary_key=True, default=uuid.uuid4, editable=False)
author = models.ForeignKey(
to=settings.AUTH_USER_MODEL,
on_delete=models.CASCADE,
related_name='posts',
)
category = models.ForeignKey(
to='Category',
on_delete=models.CASCADE,
related_name='posts',
)
tags = models.ManyToManyField(to='Tag', blank=True)
audience = models.CharField(
max_length=100,
choices=AudienceChoices.choices,
default=AudienceChoices.BEGINNER,
)
title = models.CharField(max_length=255)
def __str__(self):
return self.title
Expected behavior
Filter working as intended?
Screenshots
N/A
Environment (please complete the following information):
- OS: Ubuntu 22.04 (
Linux 5.15.0-130-generic #140-Ubuntu SMP Wed Dec 18 17:59:53 UTC 2024 x86_64
) - CPU: Intel(R) Core(TM) i3-8145U CPU @ 2.10GHz
- Python version: [e.g., 3.11] 3.11
- Django version: [e.g., 5.0.2] 5.1.5
- Django Admin List Filter package version: [e.g., 0.1.0]: 0.2.6
- Browser Vendor and version: [e.g., Firefox 126.0 (64-bit)] any browser
Additional context
This bug is trivial to fix: replace __id__exact
with __pk__exact
in the linked JS file (there are two occurrences, both have to be replaced). This is likely the only place to change. django
provides pk
attribute/field for all models that resolves to its primary key field (see e.g. here).
I'm ready to submit a PR with this change if you're interested and the project is still maintained. For now, I patch the bug in Dockerfile:
RUN sed -i -e 's/__id__exact/__pk__exact/g' /.venv/lib/python3.11/site-packages/dalf/static/admin/js/django_admin_list_filter.js