5. 설정

이 장을 마치면: 어떤 설정이 어디에 있고, 무엇을 어떻게 바꾸며, 언제 반영되는지 안다.

5.1 설정 자리 지도

자리 내용 누가 쓰나
datafiles/pgdata/postgresql.conf 끝의 관리 블록 GritDB가 필요로 하는 PostgreSQL 설정 설치 스크립트(설치, 재설치, 업그레이드, 재초기화마다 다시 쓴다)
ALTER SYSTEM(postgresql.auto.conf) 운영자가 바꾸는 PostgreSQL 설정 운영자
~/gritdb1/config/grit_*.config(파일 4개) GritDB 엔진 설정 설치 스크립트(처음 한 번)와 운영자
gritsurfer_* 확장 설정 분석 세션 설정(6.6) 접속 옵션과 세션

5.2 관리 블록

postgresql.conf 끝에 설치 스크립트가 쓰는 블록이다. 재설치, 업그레이드, 재초기화 때마다 다시 쓴다.

# >>> gritdb managed begin
(필수 블록)
port = <포트>
(튜닝 블록 — --no-config 설치에서는 없음)
# <<< gritdb managed end

필수 블록은 바꾸지 않는다.

설정 값 반영
shared_preload_libraries 'gritsurfer' 재기동
wal_level logical 재기동
search_path '"$user", public, gritdb' reload

튜닝 블록은 사양에 따라 조정하는 대상이다.

설정 기본값 반영
wal_buffers 64MB 재기동
max_wal_size 64GB reload
min_wal_size 2GB reload
checkpoint_timeout 1h reload
bgwriter_lru_maxpages 1000 reload
shared_buffers 설치 때 계산(5.5) 재기동
effective_cache_size 설치 때 계산(5.5) reload
work_mem 설치 때 계산(5.5) reload
  • 설치 스크립트가 메모리 값 셋(shared_buffers, effective_cache_size, work_mem)을 서버 메모리로 계산해 튜닝 블록 끝에 쓴다. 이 값 셋 바로 앞 줄은 # memory-derived by install_gritdb.sh: …이다. 계산 방법은 5.5에 있다.

블록 밖이나 안에 직접 쓴 줄은 이렇게 된다. PostgreSQL은 같은 설정이 여러 줄이면 마지막 줄을 쓴다(설정 파일).

직접 쓴 자리 결과
블록 위 블록의 같은 설정이 이긴다
블록 아래 지금은 이기지만, 다음 설치 때 블록이 파일 끝으로 옮겨져 덮인다
블록 안 다음 설치 때 사라진다

그래서 postgresql.conf를 직접 고치지 않고 ALTER SYSTEM으로 바꾼다(5.3).

⚠ 표식 두 줄(# >>> gritdb managed begin과 # <<< gritdb managed end)을 지우거나 고치지 않는다

  • 이유: 설치 스크립트는 두 표식으로 블록을 찾는다. 표식이 깨지면 다음 설치나 업그레이드 때 postgresql.conf의 설정을 잃을 수 있다(QuickStart 6장 금지 4).
  • 대신: 설정은 ALTER SYSTEM으로 바꾼다(5.3).

5.3 설정 바꾸는 방법 · 우선순위

오래 쓸 설정은 ALTER SYSTEM으로 바꾼다. ALTER SYSTEM 값은 관리 블록보다 먼저 쓰이고, 재설치나 업그레이드 뒤에도 남는다.

ALTER SYSTEM SET <설정> = '<값>';
  • 반영은 5.4를 본다(재기동, reload).
  • 확인할 때는 SELECT pg_reload_conf();를 먼저 실행한다. 재기동 설정도 같다. 그다음 SELECT name, setting, source, pending_restart FROM pg_settings WHERE name = '<설정>';을 실행한다. reload 설정이면 setting이 새 값이다. 재기동 설정이면 setting은 옛 값이고 pending_restart가 t다. 이때는 5.4의 재기동 순서를 따른다.
  • 되돌리려면 ALTER SYSTEM RESET <설정>;을 실행한다. 반영은 5.4를 본다.

예외:

설정 바꾸는 법
port install_gritdb.sh --pgport로만 바꾼다(2.5)
필수 블록의 세 설정 바꾸지 않는다
restart_after_crash 설정할 수 없다. GritDB는 PostgreSQL 기본값 on과 달리 off로 고정한다(4.3). postgresql.conf에 쓰면 GritDB가 기동하지 않는다. ALTER SYSTEM은 오류를 낸다
gritsurfer_session_mode postgresql.conf나 ALTER SYSTEM으로 전역 설정하지 않는다(6.6)
  • 재초기화(3.1) 뒤에는 ALTER SYSTEM 값이 없으므로 옛 postgresql.auto.conf를 보고 다시 넣는다.

시간대를 바꿀 때는 서버 시간대와 로그 시간대를 함께 바꾼다.

ALTER SYSTEM SET timezone = '<시간대>';
ALTER SYSTEM SET log_timezone = '<시간대>';
SELECT pg_reload_conf();
  • <시간대>의 예는 Asia/Seoul이다. 설정 설명은 TimeZone과 log_timezone에 있다.
  • 새 세션에서 SHOW timezone;을 실행해 <시간대>가 나오는지 확인한다.
  • 분석 세션(GritDB 엔진)은 이 설정이 아니라 GritDB를 기동한 때의 OS 시간대로 날짜와 시각을 계산한다. 기동 셸에 TZ가 있으면 그 값으로 계산한다. 그러므로 timezone은 OS 시간대와 같은 값으로만 둔다.
  • 시간대를 바꾸려면 OS 시간대, timezone, log_timezone을 같은 값으로 바꾸고 재기동한다(5.4의 재기동 순서). OS 시간대는 OS 관리자가 timedatectl set-timezone <시간대>로 바꾼다. timedatectl의 Time zone과 SHOW timezone;이 같은지 확인한다.
  • 분석 세션 결과의 시간대는 1.8과 10.3을 본다.

5.4 반영 시점

설정마다 반영 시점이 다르다. pg_settings의 context로 판별한다.

SELECT name, setting, context, pending_restart FROM pg_settings WHERE name IN ('<설정>');
context 반영 할 일
postmaster 재기동 아래 “재기동 순서”(GritDB 전체)
sighup reload SELECT pg_reload_conf();
superuser와 user reload SELECT pg_reload_conf();를 실행하면 열린 세션과 새 세션에 모두 반영된다. 세션 안에서 SET한 값은 그 세션에서 그대로다. 한 세션만 바꾸려면 그 세션 안에서 SET한다
backend와 superuser-backend reload 뒤 새 접속 SELECT pg_reload_conf();를 실행하면 새 접속부터 반영된다. 열린 접속은 그대로다
internal 바꿀 수 없다 —
  • ALTER SYSTEM은 postgresql.auto.conf에 쓰기만 하므로 postmaster가 아닌 설정은 pg_reload_conf()를 해야 반영된다.
  • pending_restart가 t면 재기동해야 반영된다. 이 값은 reload를 한 뒤에만 t가 된다.
  • GritDB 프로세스에 HUP 신호를 보내지 않는다. 보내면 프로세스가 끝난다(4.3). reload는 SELECT pg_reload_conf();로만 한다.
  • postmaster 설정(max_connections, max_worker_processes 등)은 GritDB 전체를 재기동해 반영한다. PostgreSQL만 따로 재시작하지 않는다. GritDB가 기동 때 계산한 값이 낡은 채 남기 때문이다.
  • max_connections, max_worker_processes, autovacuum_max_workers, max_wal_senders를 바꾸거나 vCPU 수가 바뀌면(가상 서버 크기 변경) 재기동 뒤 5.6의 shm_limit_mb 경고를 본다. GritDB가 기동 때 읽은 값은 grep 'channel capacity inputs' ~/gritdb1/log/grit_admin_main.log | tail -1로 본다.

재기동 순서(설정 반영):

  1. 응용 프로그램, 풀러, 리포트, BI, CDC, ETL 도구를 멈추고 남은 세션을 끊는다(4.2 “남은 세션 끊기”).
  2. ~/gritdb1/bin/gritdb-stop을 실행하고 정지 완료 판정을 한다(4.2).
  3. 4.1에서 TMPDIR을 보고 ~/gritdb1/bin/gritdb-start를 실행한다. 그다음 pg_isready를 두 번 실행한다(4.1).
  4. 5.3의 확인 쿼리를 실행해 setting이 새 값이고 pending_restart가 f인지 확인한다.
  • 세션을 끊지 않으면 정상 정지(4.2)가 즉시 정지로 넘어간다. 열린 세션이 남아 있으면 약 30초 뒤, 실행 중인 문장이 있으면 최대 300초 뒤에 넘어간다. 그러면 core 파일(9.6)이 생길 수 있다. 다음 기동은 복구 경로(4.3)를 거친다. 즉시 정지로 넘어가면 log/grit_admin_main.log에 falling back to QuickStop 줄이 남는다.

재기동이 실패하면 기동 화면에 GritAdmin process exited …가 나온다(QuickStart GDB-BOOT-005). 이때는 아래를 따른다.

  1. 원인은 tail -20 ~/gritdb1/log/postgresql.log의 FATAL:이나 ASSERT FAILED: 줄과 중단 기록 log/GRIT_SURFER_ASSERT.log(9.1)에서 본다. 예를 들어 could not map anonymous shared memory는 shared_buffers가 크다는 뜻이다. ASSERT FAILED: GritSurfer: max_worker_processes=<값> exceeds …는 그 값이 256을 넘었다는 뜻이다(6.4.1의 5번).
  2. 정지 상태인지 본다(4.2의 정지 완료 판정).
  3. 서버가 내려가 있을 때만 ~/gritdb1/datafiles/pgdata/postgresql.auto.conf를 복사해 두고, 방금 바꾼 설정 줄을 지운다. 이 파일은 서버가 도는 동안 고치지 않는다(설정 파일). 엔진 설정이면 그 파일의 값을 5.6 표의 기본값으로 되돌린다.
  4. 다시 기동한 뒤(4.1) 5.3의 확인을 한다. 실패한 기동 다음 기동은 복구 과정(4.3)을 거친다. 이때 grit_admin_main.log에 DetectScenario: ABNORMAL_RESTART가 남는다.

5.5 사양별 권장값

설치 스크립트가 서버 메모리로 PostgreSQL 메모리 값 셋을 정해 튜닝 블록 끝에 쓴다(5.2). 재설치, 업그레이드, 재초기화 때마다 다시 계산한다.

값 계산
PostgreSQL 몫 물리 메모리 − GritDB 엔진 저장(절반) − GritDB 엔진 질의(4 GB와 15% 중 큰 값). 자세한 것은 1.3을 본다
shared_buffers PostgreSQL 몫의 25%(GB 단위로 내림)
effective_cache_size PostgreSQL 몫의 75%(GB 단위로 내림). 메모리를 잡지 않는다. 계획기가 캐시 크기로 어림하는 값이다
work_mem (PostgreSQL 몫 − shared_buffers) ÷ (접속 100 × 연산 3) ÷ 병렬 2. 이 값을 2의 거듭제곱으로 내린다(가장 작게 4MB)

아래는 메모리별 값의 예다. 실제 값은 설치 화면의 줄로 본다.

메모리 PostgreSQL 몫 shared_buffers effective_cache_size work_mem
16 GB 이하(free -m의 total 16384 미만) 4 GB 미만 PostgreSQL 기본값(128MB) 기본값(4GB) 기본값(4MB)
32 GB 약 11 GB 2GB 8GB 8MB
64 GB 약 22 GB 5GB 16GB 16MB
128 GB 약 44 GB 10GB 32GB 32MB
512 GB 약 176 GB 44GB 132GB 128MB
  • 설치 화면의 [INFO] PostgreSQL memory: … 줄로 확인한다(QuickStart 3.2). 관리 블록의 # memory-derived by install_gritdb.sh: … 줄로도 확인한다(5.2).
  • PostgreSQL 몫이 4 GB 미만이면 설치 스크립트는 값을 쓰지 않는다. 이때 설치 화면에 [WARN] PostgreSQL memory share is below 4GB …가 나오고, PostgreSQL은 기본값으로 돈다.
  • 계산은 접속 100(max_connections 기본값)을 전제로 한다. 그래서 max_connections를 올리면 work_mem을 같은 비율로 낮춘다. 낮출 때는 ALTER SYSTEM을 쓴다(5.3).
  • 값을 바꾸려면 ALTER SYSTEM으로 덮는다(5.3). 관리 블록 안을 고치면 다음 설치 때 다시 계산한 값으로 바뀐다(5.2).
  • 1.1에는 GritDB가 쓰는 vCPU와 메모리를 줄이는 설정이 없으므로 서버 크기를 정해 맞춘다(1.3).
  • 그 밖의 튜닝 블록 값은 디스크 여유 200 GB 이상을 전제로 한다(1.3). 예를 들어 max_wal_size는 64 GB다.

5.6 GritDB 엔진 설정

  • 파일은 ~/gritdb1/config/grit_{burst,plug,surfer,unify}.config다. 한 줄에 key = value로 쓴다(= 앞뒤 공백은 있어도 없어도 된다). #로 시작하는 줄은 주석이다. 줄 끝에 주석을 붙이지 않는다. key = 8 # 메모는 값이 8 # 메모가 되어 기동하지 않는다. 주석은 따로 한 줄로 쓴다.
  • 같은 키가 여러 줄이면 마지막 줄이 쓰인다. 그러므로 키를 고칠 때는 그 키의 마지막 줄을 고친다.
  • 바꾼 값은 재기동해야 반영된다(5.4의 재기동 순서).
  • 설치 스크립트는 이미 있는 설정 파일을 덮지 않는다. 업그레이드 때 새 키는 3.4와 3.5를 본다.

⚠ 설정 파일의 키를 지우지 않는다

  • 이유: 키가 하나라도 없으면 GritDB가 기동하지 않는다.
  • 대신: 값만 고친다. 기본값으로 되돌리려면 아래 표의 기본값을 쓴다.
설정 파일 기본값 범위 뜻
grit_surfer.catalog.read_threads grit_surfer.config 4 1~64 catalog 읽기 스레드 수(스레드마다 PostgreSQL 접속 1). 내부 접속 수는 이 값 + 2다(기본 6). 바꾸면 7.1의 정상 값도 바뀌고, 10.2의 일반 계정이 쓸 수 있는 접속 수도 바뀐다
grit_surfer.channel.shm_limit_mb grit_surfer.config 512 16~65536 세션 채널 공유 메모리 상한(MB). max_connections, max_worker_processes, autovacuum_max_workers, max_wal_senders를 올리거나 vCPU가 늘면 모자랄 수 있다. 아래 경고를 본다
grit_burst.session.connect_timeout_ms grit_burst.config 300000 1~3600000 분석 세션이 GritDB 엔진 연결을 기다리는 시간(ms). 넘으면 질의를 PostgreSQL로 실행한다. 바인드 실행, PREPARE, fallback=false에서는 오류가 난다(6.6)
  • read_threads나 shm_limit_mb가 범위 밖이면 GritDB가 기동하지 않는다. connect_timeout_ms가 범위 밖이면 기본값으로 동작한다.
  • 고친 뒤에는 재기동한다(5.4의 재기동 순서). 그다음 키마다 새 값이 쓰이는지 확인한다.
    • 세 키 모두 grep -F '[<키>] =' ~/gritdb1/log/grit_surfer_main.log | tail -1을 실행해 읽은 값이 [<키>] = <새 값>인지 확인한다. GritDB 엔진은 기동 때 설정 파일에서 읽은 값을 키마다 한 줄 남긴다. 다른 값이 나오면 고친 줄의 키 이름이 맞는지, 그 줄이 그 키의 마지막 줄인지 다시 본다.
    • read_threads는 grep 'read_threads=' ~/gritdb1/log/grit_catalog_processor.log | tail -1을 실행해 CatalogProcessor: starting (read_threads=<새 값>, …)이 나오는지 확인한다.
    • shm_limit_mb는 grep 'channel capacity inputs' ~/gritdb1/log/grit_admin_main.log | tail -1을 실행해 shm_limit=<새 값> MB가 나오는지 확인한다.
    • connect_timeout_ms는 위 첫 항목의 읽은 값을 확인하고, 재기동 뒤 log/postgresql.log에 아래 invalid 줄이 새로 없는지도 확인한다.
  • 기동하지 않을 때 로그(9.1)에 남는 줄은 다음과 같다. 키가 없으면 Config validation failed. Missing knobs in .config files: 아래에 - <키>가 남거나 <키> is missing in <파일>이 남는다. 값이 정수가 아니면 <키>='<값>' is not an integer가 남는다. 값이 범위 밖이면 <키>=<값> out of range [<최소>, <최대>]가 남는다.
  • connect_timeout_ms가 틀리면 기동은 되고 log/postgresql.log에 GritSurfer: grit_burst.session.connect_timeout_ms='<값>' invalid (range [1, 3600000]), using default 300000 ms가 남는다.
  • 기동 때 log/grit_admin_main.log에 grit_surfer.channel.shm_limit_mb=<값> is below the <필요> MB the derived channel plan needs 경고가 나오면 GritDB는 세션 채널을 줄여서 돈다. 큰 결과 전송이 느려질 수 있다. 이때는 값을 줄 끝 Set grit_surfer.channel.shm_limit_mb >= <필요>의 값 이상으로 올리고 재기동한다.
  • 로그 등급과 크기 키는 9.2를 본다.

문제가 생기면

  • 관리 블록에 문제가 있거나 기동이 실패하면 QuickStart 7장의 GDB-INSTALL 계열, GDB-BOOT 계열, TroubleShooting을 본다.

더 알아보기