Почему некоторые записи не добавляются в таблицу m2m?

Почему некоторые записи не добавляются в таблицу m2m? Если таблица уже содержит запись с определенной темой и системой (сервис может быть любым), то при следующем добавлении записи с аналогичной темой и системой не происходит.

with transaction.atomic():
    chat_topic = ChatTopics.objects.get(ct_id=chat_topic_id)
    system = Systems.objects.get(sys_id=system_id)
    service = ServiceCatalog.objects.get(sc_id=service_id)

    chat_topic.ct_systems.add(system, through_defaults={"ctm_service": service})

Я не получаю никаких ошибок при запуске этого кода.

Ожидаемый результат: Ожидаемый результат

Фактический результат: Фактический результат

Модели:

class Systems(BaseModel):
    sys_id = models.AutoField(primary_key=True)
    sys_name = models.CharField(max_length=256, unique=True, null=False)

    def __str__(self):
        return self.sys_name

    class Meta:
        verbose_name = "Systems"
        verbose_name_plural = "Systems"
        ordering = ['sys_id']
class ServiceCatalog(BaseModel):
    sc_id = models.AutoField(primary_key=True)
    sc_service = models.CharField(max_length=250, unique=True, null=False)

    def __str__(self):
        return self.sc_service

    class Meta:
        verbose_name = "Service catalog"
        verbose_name_plural = "Service catalog"
        ordering = ['sc_id']
class ChatTopics(BaseModel):
    ct_id = models.AutoField(primary_key=True)
    ct_systems = models.ManyToManyField(Systems, blank=True, through="chattopics_m2m")
    ct_chat_id = models.CharField(max_length=20, null=False, blank=False)
    ct_chat_name = models.CharField(max_length=50, null=False, blank=False)
    ct_topic_id = models.CharField(max_length=10, null=True, default=None, blank=True)
    ct_topic_name = models.CharField(max_length=50, null=True, default=None, blank=True)
    
    def __str__(self):
        return f'{self.ct_chat_name} ({self.ct_topic_name})'
    
    class Meta:
        verbose_name = 'Topics'
        verbose_name_plural = 'Topics'
        
        constraints = [
            models.UniqueConstraint(fields=('ct_chat_id', 'ct_topic_id'), nulls_distinct=False, name='chattopics_ct_chat_id_ct_topic_id_unique')
        ]
class ChatTopics_m2m(BaseModel):
    ctm_id = models.AutoField(primary_key=True)
    ctm_chat_topic = models.ForeignKey(ChatTopics, on_delete=models.CASCADE, null=False)
    ctm_system = models.ForeignKey(Systems, on_delete=models.CASCADE, null=False)
    ctm_service = models.ForeignKey(ServiceCatalog, on_delete=models.CASCADE, null=True, blank=True)
    
    class Meta:
        ordering = ['ctm_system']

Это ожидаемое поведение .add():

Добавление во второй раз - это нормально, это не приведет к дублированию отношения:

>>> a2.publications.add(p3)

Что вы, вероятно, захотите сделать, чтобы также повысить эффективность, так это использовать:

with transaction.atomic():
    ChatTopics_m2m.objects.create(
        system_id=system_id,
        ctm_chat_topic_id=chat_topic_id,
        ctm_service_id=service
    )

и тогда атомарная транзакция, вероятно, может быть удалена, поскольку мы делаем это с помощью одного запроса.

Вернуться на верх