#25287: Multiplying and dividing connectors for datetime expressions are not supported by sqlite backed. -------------------------------------+------------------------------------- Reporter: Ahmet DAL | Owner: nobody Type: New feature | Status: new Component: Database layer | Version: 3.0 (models, ORM) | Severity: Normal | Resolution: Keywords: sqlite3, | Triage Stage: Accepted combine_duration_expression, F | expressions, | Has patch: 0 | Needs documentation: 0 Needs tests: 0 | Patch needs improvement: 0 Easy pickings: 0 | UI/UX: 0 -------------------------------------+------------------------------------- Changes (by Baptiste Mispelon):
* version: 1.8 => 3.0 Comment: I was able to reproduce the reported error on the latest master (a5855c8f0fe17b7e888bd8137874ef78012a7294) by using the following models: {{{ #!python from django.db import models class Ticket(models.Model): date_opened = models.DateTimeField() class Rule(models.Model): duration = models.DurationField() class Action(models.Model): percent = models.FloatField() rule = models.ForeignKey('Rule', on_delete=models.CASCADE) class Expire(models.Model): ticket = models.ForeignKey('Ticket', on_delete=models.CASCADE) action = models.ForeignKey('Action', on_delete=models.CASCADE) }}} And the following testcase: {{{ #!python from datetime import timedelta from django.db.models import F from django.test import TestCase from django.utils import timezone from .models import Ticket, Rule, Action, Expire class TicketTestCase(TestCase): def test_ticket(self): now = timezone.now() ticket1 = Ticket.objects.create(date_opened=now-timedelta(days=6)) ticket2 = Ticket.objects.create(date_opened=now-timedelta(days=4)) rule = Rule.objects.create(duration=timedelta(days=10)) action = Action.objects.create(rule=rule, percent=50) expire = Expire.objects.create(ticket=ticket1, action=action) expire = Expire.objects.create(ticket=ticket2, action=action) qs = Expire.objects.filter(ticket__date_opened__lte=(timezone.now() - F("action__percent") * F("action__rule__duration") / 100)) self.assertQuerysetEqual(qs, [ticket1.pk], transform=lambda x: x.ticket.pk) }}} As described in the original ticket, the testcase fails with sqlite (`DatabaseError: Invalid connector for timedelta: *.`) but passes when using postgresql. The proposed solution of adding the new `*` and `/` operators to `sqlite3.DatebaseOperations.combine_duration_expression()` [1] only works in that the `DatebaseError` disappears but the test still fails because the returned queryset is empty. Josh's suggestions of wrapping everything in an `ExpressionWrapper` don't seem to make a difference either. [1] https://github.com/django/django/blob/a5855c8f0fe17b7e888bd8137874ef78012a7294/django/db/backends/sqlite3/operations.py#L315 -- Ticket URL: <https://code.djangoproject.com/ticket/25287#comment:7> 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 django-updates+unsubscr...@googlegroups.com. To view this discussion on the web visit https://groups.google.com/d/msgid/django-updates/066.08c1cf15111d06ccbbfcc9b6b9d09e1f%40djangoproject.com.