[입 개발] Redis AOF Rewrite 설정에 관하여…

오래간만에 Redis 관련 블로깅을 하네요.(요새는 실력 부족이라… 적을 내용이…) 먼저 실제 내용 자체는 지인의 질문에 대한 답변을 해드리다가, 정리할 필요가 있어서 이렇게 적습니다.(그렇습니다. 나중에 제가 까먹을까봐지요. 그 때 소스 다시 보기는 그러니…)

Redis에서 Persist 를 제공하는 방식은 RDB/AOF 두 가지가 있습니다. 뭐, 당연히 이쯤 되면 다들 기본적으로 이게 뭔지는 아실테니… 자세한 내용은 넘어가고요. 원래 AOF는 Redis 의 Comment Handler가 처리하는 명령들 중에 write관련 커맨드들만, 디스크에 Redis Protocol 그대로 저장하는 방식입니다.(현재 이에 대해 압축을 해볼까 하는 얘기들도 오고가고 있습니다만… 일단 이건 논외로…)

그런데 로그중에 다음과 같은 에러를 보셨다고 합니다.

"Asynchronous AOF fsync is taking too long (disk is busy?). Writing the AOF buffer without waiting for fsync to complete, this may slow down Redis."

사실 Redis는 스레드를 몇 개 사용하긴 합니다. 그 중에 하나가 fsync를 스레드에서 실행하는 거죠. appendfsync 가 everysec 일 때만, 백그라운드로 돕니다. fsync 자체에서 대기하게 되면, redis가 아무작업도 못하게 되니…

appendfsync everysec

하여튼 fsync가 큐에 들어갔는데, 아직 실행이 안끝났다. 디스크가 바쁘거나, 뭔가 이슈가 있을꺼라라는 뜻이죠. 실제로 디스크가 좀 이상한 느낌이라고…

삼천포로 빠졌는데, 다시 AOF rewrite 얘기로 넘어가면, 실제로 모든 write 성 작업이 저장되기 때문에 AOF 파일이 한없이 커질 수가 있습니다. 그래서 특정시점에, 해당 파일 사이즈가 얼마 이상이면, rdb 생성 처럼 fork 후에 현재 메모리 정보를 전부 AOF 형식으로 다시 쓰게 됩니다.(그럼 사이즈가 줄어들 가능성이 있겠죠?, 변경이나 삭제가 한번도 없었다면, 줄어들지 않을수도…)

그럼 당연한 의문이 생깁니다. 어느 정도 되어야 rewrite가 일어날까? 관련 옵션이 바로 아래 두가지 입니다.

auto-aof-rewrite-percentage 100
auto-aof-rewrite-min-size 64mb

일단 rewrite가 rdb 처럼 fork를 이용하므로 사용하지 않고 싶다면 위의 auto-aof-rewrite-percentage 값을 0으로 설정하면 됩니다. auto-aof-rewrite-min-size 는 일단 최소 이것보다는 사이즈가 커야 rewrite 하라는 뜻입니다.

내부적으로 코드를 살펴보면 다음과 같습니다.

         /* Trigger an AOF rewrite if needed */
         if (server.rdb_child_pid == -1 &&
             server.aof_child_pid == -1 &&
             server.aof_rewrite_perc &&
             server.aof_current_size > server.aof_rewrite_min_size)
         {
            long long base = server.aof_rewrite_base_size ?
                            server.aof_rewrite_base_size : 1;
            long long growth = (server.aof_current_size*100/base) - 100;
            if (growth >= server.aof_rewrite_perc) {
                serverLog(LL_NOTICE,"Starting automatic rewriting of AOF on %lld%% growth",growth);
                rewriteAppendOnlyFileBackground();
            }
         }

내부적으로 aof_current_size 와 aof_rewrite_base_size 를 사용하는데… AOF를 처음 만들면… 마지막으로 만들어졌던 AOF 파일의 크기가 aof_rewrite_base_size 가 되고 현재 AOF 파일의 크기가 aof_current_size 가 됩니다. 즉 auto-aof-rewrite-percentage 이 100이면, 이전에 만들어진 AOF가 1G 였다면, 2G가 되면(즉 100% 커지면) 하라는 뜻이 됩니다. 그리고 위의 조건 문에 의해서 0이면 실제로 AOF rewrite는 동작하지 않습니다.