서론

지금까지 별생각없이 insert statement를 써왔다. 되게 오래걸리는 작업, 크론에서 돌아가야할 애들인 경우에만 의식적으로 bulk insert를 썼다.('bulk' 라는 말 때문이었을까? 뭔가 대용량인 경우에만 써야할 것 처럼 느껴졌다.)

최근 내가 만든 부분에서 에러로그가 자주 올라오면서 우리 센터장이신 분이 나에게 찾아와 질문하시길... 

for문 돌면서 insert해요, 아니면 statement 만들어서 insert 해요?

나는 당당하게! for 돌면서 insert하고 있슴디다^-^ 문제 없습니다. 했는데 문제가 있다고 한다. '엔지니어'라는 직함을 달고있다면 어떤 원리인지 찾아보아야 했을텐데 잘 몰랐어서, 그리고 찾아볼 생각도 없었어서 ㅠ 이제라도 다시 찾아본다. 


본론

역시 가장 정확한 정보는 만든 사람들의 가이드가 아니겠는가. insert vs bulk insert와 같은 키워드로 googling을 해보니 쉽게 찾을 수 있는 링크! 내용 중 중요하다고 생각되어지는 부분들을 가지고와 번역해본다. 

https://dev.mysql.com/doc/refman/8.0/en/insert-optimization.html


Optimizing INSERT Statements 

insert 문을 최적화 하기

To optimize insert speed, combine many small operations into a single large operation. Ideally, you make a single connection, send the data for many new rows at once, and delay all index updates and consistency checking until the very end.

insert속도를 최적화하기 위해서는, 여러개의 작은 연산을 하나의 큰 연산으로 합쳐라. 이론상으로, 하나의 커넥션을 만들고, 한번에 다수의 행에대한 데이터를 보내고, 모든 index 업데이트,  consistency checking(무결성 체크?)를 끝날때까지 지연시킨다. 


The time required for inserting a row is determined by the following factors, where the numbers indicate approximate proportions:

한 행을 insert하는데 필요한 시간은 다음과 같은 요인들에 의해서 결정된다. 숫자는 대락적인 비율을 뜻한다. 

Connecting: (3)

Sending query to server: (2)

Parsing query: (2)

Inserting row: (1 × size of row)

Inserting indexes: (1 × number of indexes)

Closing: (1)

If you are inserting many rows from the same client at the same time, use INSERT statements with multiple VALUES lists to insert several rows at a time. 

만약 동일한 클라이언트에서 동시에 여러 행들을 insert하고 있다면, 한번에 여러 행을 insert하도록 insert문을 VALUES 리스트랑 같이 사용해라.

This is considerably faster (many times faster in some cases) than using separate single-row INSERT statements. 

이것은 분리된 한행의 insert문을 사용하는 것보다 상당히 빠르다. 



결론

사소한 것일지라도, 내가 만든 것이 어떻게 되어있는지 알고 넘어가야겠다는 생각이 들었다. 내가 만든 부분은 한 클라이언트에서 동시에 약 10번의 insert가 개인당 이뤄졌었다. 5000명이 들어왔다고 하면 50000번의 insert가 있었던 거였는데 이걸 2번의 insert로 줄일 수 있었다. 그러면 총 10000번의 insert로 오분의 일로 커넥션을 줄일 수 있었따. 히이익. 자주 몰리는 부분들에 대해 조금 더 고민해 볼 것. 그리고 트랜잭션 레벨에 대해서도 고민해볼 것. 고민할 것이 투성이다. 


'개발개발 > mySql' 카테고리의 다른 글

DB를 쿼리로 업데이트 할때  (0) 2018.09.16
mysql 월/주차 구하기  (1) 2018.01.06
left join 시 속도 문제  (0) 2016.12.20
SELECT 정렬하기 정리  (0) 2016.12.13
order by varchar to int  (0) 2016.11.24

+ Recent posts