2010-02-12 3 views

답변

8

get_or_create (또는 생성)로 알맞은 대량 삽입을 수행 할 수 없습니다. 쉽게이 작업을 수행 할 수있는 API가 없습니다.

테이블이 원시 SQL을 사용하여 행을 만드는 것이 너무 간단하지 않으면 너무 어렵지 않습니다. 같은 :

% s이 (가) 당신이 자신을 만들고 제대로 탈출해야합니다 ("field1, field2"), ("field3, field4"), ("field5, field6") 같은 문자열이
INSERT INTO site_entry (field1, field2) 
(
     SELECT i.field1, i.field2 
     FROM (VALUES %s) AS i(field1, field2) 
     LEFT JOIN site_entry as existing 
       ON (existing.field1 = i.field1 AND existing.field2 = i.field2) 
     WHERE existing.id IS NULL 
) 

. 참조

+0

내가 한 것처럼 여러 쿼리를 한 번에 여러 행을 일괄 적으로 삽입 할 수 있습니다. –

+0

그래,하지만 MySQL로 할 수 없어 제안 된 쿼리로 올바른 SQL 문법을 찾을 수없는 것 같아 – kemar

+0

어떻게하면 될까? 모델 객체를 어떻게받을 것인가? 이 쿼리? –

4

목표에 달려 있습니다. manage.pyloaddata 함수를 사용하여 적절한 형식 (JSON, XML, YAML, ...)으로 데이터를로드 할 수 있습니다.

도 참조하십시오. this discussion.

+2

이것은 깨진 링크입니다. – wim

0

나는 그렇지 않다고 말하고 싶다.

그러나 field1field2을 속성으로 사용하는 경우 어떤 유형의 item이 맞는지 궁금합니다. 엔트리를 나타내는 다른 클래스가 있지만, models.Model에서 파생되지 않은 것처럼 보입니다. 어쩌면이 클래스를 생략하고 해당 항목을 만드는 대신 즉시 Entry 인스턴스를 만들 수 있습니다.

1

item_list의 내용이 DB에 이미 있는지, 모델 개체가 필요한지 확실하지 않은 경우 get_or_create을 꼭 사용해야합니다.

for item in item_list: 
    new = Entry.objects.create(
     field1 = item.field1, 
     field2 = item.field2, 
    ) 

을 그리고 당신은 개체를 필요로하지 않는 경우, 바로 함수 호출의 반환을 무시 :

당신이 항목이 DB에없는 알고 있다면, 당신은 더 나은 일을 할 것입니다. 그것은 DB 물건을 빠르게하지는 않겠지 만, 그것이 문제라면 메모리 관리에 도움이 될 것입니다.

데이터가 이미 DB에 있는지 여부가 확실하지 않지만 두 필드 중 하나에 unique=True 플래그가 있으면 DB가 고유성을 적용하므로 예외를 catch하고 계속 이동할 수 있습니다. 이렇게하면 기존 개체를 선택하지 않아도 DB가 추가로 손상되지 않습니다.

from django.db import IntegrityError 

for item in item_list: 
    try: 
     new = Entry.objects.create(
      field1 = item.field1, 
      field2 = item.field2, 
     ) 
    except IntegrityError: 
     continue 

트랜잭션을 수동으로 관리하여 속도를 향상시킬 수 있습니다. Django는 모든 저장을 위해 트랜잭션을 자동으로 생성하고 커밋하지만 특정 기능에서 많은 DB 저장을 수행한다는 것을 알게되면 효율성을 크게 높일 일부 데코레이터를 제공합니다. Django 문서는 내가 할 수있는 것보다 더 잘 설명 할 수 있지만, 특히주의를 기울 이길 원할 것입니다. django.db.transaction.commit_on_success

+1

내 item_list *에있는 항목이 이미 내 DB에있을 수 있습니다. 예, 모델 개체가 필요합니다. 그리고 어떤 필드도 고유 = True 제약 조건을 가지고 있지 않습니다 : '(그래서 나는 get_or_create가 갈 길이라고 생각합니다.) 데이터베이스를 치자! – kemar

+4

먼저 질문에 답하지 않습니다. get_or_create는 대량 삽입을하지 않기 때문에 get_or_create가 도움이되지 않습니다. 한 번에 하나씩 항목을 삽입하면 일괄 삽입에 잘못된 작업이 발생합니다. 마지막으로 오류를 일으키지 않고 무시할 수 없습니다. Postgresql에서 체크 포인트를 뛰어 넘지 않으면 "트랜잭션이 중단되었습니다"오류가 발생합니다. –

1

1.4 이후는 bulk_create에게

을 할 수 the docs

* (가장 중요한 하나는 pre_save 따라서 모델의 저장() 메서드가 호출되지 않습니다되고, 그리고 비록주의에주의를 기울 말고 post_save 신호는 전송되지 않습니다.) *

관련 문제