很久以前用 Django 做的一个外包项目,我用了 PostgreSQL 的 ArrayField 套 CharField,非常方便的实现了基于 Tag 的搜索。最近客户反应了一个小问题,问能不能让搜索 Tag 时可以不区分大小写,我简单的研究了一下,发现是可行的。

首先,这个 Field 是这样定义的:

tags = ArrayField(models.CharField(max_length=32), blank=True, null=True, verbose_name="标签")

然后,搜索时是这样调用的:

queryset.filter(tags__contains=[query])

问题来了,用这种方式,不仅没办法实现不区分大小写的搜索,甚至 Tag 必须得全匹配,少输一个字母都不行。所以,要如何实现搜索时不区分大小写?很简单,在搜索时改成这样的代码即可:

queryset.filter(tags__icontains=query)

为什么不需要通过 Array contain 的方式就可以达到目的?这是因为在这种情况下,Django + PostgreSQL 会自动把 ArrayField 转化成字符串,然后在这个字符串中去匹配,自然能做到不区分大小写,甚至只是部分匹配了。

扩展阅读