본문 바로가기
Programming/Database System

[DBMS] PK 선정 전략 - surrogate key와 natural key

by kghworks 2023. 1. 15.

목차

  • PK 선정 시 고려할 것 Surrogate key, Natural key
  • Surrogate key vs Natural key
  • 생각
  • 참고
How to Choose a Good Primary Key

 

 


PK 선정 시 고려할 것

데이터베이스 테이블 모델링 시 가장 먼저 하게 되는 작업이 해당 테이블의 Primary key를 선정하는 작업입니다. Pk가 가져야 하는 기본성질은 아래와 같습니다.

 

  • Uniqueness : 다른 ROW로부터 식별이 가능한 유일값
  • Stability (a situation in which something is not likely to move or change 캠브릿지 사전 참고) : 수정되면 안 됨
  • Irreducibility (비환원성) : 복합키를 사용한다면 그 키의 어느 컬럼이건 수정하는 순간 PK 유일성이 깨질 수 있음
  • Simplicity : 읽기 쉽고 기억이 쉽게 될 수 있는 데이터를 저장해야 하고, (이를테면 sequence number) 시스템과 호환성이 좋아야 함 (인코딩, 용량, 메모리 이슈 등)

 

위를 반영하면 크게 2가지 중 하나를 PK로 선정할 수 있습니다.

  • Surrogate key (대체키) : 시스템이 만들어내는 값 자체에는 의미 없는 데이터 (MySQL의 auto_increment 옵션, ORACLE의 Sequence object, uuid 등)
  • Natural key (business key, 자연키) : 유일한 성질을 가지고, 실제 의미를 가진 데이터 (주민번호, 품번, 부서코드 등)

 

PK를 설계하는 2가지 방법 (위 : 대체키, 아래 : 자연키)

 


Surrogate key vs Natural key

 

  Surrogate key (대체키) Natural key (자연키)
Uniqueness O (정책에 따라 다름)
Stability O △ (정책에 따라 다름)
Irreducibility O △ (정책에 따라 다름)
Simplicity O △ (정책에 따라 다름)
Familiarity (가시성) X O

 

 만일 자연키를 채택했다면, PK 값을 수정해야 하는 상황이 오면 참조 중인 다른 테이블에서도 값을 바꿔주어야 합니다. (PK의 값을 바꾼다는 건 절대 있으면 안 되는 일입니다만) 거기다 2개 이상의 복합키를 채택했다면, 참조하려는 테이블은 모두 복합키 컬럼 개수만큼 외래키를 생성해 나가야 합니다. 그럴수록 비즈니스 단의 sql은 복잡해지고, 디비 공간점유는 늘어납니다.

 대체키를 선택했다면, PK를 위한 컬럼을 하나 만들어야 합니다. 데이터는 의미가 없고, pk를 위해 존재하는 데이터로 pk를 위해 디비 공간을 점유합니다.

 

자연키의 좋은 점

  1. 데이터 가독성
  2. 자연키의 데이터가 유일성을 가짐을 db-side에서 강제
  3. 대체키를 안 만들어도 됨으로 PK를 위한 공간점유 없음

 1, 2번은 컬럼에 unique 제약조건을 줌으로써 해소할 수 있습니다. 3번의 경우 장점일 수 있지만, 자연키가 복합키라면 multi-column을 참조하는 외부 테이블들의 FK 공간도 무시할 수 없습니다.

 

 그래서 차라리 PK라는 목적 외에 아무 의미 없는 가장 단순한 데이터타입을 가지는 대체키를 채택하는 것이 대부분의 경우에 더 좋습니다. 제가 생각하는 좋은 대체키는 아래 조건을 만족합니다. (이건 제 생각입니다)

 

  • 아무 의미 없는 데이터
  • 단순
  • 불변
  • 그래서 난 sequence number가 좋다

 

PK의 데이터 타입과 사이즈

 자연키를 채택했다면, PK의 데이터 타입과 사이즈를 고려하지 않아도 됩니다. 비즈니스 정책에 의해 결정되기 때문입니다.

 그러나 대체키를 선택했다면 고민해봐야 합니다. 아래는 대체키에 많이 적용하는 타입들입니다.

  • Sequence Number (numeric, integer) : 가장 간단하고 많이 쓰이는 타입입니다. 보통 1~8 bytes를 차지하고 DBMS별로 자동으로 생성할 수 있도록 기능을 제공합니다.(auto_increment, Sequence Object)
  • UUID / GUID : 간단하게 생성할 수 있는 일정 사이즈의 난수입니다. 16 bytes를 필요로 합니다.
  • Alphanumeric (문자 + 숫자) : 가시성은 좋습니다. Entity의 고유 값을 식별할 수 있음과 동시에 의미도 어느 정도 내포할 수 있으므로 대체키가 가진 단점을 해소가 가능합니다. (ex. 부서코드 D001, 품목번호 P_L_01 등)

반대로 자주 쓰지 않는 타입은 Date, Datetime, Decimal과 같은 것들이 있습니다.

 

안 좋은 case

무엇을 선택하건 간에 안 좋은 케이스들도 존재합니다.

 

