메타데이터 관리 시스템 설계 — 저장소 데이터 모델

핵심 엔티티, 이력 관리, 갭 분석을 위한 저장소 스키마 설계

메타데이터 저장소의 데이터 모델 설계 원칙과 핵심 엔티티 구조를 다룬다. 기술/비즈니스 메타데이터 분리, 표준 관리, 공통 코드, 중요데이터, 이력 테이블, 갭 분석 결과 저장까지 전체 스키마를 설계한다.

Data Governance
저자

Kwangmin Kim

공개

2026년 03월 26일

1 저장소 데이터 모델 설계 원칙

메타데이터 저장소의 데이터 모델은 일반 업무 시스템 DB 설계와 다른 특수한 요구사항을 갖는다.

이력 보존 필수 스키마 변경, 표준 변경, 품질 진단 결과는 모두 시점 이력을 보존해야 한다. 단순히 현재 상태만 저장하면 “이 칼럼이 언제 추가되었는가”, “표준이 왜 바뀌었는가”를 추적할 수 없다.

다중 환경 지원 동일 테이블이 개발/스테이징/운영 환경에 각각 다른 버전으로 존재할 수 있다. 환경 구분자(env_type)를 스키마 메타데이터의 핵심 키로 설계해야 한다.

다중 DBMS 추상화 Oracle의 NUMBER, MySQL의 INT, PostgreSQL의 INTEGER는 개념적으로 동일하지만 물리적 표현이 다르다. 저장소에서는 표준화된 데이터 타입으로 정규화할지, 원본 타입을 그대로 보존할지 결정해야 한다. 권장하는 방식은 원본 타입을 그대로 보존하고, 표준 타입 매핑 테이블을 별도로 관리하는 것이다.

원칙 이유 미적용 시 문제
이력 보존 변경 추적, 감사 대응 “언제 바뀌었는가” 추적 불가
다중 환경 dev/staging/prod 갭 분석 환경 간 불일치 감지 불가
DBMS 추상화 이기종 DBMS 통합 관리 DBMS별 별도 저장소 필요

2 핵심 엔티티 설계

2.1 환경 및 연결 정보

TB_CONNECTION (DBMS 연결 정보)
├── conn_id          VARCHAR PK      연결 ID
├── conn_name        VARCHAR         연결 이름 (예: "운영_Oracle")
├── dbms_type        VARCHAR         DBMS 종류 (ORACLE/MYSQL/POSTGRESQL/MSSQL/DB2/TIBERO/SYBASE/MARIADB)
├── env_type         VARCHAR         환경 구분 (DEV/STAGING/PROD/DW/BCV)
├── host             VARCHAR         호스트 주소
├── port             INTEGER         포트번호
├── database_name    VARCHAR         데이터베이스/서비스명
├── schema_name      VARCHAR         기본 스키마명
├── use_yn           CHAR(1)         사용 여부
└── collect_cycle    INTEGER         수집 주기(분)
힌트

env_type은 단순 텍스트가 아니라 코드 테이블로 관리한다. 이후 갭 분석에서 “어떤 환경 쌍을 비교할 것인가”를 쿼리할 때 이 값을 기준으로 조인하기 때문이다.


2.2 스키마 메타데이터 (기술 메타데이터의 핵심)

TB_META_TABLE (테이블 메타데이터)
├── table_id         BIGINT PK       테이블 ID (surrogate key)
├── conn_id          VARCHAR FK      연결 ID (TB_CONNECTION 참조)
├── owner            VARCHAR         스키마 오너 (예: dbo, public)
├── table_name       VARCHAR         물리 테이블명
├── table_comment    VARCHAR         DBMS에 등록된 코멘트
├── table_type       VARCHAR         TABLE/VIEW/MATERIALIZED_VIEW
├── row_count        BIGINT          행 수 (수집 시점 기준)
├── data_size_mb     DECIMAL         데이터 크기(MB)
├── collect_dt       DATETIME        수집 일시
├── create_dt        DATETIME        테이블 생성 일시 (DBMS에서 수집)
├── is_deleted       CHAR(1)         삭제 여부 (실제 DBMS에서 사라진 경우)
└── delete_dt        DATETIME        삭제 감지 일시
TB_META_COLUMN (칼럼 메타데이터)
├── column_id        BIGINT PK       칼럼 ID
├── table_id         BIGINT FK       테이블 ID
├── column_name      VARCHAR         물리 칼럼명
├── column_order     INTEGER         칼럼 순서
├── data_type        VARCHAR         DBMS 원본 데이터 타입 (예: VARCHAR2, INT)
├── data_length      INTEGER         길이
├── data_precision   INTEGER         전체 자릿수 (NUMBER 타입 등)
├── data_scale       INTEGER         소수점 자릿수
├── nullable_yn      CHAR(1)         NULL 허용 여부
├── default_value    VARCHAR         기본값
├── column_comment   VARCHAR         DBMS에 등록된 코멘트
├── collect_dt       DATETIME        수집 일시
├── is_deleted       CHAR(1)         삭제 여부
└── delete_dt        DATETIME        삭제 감지 일시
TB_META_INDEX (인덱스 메타데이터)
├── index_id         BIGINT PK
├── table_id         BIGINT FK
├── index_name       VARCHAR
├── index_type       VARCHAR         UNIQUE/NORMAL/BITMAP/HASH
├── is_pk            CHAR(1)         PK 구성 인덱스 여부
├── collect_dt       DATETIME
└── [TB_META_INDEX_COLUMN] (인덱스 구성 칼럼)
    ├── index_id     BIGINT FK
    ├── column_id    BIGINT FK
    └── column_order INTEGER
