programing

Oracle을 사용한 Django ORM의 성능 저하

codeshow 2023. 10. 9. 23:41
반응형

Oracle을 사용한 Django ORM의 성능 저하

저는 오라클 백엔드로 장고 웹사이트를 만들고 있는데, 기본 키에서 간단한 검색을 해도 성능이 매우 느립니다.MySQL에 동일한 데이터가 로드되면 동일한 코드가 매우 빠르게 작동합니다.

실적이 부진한 이유는 무엇일까요?문제가 Oracle bind parameter의 사용과 관련된 것이 아닌가 하는 의심이 들지만, 그렇지 않을 수도 있습니다.

장고 모형(~6,200,000 행의 검정표

from django.db import models

class Mytable(models.Model):
    upi = models.CharField(primary_key=True, max_length=13)

    class Meta:
        db_table = 'mytable'

장고 ORM (1초 소요)

from myapp.models import *
r = Mytable.objects.get(upi='xxxxxxxxxxxxx')

바인딩 매개 변수를 사용한 원시 쿼리(1초 소요)

cursor.execute("SELECT * FROM mytable WHERE upi = %s", ['xxxxxxxxxxxxx'])
row = cursor.fetchone()
print row

바인딩 매개 변수가 없는 원시 쿼리(순간)

cursor.execute("SELECT * FROM mytable WHERE upi = 'xxxxxxxxxxxxx'")
row = cursor.fetchone()
print row

나의환경

  • 파이썬 2.6.6
  • 장고 1.5.4
  • cx-오라클 5.1.2
  • 오라클 11g

Oracle 데이터베이스에 연결할 때 다음을 지정합니다.

'OPTIONS': {
    'threaded': True,
}

어떤 도움이라도 주시면 대단히 감사하겠습니다.

[업데이트] 나는 다음을 사용하여 몇 가지 테스트를 했습니다.debugsqlshell장고 디버그 도구 모음의 도구입니다.

# takes ~1s
>>>Mytable.objects.get(upi='xxxxxxxxxxxxx')
SELECT "Mytable"."UPI"
FROM "Mytable"
WHERE "Mytable"."UPI" = :arg0  [2.70ms]

이는 Django가 Oracle bind parameter를 사용하고 쿼리 자체가 매우 빠르지만 해당 Python 개체를 생성하는 데 시간이 매우 오래 걸린다는 것을 의미합니다.

확인을 위해 cx_Oracle을 사용하여 동일한 쿼리를 실행했습니다.cursor제 원래 질문은 장고 커서입니다.

import cx_Oracle
db= cx_Oracle.connect('connection_string')
cursor = db.cursor()

# instantaneous
cursor.execute('SELECT * from mytable where upi = :upi', {'upi':'xxxxxxxxxxxxx'})
cursor.fetchall()

장고 ORM의 속도를 늦추는 것은 무엇일까요?

[업데이트 2] 오라클 쪽에서 데이터베이스 성능을 살펴봤는데, 질의가 장고에서 올 때 인덱스를 사용하지 않는 것으로 나타났습니다.왜 이런 일이 벌어질지 짐작이 가십니까?

를 사용하면 성능 문제가 해결됩니다.

cursor.execute("SELECT * FROM mytable WHERE upi = TO_CHAR(%s)", ['xxxxxxxxxxxxx'])

DBA들과 함께 일을 해본 결과, 어떤 이유에서인지 장고get(upi='xxxxxxxxxxxx')쿼리가 데이터베이스 인덱스를 사용하지 않았습니다.

다음을 사용하여 동일한 쿼리를 다시 작성한 경우filter(upi='xxxxxxxxxxxx')[:1].get(), 질문이 빨랐습니다.

get쿼리는 정수 기본 키로만 빠릅니다(원래 질문에서 문자열이었습니다).

최종 솔루션

create index index_name on Mytable(SYS_OP_C2C(upi));

cx_Oracle과 Oracle에서 사용하는 문자 집합이 일치하지 않는 것 같습니다.C2C 인덱스를 추가하면 문제가 해결됩니다.

업데이트: 또한 Oracle의 VARCHAR2에서 NVARCHAR2로 전환하면 동일한 효과가 있으며 기능 인덱스 대신 사용할 수 있습니다.

다음은 에게 도움이 된 몇 가지 유용한 토론 스레드입니다. http://comments.gmane.org/gmane.comp.python.db.cx-oracle/2940 http://comments.gmane.org/gmane.comp.python.db.cx-oracle/3049

언급URL : https://stackoverflow.com/questions/18978536/poor-performance-of-django-orm-with-oracle

반응형