🗄️ 데이터베이스

데이터 무결성

Data Integrity

데이터의 정확성과 일관성을 보장하는 속성. 개체 무결성, 참조 무결성, 도메인 무결성으로 구분.

📖 상세 설명

데이터 무결성(Data Integrity)은 데이터의 정확성, 일관성, 유효성을 보장하는 데이터베이스의 핵심 속성입니다. 잘못된 데이터가 저장되거나 데이터 간 불일치가 발생하지 않도록 보호합니다.

무결성의 주요 유형: 개체 무결성(Primary Key는 NULL이나 중복 불가), 참조 무결성(Foreign Key는 참조 테이블에 존재해야 함), 도메인 무결성(컬럼 값은 정의된 타입/범위 내), 사용자 정의 무결성(비즈니스 규칙 적용).

DBMS는 제약조건(Constraints), 트리거(Triggers), 트랜잭션(ACID)을 통해 무결성을 강제합니다. 애플리케이션 레벨에서도 유효성 검증이 필요합니다.

💻 코드 예제

-- 개체 무결성: Primary Key 제약
CREATE TABLE users (
    id SERIAL PRIMARY KEY,  -- NOT NULL + UNIQUE 자동 적용
    email VARCHAR(255) NOT NULL UNIQUE
);

-- 참조 무결성: Foreign Key 제약
CREATE TABLE orders (
    id SERIAL PRIMARY KEY,
    user_id INT NOT NULL,
    FOREIGN KEY (user_id) REFERENCES users(id)
        ON DELETE RESTRICT  -- 참조된 사용자 삭제 방지
        ON UPDATE CASCADE   -- 사용자 ID 변경 시 자동 반영
);

-- 도메인 무결성: CHECK 제약
CREATE TABLE products (
    id SERIAL PRIMARY KEY,
    name VARCHAR(100) NOT NULL,
    price DECIMAL(10,2) CHECK (price >= 0),
    stock INT DEFAULT 0 CHECK (stock >= 0),
    status VARCHAR(20) CHECK (status IN ('active', 'inactive', 'discontinued'))
);

-- 사용자 정의 무결성: 트리거
CREATE OR REPLACE FUNCTION check_order_total()
RETURNS TRIGGER AS $$
BEGIN
    IF NEW.total < 0 THEN
        RAISE EXCEPTION 'Order total cannot be negative';
    END IF;
    IF NEW.total > 1000000 THEN
        RAISE EXCEPTION 'Order total exceeds maximum limit';
    END IF;
    RETURN NEW;
END;
$$ LANGUAGE plpgsql;

CREATE TRIGGER validate_order
BEFORE INSERT OR UPDATE ON orders
FOR EACH ROW EXECUTE FUNCTION check_order_total();

🗣️ 실무 대화 예시

QA: "주문 데이터에 존재하지 않는 user_id가 들어가 있어요. 어떻게 된 거죠?"

DBA: "Foreign Key 제약이 없네요. 누가 성능 이슈로 뺐나 봐요."

백엔드 개발자: "제가 빼달라고 했어요. INSERT 속도가 느려서요."

DBA: "FK 체크 비용보다 잘못된 데이터 수정 비용이 훨씬 커요. 다시 추가하고, 성능은 인덱스로 해결합시다."

면접관: "데이터 무결성의 종류와 보장 방법을 설명해주세요."

지원자: "개체 무결성은 PK로, 참조 무결성은 FK로, 도메인 무결성은 CHECK/NOT NULL로, 사용자 정의 무결성은 트리거로 보장합니다. ACID 트랜잭션으로 연산 중 일관성도 유지합니다."

면접관: "NoSQL에서는 어떻게 하나요?"

지원자: "DB 레벨 제약이 없어서 애플리케이션에서 검증합니다. 스키마 검증 라이브러리나 ODM의 validator를 사용하고, 중요 로직은 트랜잭션을 지원하는 DB를 선택합니다."

리뷰어: "status 값이 그냥 VARCHAR인데, 잘못된 값이 들어갈 수 있어요."

개발자: "애플리케이션에서 enum으로 검증하고 있어요."

리뷰어: "그래도 DB에 CHECK 제약 추가하세요. 다른 경로로 데이터 들어올 수도 있고, DB가 마지막 방어선이에요."

개발자: "맞네요. CHECK (status IN ('pending', 'confirmed', 'shipped')) 추가하겠습니다."

⚠️ 주의사항

🔗 관련 용어

📚 더 배우기