대체키의 안좋은 사례

  • 데이터 타입의 통일 : DB의 모든 PK들을 같은 데이터 타입으로 통일하려는 것입니다. (GUID 등을 이용) 부서 테이블과 같은 행의 개수가 상대적으로 적은 테이블의 경우 16 bytes GUID와 같은 길이의 PK는 공간 낭비입니다.
  • Over-sizing, Under-sizing : PK 데이터 사이즈에 보수적으로 접근하여 미리 과하게 잡거나 적게 잡는 것입니다

 

자연키의 안 좋은 사례 : 서비스 운용 중 중복되는 자연키 발생

 품목 테이블에 자연키로 품목코드를 두었다고 봅시다. (ex. 'BK_LG_001'데이터. Black color + Large size + 001 옷)

만일 이 회사가 다른 회사를 사들여 같은 옷 데이터가 테이블에 insert 되어야 한다면 참사는 시작됩니다. 'BK_LG_001_'라던지, '회사명_BK_LG_001'이라던지 와 같은 패턴으로 PK 값을 전면 수정해야 되는 것입니다. 최초에 자연키의 패턴을 신중히 설계해야 하는 이유입니다.

 

... (중략)

ID를 사용하는 장점으로 ID 자체는 아무런 의미가 없기 때문에 변경할 필요가 없다. 즉 식별정보를 변경해도 ID는 동일하게 유지할 수 있다. 하지만 의미를 가지는 경우라면 미래에 언젠가는 ID를 변경해야 할 수도 있다. 만약 정보가 중복돼 있으면 모든 중복 항목을 변경해야 한다. 이것은 쓰기 오버헤드와 불일치 (정보의 일부 중복은 갱신됐지만 다른 중복 항목이 갱신되지 않음) 위험이 있다. 이런 중복을 제거하는 일이 데이터 베이스의 정규화 이면에 놓인 핵심개념이다.

... (중략)

* [책] 데이터 중심 애플리케이션 설계  중 part 1 데이터 시스템의 기초 (34p)

 

자연 키보다는 대리 키를 권장한다
... (중략) 
될 수 있으면 대리 키의 사용을 권장한다. 
... (중략)
하지만 현실과 비즈니스 규칙은 생각보다 쉽게 변한다. 주민등록번호조차도 여러 가지 이유로 변경될 수 있다.

비즈니스 환경은 언젠가 변한다
... (중략)
기본 키의 조건을 현재는 물론이고 미래까지 충족하는 자연 키를 찾기는 쉽지 않다. 대리 키는 비즈니스와 무관한 임의의 값이므로 요구사항이 변경되어도 기본 키가 변경되는 일은 드물다. 대리 키를 기본 키로 사용하되 주민등록번호나 이메일처럼 자연 키의 후보가 되는 컬럼들은 필요에 따라 유니크 인덱스를 설정해서 사용하는 것을 권장한다.

JPA는 모든 엔티티에 일관된 방식으로 대리 키 사용을 권장한다

* [책] 자바 ORM 표준 JPA 프로그래밍 (저: 김영한) 중 4장 엔티티 매핑 (143p)

 


생각

 DB 설계에 대한 표준들을 다 가지고 있을 텐데요. 자연키, 대체키 등 각자 채택한 방식과 그 이유가 있을 겁니다. 저의 경우엔 대부분 대체키가 더 좋았습니다. 제가 경험한 자연키의 장점은 데이터 가독성 말고는 없었습니다. 자연키를 만드는 모듈이 별도로 필요한 경우도 있었습니다. (품목 코드 생성하는 함수 등) 대체키 컬럼이 공간을 점유하는 단점이 있다고 하지만, 단순불변의 숫자 대체키가 결론적으로 더 공간을 효율적으로 쓰는 것일 수도 있습니다.

 


참고

 

https://vertabelo.com/blog/primary-key/

 

How to Choose a Good Primary Key

Learn how to choose the best primary key for your SQL database tables. Get practical examples using the Vertabelo online data modeling platform.

vertabelo.com

 

https://vertabelo.com/blog/natural-and-surrogate-primary-keys/

 

Designing a Database: Should a Primary Key Be Natural or Surrogate?

Suppose we design a database. We've created some tables, each one has a few columns. Now we need to choose columns to be primary keys (PK) and make references between tables. And here some inexperienced designers face the dilemma – should a primary key b

vertabelo.com

https://www.vertabelo.com/blog/natural-key/

 

What Is a Business or Natural Key?

Learn what natural (business) keys are, when to use them, and how they compare to surrogate keys. Use them on Vertabelo’s web-based design tool.

vertabelo.com

https://hoing.io/archives/5248

 

MySQL - UUID 활용 - PK 로 사용

 

hoing.io

http://www.yes24.com/Product/Goods/59566585

 

데이터 중심 애플리케이션 설계 - YES24

데이터는 오늘날 시스템을 설계할 때 마주치는 많은 도전 과제 중에서도 가장 중심에 있다. 확장성, 일관성, 신뢰성, 효율성, 유지보수성과 같은 해결하기 어려운 문제를 파악해야 할 뿐 아니라

www.yes24.com

https://product.kyobobook.co.kr/detail/S000000935744

 

자바 ORM 표준 JPA 프로그래밍 | 김영한 - 교보문고

자바 ORM 표준 JPA 프로그래밍 | 자바 ORM 표준 JPA는 SQL 작성 없이 객체를 데이터베이스에 직접 저장할 수 있게 도와주고, 객체와 관계형 데이터베이스의 차이도 중간에서 해결해준다. 이 책은 JPA

product.kyobobook.co.kr

 

댓글