힌트

is_deleted 플래그를 두는 이유는 실제 DBMS에서 테이블이 삭제되더라도 메타데이터 저장소에서 물리 삭제하지 않고 논리 삭제로 처리하기 위해서다. 이렇게 해야 품질 진단 이력, 변경 이력, 비즈니스 메타데이터가 고아 레코드가 되지 않는다.


2.3 비즈니스 메타데이터

기술 메타데이터(TB_META_TABLE, TB_META_COLUMN)는 DBMS에서 자동 수집하지만, 비즈니스 메타데이터는 사람이 직접 입력한다. 이 두 개를 별도 테이블로 분리하는 것이 핵심 설계 결정이다.

TB_BIZ_TABLE (테이블 비즈니스 메타데이터)
├── table_id         BIGINT FK       TB_META_TABLE 참조 (1:1)
├── logical_name     VARCHAR         논리 테이블명 (한글)
├── biz_definition   TEXT            업무 정의
├── data_subject     VARCHAR         데이터 주제 영역
├── owner_dept       VARCHAR         데이터 오너 부서
├── owner_person     VARCHAR         데이터 오너 담당자
├── data_lifecycle   VARCHAR         데이터 보존 주기 (예: 5년)
├── source_system    VARCHAR         데이터 발생 원천 시스템
├── update_cycle     VARCHAR         데이터 갱신 주기 (실시간/일배치/월배치)
├── input_person     VARCHAR         입력자
├── input_dt         DATETIME        입력 일시
├── update_person    VARCHAR         최종 수정자
└── update_dt        DATETIME        최종 수정 일시
TB_BIZ_COLUMN (칼럼 비즈니스 메타데이터)
├── column_id        BIGINT FK       TB_META_COLUMN 참조 (1:1)
├── logical_name     VARCHAR         논리 칼럼명 (한글)
├── biz_definition   TEXT            업무 정의
├── domain_id        BIGINT FK       도메인 참조 (TB_STANDARD_DOMAIN)
├── std_term_id      BIGINT FK       표준 용어 참조
├── sensitive_grade  VARCHAR         중요데이터 등급 (1~5 또는 NULL)
├── is_personal_info CHAR(1)         개인정보 여부
├── sample_value     VARCHAR         샘플 값 (예시)
├── input_person     VARCHAR
└── input_dt         DATETIME
힌트

domain_idstd_term_id는 표준 관리 모듈과의 연결 고리다. 칼럼에 도메인이 매핑되면, 해당 도메인의 규칙을 이용해 자동으로 품질 진단을 실행할 수 있다. 이 외래키가 없으면 표준과 품질이 분리된 고립된 시스템이 된다.


2.4 데이터 표준 (Standard)

TB_STANDARD_TERM (표준 용어)
├── term_id          BIGINT PK
├── std_id           BIGINT FK       소속 표준 세트 (TB_STANDARD_SET)
├── term_name        VARCHAR         표준 용어명 (영문)
├── term_name_ko     VARCHAR         표준 용어명 (한글)
├── abbreviation     VARCHAR         약어 (칼럼명 생성 규칙에 사용)
├── definition       TEXT            정의
├── status           VARCHAR         ACTIVE/DEPRECATED
├── create_dt        DATETIME
└── update_dt        DATETIME

