내부 구조

Shared Memory
Shared Buffer
- 디스크 IO를 최소화 하는것
- 미리 디스크에서 읽어서 버퍼에 올려두고 수정작업 진행
- 이후 디스크 반영
WAL 버퍼
- 변경사항을 잠시 저장하는 버퍼
- 오라클의 redo log 와 같은 역할
- 백업 및 복구에 쓰인다.
Lock Space
Process
Postmaster Process
- Shared Memory 초기화
- 백그라운드 프로세스 구동작업
- 요청이 있을 때마다 백엔드 프로세스 생성

Background Process
- logger
- checkpointer : 체크포인트 발생시, dirty 버퍼를 파일에 기록
- writer : dirty 버퍼를 파일에 기록
- wal writer : WAL 버퍼 내용을 WAL파일에 기록
- autovacuum launcher : 오토배큠 실행
- archiver : archive log 모드일 때 wal 파일을 지정된 디렉토리에 복사
- stats collector : 세션 수행 정보와 테이블 사용 통계 정보와 같은 DBMS 사용통계 정보 수집
Backend Process
- max_connections 파라미터 만큼 생성
- 기본값은 100
- 쿼리 요청 수행 후 결과 전송
락
크게 Table Level Lock과 Row Level Lock으로 구분
- Table Level Lock
- access share
- row share
- row exclusive
- share update exclusive
- share
- share row exclusive
- exclusive
- access exclusive
- Row level locks
- for update
- for no key update
- for share
- for key share
Table Level Locks
테이블 범위로 적용되는 락이다. Row가 들어간 락이 있어서 헷갈릴 수 있지만 전부 테이블 수준 락이다.

X가 쳐져 있는 것은 충돌한다는 것이다. X가 쳐져 잇지 않은 것은 동시에 사용가능하다는 것이다.
특정 작업을 수행할 때 PG가 알아서 걸어주는 경우가 많다.
Access share
- 읽기만 하고 수정하지 않는 모든 쿼리에 적용
- Access Excl.와 충돌
Row Share
- SELECT FOR UPDATE, FOR KEY UPDATE, FOR SHARE, FOR KEY SHARE 문을 실행하면 얻는다.
- row 단위가 아니다.
- (Access) Exclusive 와 충돌이 생긴다.
Row Exclusive
- 테이블의 데이터를 수정하는 모든 명령에 의해 획득
Share Update Exclusive
- VACUUM (FULL 제외), ANALYZE, CREATE INDEX CONCURRENTLY, CREATE SATISTICS, COMMENT ON, REINDEX CONCURRENTLY
- 그리고 특정 ALTER INDEX 그리고 ALTER TABLE 등도 포함될 수 있습니다.
Share
- 여러 트랜젝션이 동시에 같은 데이터를 읽을 수 있도록 하고
- 데이터를 수정하려는 트랜잭션은 제한합니다.
- CREATE INDEX 에 의해서 획득됩니다.
- 즉 데이터 수정은 인덱스 생성까지 대기합니다.
Share For Exclusive
- CREATE TRIGGER 그리고 몇몇 ALTER TABLE 에 의해서 획득됩니다.
Exclusive
- REFRESH MATERIALIZED VIEW CONCURRENTLY 에 의해서 획득됩니다.
ACCESS EXCLUSIVE
- 가장 강력한 Table Level Lock
- 어떤 식으로든 테이블에 접근하는 유일한 트랜잭션임을 보장한다.
- DROP TABLE
- TRUNCATE
- REINDEX
- CLUSTER
- VACUMM FULL
- REFRESH MATERIALIZED VIEW
Row Level Locks
말그대로 하나의 레코드(튜플) 에 걸리는 락이다.
FOR UPDATE
- 다른 트랜잭션의 변경을 방지합니다.
- REPEATABLE READ나 SERIALIZABLE 격리 수준에서 변경된 행을 잠그려고 할 경우 오류를 발생한다. (MySql은 그냥 변경된 행을 리턴하고 잠금)
- UPDATE, DELETE, SELECT FOR UPDATE, SELECT FOR NO KEY UPDATE, SELECT FOR SHARE, SELECT FOR KEY SHARE 등을 방지한다.
FOR NO KEY UPDATE
- FOR UPDATE가 아닌 UPDATE 문에 자동 적용
- FOR UPDATE와 동일하지만, SELECT FOR KEY SHARE는 허용한다.
FOR SHARE
- exclusive lock이 아닌 shared lock을 획득
- share 류와 함께 공유 가능
FOR KEY SHARE
- FOR SHARE과 기능은 같으나, SELECT FOR NO KEY UPDATE를 허용
- 키 값이 아닌 컬럼 변경을 허용
Advisory Locks
MySql의 Named Lock과 동일
SELECT pg_advisory_lock(123);
SELECT pg_advisory_unlock(123);
인덱스
- B-tree
- Hash : 32비트 해시 코드 저장, 단순한 동등 연산
- GiST : R-Tree 동작 구현을 위해 사용됨
- GIN : 역 인덱스, 정렬 기능 없음
- SP-Gist : Spatial용, 인메모리 율
- BRIN(Block Range Indexes)
- 대량의 데이터를 가진 테이블에서 성능 향상을 위해 생김
- 블록 범위를 기반으로 한 인덱스
- 정렬된 데이터(시계열 등)에 적합
- 데이터를 블록 단위로 그룹화 하고, 최소값과 최대값 저장
- B-Tree의 1%밖에 사용 안함
- 별도로 관리되는 인덱스 사용하지 않음, 데이터 테이블과 함께 존재하며
- 블록 크기보다 큰 정렬된 데이터 범위를 조회하는 경우, 효과 제한됨
- 나의 예상으로는 MySql의 클러스터링 인덱스와 비슷한듯