2

I have a Model of an object and few tags are assigned to the object of this model. Tags may be uppercased, lowercased or mix of both cases. I want to write a queryset which will return those object which has same tags which I provided. Note: I am using django-taggit module.
Views.py

def home(request):
    book = Book.objects.filter(tags__name__in= map(lambda s:s.lower(), ['harry-potter', 'Champak', 'Physics']))
    print(book)
    return HttpResponse("Books Retrieved")

Models.py

from django.db import models
from django.utils.translation import ugettext_lazy as _

from taggit.managers import TaggableManager
from taggit.models import GenericUUIDTaggedItemBase, TaggedItemBase

class UUIDTaggedItem(GenericUUIDTaggedItemBase, TaggedItemBase):
    class Meta:
        verbose_name = _("Tag")
        verbose_name_plural = _("Tags")

class Book(models.Model):
    name = models.CharField(max_length=100)
    details = models.TextField(blank=True)
    tags = TaggableManager(through=UUIDTaggedItem, blank = True)

Now I want to return all the books which have tags mentioned as 'HArry-Potter', 'HARRY-POTTER', or any other word.

PS: If anyhow we can lower the 'tags__name__in' List, our work will be done.

Vishal Pandey
  • 55
  • 1
  • 7
  • Does this answer your question? [Is there any way to do a case-insensitive IN query in Django?](https://stackoverflow.com/questions/2360800/is-there-any-way-to-do-a-case-insensitive-in-query-in-django) – benzkji Aug 25 '21 at 09:42

2 Answers2

3

You can make a Q object where you filter case insensitive with:

from django.db.models import Q

data = ['harry-potter', 'Champak', 'Physics']

qfilter = Q(
    *[Q(tags__name__iexact=item) for item in data],
    _connector=Q.OR
)

Book.objects.filter(
    qfilter
)

The __iexact [Django-doc] will match case insensitively with each item in data.

Willem Van Onsem
  • 443,496
  • 30
  • 428
  • 555
0

After googling and studying documentation, I came with this answer which does my work

tag_re = '(' + 'pipe|seperated|list|of|tags' + ')'
Book.filter(tags__name__iregex=rf'{tag_re}').distinct()
Vishal Pandey
  • 55
  • 1
  • 7