TB_STANDARD_WORD (표준 단어)
├── word_id          BIGINT PK
├── std_id           BIGINT FK
├── word_name        VARCHAR         단어 (예: CUSTOMER)
├── word_name_ko     VARCHAR         한글 단어 (예: 고객)
├── abbreviation     VARCHAR         약어 (예: CUST)
├── domain_id        BIGINT FK       기본 도메인 (이 단어로 끝나는 칼럼의 도메인 추론에 사용)
└── status           VARCHAR

TB_STANDARD_DOMAIN (도메인)
├── domain_id        BIGINT PK
├── std_id           BIGINT FK
├── domain_group_id  BIGINT FK       도메인 그룹 참조
├── domain_name      VARCHAR         도메인명 (예: 금액, 날짜, 코드값)
├── data_type        VARCHAR         허용 데이터 타입
├── data_length      INTEGER         허용 최대 길이
├── rule_type        VARCHAR         RANGE/REGEX/CODE/CUSTOM
├── rule_value       TEXT            규칙 표현식 또는 코드 도메인 ID
├── description      TEXT
└── status           VARCHAR

TB_STANDARD_SET (표준 세트 - 복수 표준 관리)
├── std_id           BIGINT PK
├── std_name         VARCHAR         표준명 (예: "전사 표준", "패키지 표준")
├── std_type         VARCHAR         PUBLIC/LOCAL/NON_STANDARD
├── description      TEXT
└── is_default       CHAR(1)         기본 표준 여부
힌트

TB_STANDARD_SET을 두는 이유는 하나의 조직에서 전사 표준(Public), 레거시/패키지 시스템의 로컬 표준(Local), 표준 미적용 시스템(Non-Standard)이 공존하기 때문이다. 모든 것을 하나의 표준으로 강제하면 패키지 솔루션이나 인수합병 시스템을 메타데이터 시스템에 등록할 수 없게 된다.


2.5 공통 코드 (Master Code)

TB_CODE_GROUP (코드 그룹)
├── code_group_id    VARCHAR PK      예: "GENDER", "ORDER_STATUS"
├── code_group_name  VARCHAR         코드 그룹명
├── table_id         BIGINT FK       실제 저장 테이블 (TB_META_TABLE)
├── key_column_id    BIGINT FK       코드 키 칼럼
├── value_column_id  BIGINT FK       코드 값 칼럼
├── description      TEXT
├── domain_id        BIGINT FK       연결 도메인 (품질 진단에 사용)
└── status           VARCHAR

TB_CODE_VALUE (코드 값)
├── code_value_id    BIGINT PK
├── code_group_id    VARCHAR FK
├── env_type         VARCHAR         환경 구분
├── code_key         VARCHAR         코드 키 (예: "M")
├── code_value       VARCHAR         코드 값 (예: "남성")
├── sort_order       INTEGER         정렬 순서
├── effective_from   DATE            유효 시작일
├── effective_to     DATE            유효 종료일
└── status           VARCHAR         ACTIVE/INACTIVE
힌트

TB_CODE_VALUEenv_type을 두는 이유는 개발과 운영 환경의 코드 값이 다를 수 있기 때문이다. 개발에서 코드를 추가한 후 운영에 배포하기 전까지 두 환경의 코드 셋이 다른 상태가 된다. 이 갭을 코드 갭 분석 기능에서 탐지해야 한다.


2.6 중요데이터 관리

TB_SENSITIVE_GRADE_STD (등급 기준 정의)
├── grade            VARCHAR PK      등급 코드 (1,2,3,4,5,PI)
├── grade_name       VARCHAR         등급명 (예: "1등급: 극비")
├── description      TEXT            등급 기준 설명
└── mask_rule_default TEXT           기본 비식별화 규칙

TB_SENSITIVE_COLUMN (중요데이터 칼럼)
├── sensitive_id     BIGINT PK
├── column_id        BIGINT FK       TB_META_COLUMN 참조
├── grade            VARCHAR FK      등급
├── is_personal_info CHAR(1)         개인정보 여부
├── mask_rule_id     BIGINT FK       비식별화 규칙
├── reason           TEXT            등급 부여 사유
├── confirmed_yn     CHAR(1)         확인 완료 여부
├── confirm_person   VARCHAR
└── confirm_dt       DATETIME

TB_MASK_RULE (비식별화 규칙)
├── mask_rule_id     BIGINT PK
├── rule_name        VARCHAR         규칙명
├── rule_type        VARCHAR         MASKING/ENCRYPTION/GENERALIZATION/SUPPRESSION/NOISE_ADDITION
├── rule_expression  TEXT            규칙 표현식 또는 함수
└── example          VARCHAR         예시 (원본: 010-1234-5678 -> 마스킹: 010-****-****)

