Get count of rows actually inserted using bulk_create with ignore_conflicts

I’m trying to use bulk_create(..., ignore_conflicts=True) to insert records into a table. The ideal behavior for me would be to either:

  1. Only return instances that were actually inserted
  2. Or, just the number of instances actually inserted

The default behavior, at least in Postgres, is to return the count of records actually inserted. If there is a conflict, Postgres will not count that toward the count. Similarly, if using RETURNING "id" or similar, only the ids of records actually inserted will be returned.

Instead in Django, ALL objects are returned in a list, whether they were inserted or not.

Is there a way to mimic the Postgres behavior using the ORM?

FWIW this is the somewhat hacky but direct alternative using raw SQL I’ve come up with:

from django.utils import timezone
from django.db import connection
from psycopg2.extras import execute_values
# Other imports missing

now = timezone.now()
values = [(request.user.id, i.id, list_type, now, now) for i in ingredients]
query = """
INSERT INTO core_useringredient (user_id, ingredient_id, list_type, added, modified)
VALUES %s
ON CONFLICT DO NOTHING
RETURNING id
"""

with connection.cursor() as cursor:
    execute_values(cursor, query, values)
    inserted_ids = [row[0] for row in cursor.fetchall()]

So if we send in values to insert, but all conflict, inserted_ids is just an empty list.