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.