Django equivalent SQL REPLACE

Is there a Django ORM best practice for this SQL:

REPLACE app_model SET field_1 = 'some val', field_2 = 'some val';

Assumption: field_1 or field_2 will have a unique key for them (or in my case both), otherwise it will always be evaluated using INSERT.

Edit:

My best personal answer now is this, but these are 2-3 questions, where 1 should be possible:

    from django.core.exceptions import ValidationError
    try:
        Model(field_1='some val',field_2='some val').validate_unique()
        Model(field_1='some val',field_2='some val',extra_field='some val').save()
    except ValidationError:
        Model.objects.filter(field_1='some val',field_2='some val').update(extra_field='some val')
+5
source share
3 answers

You say you want REPLACEone that I suppose should remove any existing lines before inserting, but your example indicates that you want something more than UPSERT..

AFAIK, django does not support REPLACE(or sqlite INSERT OR REPLACE, or UPSERT). But your code can be consolidated:

obj, created = Model.objects.get_or_create(field_1='some val', field_2='some_val')
obj.extra_field = 'some_val'
obj.save()

, , , field_1, field_2, ( ).

(a SELECT get_or_create INSERT UPDATE save), , - UPSERT ( , ), , .

+11

Django 1.7 update_or_create:

obj, created = Person.objects.update_or_create(
    first_name='John', last_name='Lennon', defaults=updated_values)
+9

I think the following is more efficient.

(obj, created) = Model.objects.get_or_create(
   field_1 = 'some val',
   field_2 = 'some_val',
   defaults = {
      'extra_field': 'some_val'
   },
)
if not created and obj.extra_field != 'some_val':
   obj.extra_field = 'some_val'
   obj.save(
      update_fields = [
         'extra_field',
      ],
   )

This will update the additional field if the row has not been created and needs to be updated.

+4
source

All Articles