장고 모델 사용자 정의 save () 메소드에서 새 객체를 어떻게 식별해야합니까?
새 레코드를 저장할 때 (기존 레코드를 업데이트하지 않음) Django 모델 객체의 save () 메서드에서 특수 동작을 트리거하고 싶습니다.
자체 기록이 새롭고 업데이트되지 않도록하기 위해 (self.id! = None) 검사가 필요하고 충분합니까? 이것이 간과 될 수있는 특별한 경우?
self.pk is None:
객체가로 설정 UUIDField
되어 있지 않으면 새 Model 객체 내에서 True를 반환 합니다 primary_key
.
걱정해야 할 가장 중요한 경우는 ID 이외의 필드에 고유 제약 조건이 있는지 여부입니다 (예 : 다른 필드의 보조 고유 인덱스). 이 경우 여전히 새 레코드를 보유 할 수는 있지만 저장할 수는 없습니다.
모델을 self.pk
확인할 수있는 대체 방법self._state
self._state.adding is True
창조
self._state.adding is False
업데이트
이 페이지 에서 얻었습니다
검사 self.id
는 이것이 id
모델의 기본 키 라고 가정합니다 . 보다 일반적인 방법은 pk 단축키 를 사용하는 것 입니다.
is_new = self.pk is None
에 대한 검사 self.pk == None
입니다 하지 개체를 삽입하거나 데이터베이스에 업데이트 될 것입니다 있는지 확인하기에 충분.
Django O / RM에는 기본적으로 PK 위치에 무언가가 있는지 확인하고 UPDATE가있는 경우 INSERT를 수행하는 특히 불쾌한 해킹이 있습니다 (PK가 None 인 경우 INSERT에 최적화 됨).
이 작업을 수행해야하는 이유는 개체를 만들 때 PK를 설정할 수 있기 때문입니다. 기본 키의 시퀀스 열이있는 경우 일반적이지 않지만 다른 유형의 기본 키 필드에는 적용되지 않습니다.
정말로 알고 싶다면 O / RM의 기능을 수행하고 데이터베이스를 살펴 봐야합니다.
물론 코드에 특정 사례 self.pk == None
가 있으며 알아야 할 모든 것을 알려주는 가능성이 높지만 일반적인 해결책 은 아닙니다 .
"만들어진"크워 그를 보내는 post_save 신호에 연결할 수 있습니다. 참이면 개체가 삽입 된 것입니다.
http://docs.djangoproject.com/en/stable/ref/signals/#post-save
확인 self.id
하고 force_insert
플래그.
if not self.pk or kwargs.get('force_insert', False):
self.created = True
# call save method.
super(self.__class__, self).save(*args, **kwargs)
#Do all your post save actions in the if block.
if getattr(self, 'created', False):
# So something
# Do something else
새로 만든 객체 (자체)에 pk
가치 가 있기 때문에 편리 합니다.
이 대화에 매우 늦었지만 self.pk와 관련된 기본값이있을 때 채워지는 문제가 발생했습니다.
이 문제를 해결하는 방법은 모델에 date_created 필드를 추가하는 것입니다
date_created = models.DateTimeField(auto_now_add=True)
여기에서 당신은 갈 수 있습니다
created = self.date_created is None
대신 id 대신 pk 를 사용하십시오 .
if not self.pk:
do_something()
UUIDField
기본 키 를 가지고 있어도 작동하는 솔루션의 경우 (다른 사람이 무시한None
경우 가 아니라 save
) 장고의 post_save 신호에 연결할 수 있습니다 . 당신이 추가 models.py :
from django.db.models.signals import post_save
from django.dispatch import receiver
@receiver(post_save, sender=MyModel)
def mymodel_saved(sender, instance, created, **kwargs):
if created:
# do extra work on your instance, e.g.
# instance.generate_avatar()
# instance.send_email_notification()
pass
이 콜백은 save
메소드 를 차단 하므로 양식을 사용하든 AJAX 호출에 Django REST 프레임 워크를 사용하든 응답을 유선으로 다시 보내기 전에 트리거 알림과 같은 작업을 수행하거나 모델을 추가로 업데이트 할 수 있습니다. 물론, 사용자를 기다리지 않고 책임감있게 사용하고 무거운 작업을 작업 대기열로 오프로드하십시오. :)
그렇게하는 것이 일반적인 방법입니다.
ID는 db에 처음 저장되는 동안 주어집니다
Would this work for all the above scenarios?
if self.pk is not None and <ModelName>.objects.filter(pk=self.pk).exists():
...
To know whether you are updating or inserting the object (data), use self.instance.fieldname
in your form. Define a clean function in your form and check whether the current value entry is same as the previous, if not then you are updating it.
self.instance
and self.instance.fieldname
compare with the new value
'programing tip' 카테고리의 다른 글
이 확인란은 어떻게 작동하며 어떻게 사용합니까? (0) | 2020.06.12 |
---|---|
HTML : 선택적인 닫기 태그를 포함 또는 제외 하시겠습니까? (0) | 2020.06.12 |
Log4net이 로그 파일을 쓰지 않습니다 (0) | 2020.06.10 |
List <>에서 마지막 요소를 어떻게 찾을 수 있습니까? (0) | 2020.06.10 |
PS 명령의 전체 출력보기 (0) | 2020.06.10 |