3 핵심 관계 다이어그램

TB_CONNECTION
    |
    | 1:N
    v
TB_META_TABLE ---------------------- TB_BIZ_TABLE
    |                                     |
    | 1:N                                 |
    v                                     v
TB_META_COLUMN -------------------- TB_BIZ_COLUMN
    |                          |-- domain_id --> TB_STANDARD_DOMAIN
    |                          +-- std_term_id -> TB_STANDARD_TERM
    | 1:N
    v
TB_META_INDEX
    |
    v
TB_META_INDEX_COLUMN

TB_STANDARD_SET
    |-- TB_STANDARD_TERM
    |-- TB_STANDARD_WORD
    +-- TB_STANDARD_DOMAIN
            |
            +-- domain_id -> TB_CODE_GROUP (rule_type = CODE인 경우)

TB_SENSITIVE_COLUMN
    |-- column_id --> TB_META_COLUMN
    +-- mask_rule_id -> TB_MASK_RULE

핵심 관계를 요약하면:

  • TB_CONNECTIONTB_META_TABLETB_META_COLUMN: 기술 메타데이터의 계층 구조
  • TB_META_TABLE ↔︎ TB_BIZ_TABLE, TB_META_COLUMN ↔︎ TB_BIZ_COLUMN: 기술-비즈니스 1:1 매핑
  • TB_BIZ_COLUMNTB_STANDARD_DOMAIN, TB_STANDARD_TERM: 표준과의 연결
  • TB_SENSITIVE_COLUMNTB_META_COLUMN: 중요데이터 등급 부여

4 이력 테이블 설계

모든 핵심 마스터 테이블은 이력 테이블을 별도로 갖는다. 이력 테이블은 마스터 테이블명에 _HIS를 붙이는 관례를 사용한다.

TB_META_COLUMN_HIS (칼럼 메타데이터 이력)
├── his_id           BIGINT PK       이력 ID
├── column_id        BIGINT          원본 column_id (FK 아님 - 삭제되더라도 이력은 남아야 함)
├── table_id         BIGINT          원본 table_id
├── [모든 TB_META_COLUMN의 칼럼들]
├── change_type      VARCHAR         INSERT/UPDATE/DELETE
├── changed_by       VARCHAR         변경자 (시스템 자동 수집인 경우 SYSTEM)
└── changed_dt       DATETIME        변경 일시
경고

이력 테이블에서 FK 제약조건을 제거하는 이유는, 원본 레코드가 삭제된 후에도 이력은 영구 보존해야 하기 때문이다. FK가 있으면 원본 삭제 시 CASCADE 또는 에러가 발생한다.


5 갭 분석을 위한 설계

갭 분석은 두 소스의 동일 객체를 비교해서 불일치를 탐지하는 기능이다. 비교 소스의 종류는 다음과 같다.

갭 유형 비교 대상 사용 시나리오
환경 간 갭 개발 DB 스키마 vs 운영 DB 스키마 배포 전 불일치 탐지
모델-DBMS 갭 ERD 모델 vs 실제 DBMS 스키마 설계-구현 일치 검증
표준-실제 갭 표준 명명 규칙 vs 실제 칼럼명 표준 준수율 측정

갭 분석 결과는 별도 테이블에 저장하거나, 뷰(View)로 실시간 계산한다. 데이터 양이 많으면 배치로 계산해서 결과 테이블에 적재하는 방식이 성능상 유리하다.

TB_GAP_RESULT (갭 분석 결과)
├── gap_id           BIGINT PK
├── gap_type         VARCHAR         ENV_DIFF/MODEL_DIFF/STANDARD_DIFF
├── source_conn_id   VARCHAR         소스 연결 ID
├── target_conn_id   VARCHAR         타겟 연결 ID
├── object_type      VARCHAR         TABLE/COLUMN/INDEX/CODE
├── source_object_id BIGINT          소스 객체 ID
├── target_object_id BIGINT          타겟 객체 ID (NULL이면 타겟에 없음)
├── gap_attribute    VARCHAR         불일치 속성 (예: "data_type", "data_length")
├── source_value     VARCHAR         소스의 값
├── target_value     VARCHAR         타겟의 값
├── status           VARCHAR         OPEN/RESOLVED/IGNORED
├── detected_dt      DATETIME        감지 일시
└── analysis_job_id  BIGINT FK       분석 작업 ID

6 관련 주제

시리즈 연결

카테고리 내 연결

Subscribe

Enjoy this blog? Get notified of new posts by email: