【问题标题】:Case sensitive search in Django, but ignored in MysqlDjango中区分大小写的搜索,但在Mysql中被忽略
【发布时间】:2015-03-20 08:51:47
【问题描述】:

我在 Django 模型中有一个字段用于存储唯一(哈希)值。事实证明,数据库(MySQL/inno)没有对这种类型(VARCHAR)进行区分大小写的搜索,即使我明确告诉 Django 进行区分大小写的搜索 Document.objects.get(hash__exact="abcd123")。所以“abcd123”和“ABcd123”都返回了,这是我不想要的。

class document(models.Model):
   filename    = models.CharField(max_length=120)
   hash        = models.CharField(max_length=33 )

我可以将“哈希字段”更改为 BinaryField ,因此在数据库中它变成了 LONGBLOB ,并且它会进行区分大小写的搜索(并且有效)。但是,这对我来说似乎不是很有效。 有没有更好的方法(在 Django 中)来做到这一点,比如添加“utf8 COLLATE”?或者在这种情况下正确的 Fieldtype 是什么? (是的,我知道我可以使用 PostgreSQL 代替......)

【问题讨论】:

    标签: mysql django collation


    【解决方案1】:

    MySQL 字符集的默认排序规则是 latin1_swedish_ci,不区分大小写。不知道为什么会这样。但是你应该像这样创建你的数据库:

    CREATE DATABASE database_name CHARACTER SET utf8;
    

    【讨论】:

    • 我现在已经更改了数据库,但我希望这可以在 Django 中完成。但这也有效。
    • 你真的应该一直使用 utf8。如果你不这样做,你一定会遇到问题。
    【解决方案2】:

    正如@dan-klasson 提到的,default non-binary string comparison is case insensetive by default;注意latin1_swedish_ci 末尾的_ci,它代表不区分大小写。 正如 Dan 所说,您可以使用区分大小写的排序规则和字符集来创建数据库。

    您可能也有兴趣知道您始终可以create a single table or even set only a single column to use a different collation(获得相同的结果)。您还可以在创建后更改这些排序规则,例如每个表:

    ALTER TABLE documents__document CONVERT TO CHARACTER SET utf8 COLLATE utf8_general_ci;
    

    此外,如果您不想更改数据库/表字符集/排序规则,Django 允许run a custom query using the raw method。因此,尽管我自己没有对此进行测试,但您也许可以通过使用以下内容来解决此更改:

    Document.objects.raw("SELECT * FROM documents__document LIKE '%s' COLLATE latin1_bin", ['abcd123'])
    

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 2011-04-13
      • 2013-09-26
      • 2013-10-09
      • 2020-05-28
      • 2017-02-25
      • 1970-01-01
      • 2013-02-17
      • 1970-01-01
      相关资源
      最近更新 更多