Conditional bulk update in Django using grouping Conditional bulk update in Django using grouping postgresql postgresql

Conditional bulk update in Django using grouping


To complement @Bernhard Vallant answer. You can use only 3 queries.

def create_invoices(invoice_date):    # Maybe use Exists clause here instead of subquery,     # do some tests for your case if the query is slow    clients_with_transactions = Client.objects.filter(        id__in=Transaction.objects.values('client')    )    invoices = [        Invoice(client=client, number=get_invoice_number(), date=invoice_date)        for client in clients_with_transactions    ]    # With PostgreSQL Django can populate id's here    invoices = Invoice.objects.bulk_create(invoices)    # And now use a conditional update    cases = [        When(client_id=invoice.client_id, then=Value(invoice.pk))        for invoice in invoices    ]    Transaction.objects.update(invoice_id=Case(*cases))


You could try constructing a conditional update query if you are able to generate a mapping from clients to invoices before:

from django.db.models import Case, Value, When# generate this after creating the invoicesclient_invoice_mapping = {    # client: invoice}cases = [When(client_id=client.pk, then=Value(invoice.pk))          for client, invoice in client_invoice_mapping.items()]Transaction.objects.update(invoice_id=Case(*cases))

Note that Conditional Queries are available since Django 1.8. Otherwise you may look into constructing something similar using raw SQL.