#34505: Non-deterministic collations doesn't work with unique related fields on
PostgreSQL
-------------------------------------+-------------------------------------
               Reporter:  Petter     |          Owner:  nobody
  Friberg                            |
                   Type:  Bug        |         Status:  new
              Component:             |        Version:  4.2
  Migrations                         |       Keywords:  collation unique
               Severity:  Normal     |  related index
           Triage Stage:             |      Has patch:  0
  Unreviewed                         |
    Needs documentation:  0          |    Needs tests:  0
Patch needs improvement:  0          |  Easy pickings:  0
                  UI/UX:  0          |
-------------------------------------+-------------------------------------
 Creating a relation to a column with a non-deterministic collation raises:

 `django.db.utils.NotSupportedError: nondeterministic collations are not
 supported for operator class "varchar_pattern_ops"`

 Error is raised due to creation of a `_like` index.

 This is kind of a continuation of #33901, but instead regarding relations.

 Here's some code to reproduce:

 {{{
 #!python

 class Migration(migrations.Migration):

     initial = True

     dependencies = [
     ]

     operations = [
         CreateCollation(
             'ci',
             provider='icu',
             locale='und-u-ks-level2',
             deterministic=False
         ),
         migrations.CreateModel(
             name='User',
             fields=[
                 ('id', models.BigAutoField(auto_created=True,
 primary_key=True, serialize=False, verbose_name='ID')),
                 ('password', models.CharField(max_length=128,
 verbose_name='password')),
                 ('username', models.CharField(db_collation='ci',
 max_length=30, unique=True, verbose_name='username')),
             ],
             options={
                 'abstract': False,
             },
         ),
         migrations.CreateModel(
             name='ExtendedUser',
             fields=[
                 ('id', models.BigAutoField(auto_created=True,
 primary_key=True, serialize=False, verbose_name='ID')),
                 ('user',
 models.OneToOneField(on_delete=django.db.models.deletion.CASCADE,
 to=settings.AUTH_USER_MODEL, to_field='username')),
             ],
         ),
     ]
 }}}

 Adding a test case similar to what can be found in
 [changeset:"f3f9d03edf17ccfa17263c7efa0b1350d1ac9278" f3f9d03], but
 adjusted to include a `OneToOneField`, fails on main

 {{{
 #!python
     @isolate_apps("schema")
     @unittest.skipUnless(connection.vendor == "postgresql", "PostgreSQL
 specific")
     @skipUnlessDBFeature(
         "supports_collation_on_charfield",
         "supports_non_deterministic_collations",
     )
     def test_unique_relation_to_collation_charfield(self):
         ci_collation = "case_insensitive"

         def drop_collation():
             with connection.cursor() as cursor:
                 cursor.execute(f"DROP COLLATION IF EXISTS {ci_collation}")

         self.addCleanup(drop_collation)

         with connection.cursor() as cursor:
             cursor.execute(
                 f"CREATE COLLATION IF NOT EXISTS {ci_collation} (provider
 = icu, "
                 f"locale = 'und-u-ks-level2', deterministic = false)"
             )

         class CiCharModel(Model):
             field = CharField(max_length=16, db_collation=ci_collation,
 unique=True)

             class Meta:
                 app_label = "schema"

         class RelationModel(Model):
             field = OneToOneField(CiCharModel, on_delete=CASCADE,
 to_field="field")

             class Meta:
                 app_label = "schema"

         # Create the table.
         with connection.schema_editor() as editor:
             editor.create_model(CiCharModel)
             editor.create_model(RelationModel)

         self.isolated_local_models = [CiCharModel, RelationModel]
         self.assertEqual(
             self.get_column_collation(RelationModel._meta.db_table,
 "field_id"),
             ci_collation,
         )
         self.assertIn("field_id",
 self.get_uniques(RelationModel._meta.db_table))
 }}}

-- 
Ticket URL: <https://code.djangoproject.com/ticket/34505>
Django <https://code.djangoproject.com/>
The Web framework for perfectionists with deadlines.

-- 
You received this message because you are subscribed to the Google Groups 
"Django updates" group.
To unsubscribe from this group and stop receiving emails from it, send an email 
to [email protected].
To view this discussion on the web visit 
https://groups.google.com/d/msgid/django-updates/010701879ecd56de-a23e878e-2c6b-4960-b1f7-81ed2573cf39-000000%40eu-central-1.amazonses.com.

Reply via email to