这个SQL是否有Django ORM最佳实践:
REPLACE app_model SET field_1 = 'some val', field_2 = 'some val';
Run Code Online (Sandbox Code Playgroud)
假设:field_1或field_2在它们上面会有一个唯一的密钥(或者在我的情况下都是两个),否则这将始终评估为INSERT.
编辑:
我现在最好的个人答案就是这个,但这是2-3个查询,其中1应该是可能的:
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')
Run Code Online (Sandbox Code Playgroud)
ete*_*ode 11
你说你想要的REPLACE,我相信它应该在插入之前删除任何现有的行,但是你的例子表明你想要更像的东西UPSERT.
AFAIK,django不支持REPLACE(或sqlite INSERT OR REPLACE,或UPSERT).但是您的代码可以合并:
obj, created = Model.objects.get_or_create(field_1='some val', field_2='some_val')
obj.extra_field = 'some_val'
obj.save()
Run Code Online (Sandbox Code Playgroud)
这当然假设其中一个field_1,field_2或两个都是唯一的(如你所说).
它仍然是两个查询(SELECTfor get_or_create,and INSERT或UPDATEfor save),但是直到UPSERT类似的解决方案出现(并且它可能不会持续很长时间),它可能是你能做的最好的.
从Django 1.7开始你可以使用update_or_create方法:
obj, created = Person.objects.update_or_create(
first_name='John', last_name='Lennon', defaults=updated_values)
Run Code Online (Sandbox Code Playgroud)
我认为以下更有效.
(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',
],
)
Run Code Online (Sandbox Code Playgroud)
如果未创建行且需要更新,则仅更新extra_field.
| 归档时间: |
|
| 查看次数: |
6053 次 |
| 最近记录: |