Notice
Recent Posts
Recent Comments
Link
| 일 | 월 | 화 | 수 | 목 | 금 | 토 |
|---|---|---|---|---|---|---|
| 1 | 2 | 3 | 4 | 5 | 6 | |
| 7 | 8 | 9 | 10 | 11 | 12 | 13 |
| 14 | 15 | 16 | 17 | 18 | 19 | 20 |
| 21 | 22 | 23 | 24 | 25 | 26 | 27 |
| 28 | 29 | 30 |
Tags
- Java데이터 타입
- for문
- While
- continue문
- 연관관계
- JAVA기초
- 메서드
- JAVA객체지향
- 집합관계
- IntelliJ IDEA
- 인텔리제이 한글 깨짐 해결법
- java변수
- 반복문
- OPP개념
- multi-threading
- 인텔리제이 기초 설정
- 형 변환
- this예약어
- Java
- 컴파일
- break문
- function
- 생성자
- 자바 멀티스레딩
- Thread
- 접근제어지시자
- 상수
- 시스템 환경 변수 편집
- 포함관계
- 메서드 오버로딩
Archives
- Today
- Total
최원종의 개발 블로그
PRIMARY KEY, UNIQUE, FOREIGN KEY - 10 본문
키 제약 조건이란?
데이터 무결성(데이터가 정확하고 일관되게 유지되는 것)을 보장하기 위한 규칙을 말함
비유: 학교 학생증
PK = 학번 (전교에서 절대 겹칠 수 없음, 비워둘 수 없음)
UNIQUE = 이메일 (각자 달라야 함, 학번과 달리 없을 수도 있음)
FK = 소속 학과 코드 (학교에 실제 존재하는 학과만 쓸 수 있음)

PRIMARY KEY (기본 키)
역할: 테이블의 각 행을 고유하게 식별
특징:
- 중복 값 불가
- NULL 불가
- 테이블당 하나만 설정 가능
- 자동으로 인덱스 생성 → 조회 빠름
-- 방법 1: 컬럼 뒤에 바로 선언
CREATE TABLE student2 (
student_id INT PRIMARY KEY,
name VARCHAR(50) NOT NULL
);
-- 방법 2: 테이블 끝에 선언 (복합 PK 등에 사용)
CREATE TABLE student3 (
student_id INT,
name VARCHAR(50) NOT NULL,
PRIMARY KEY (student_id)
);
-- 1. 테이블 하단에 PRIMARY KEY(컬럼1, 컬럼2) 형태
-- 수강신청 정보를 저장하는 테이블
CREATE TABLE enrollment (
student_id INT, -- 학번
course_id VARCHAR(10), -- 과목코드 (예: 'CS101')
reg_date DATE, -- 신청 날짜
PRIMARY KEY (student_id, course_id)
);
-- [핵심] 두 컬럼을 묶어서 기본키로 설정
-- 이 조합은 테이블 전체에서 유일해야 함!
UNIQUE KEY (고유 키)
역할: 특정 컬럼의 값이 중복되지 않도록 보장
특징:
- 중복 값 불가
- NULL 은 여러 개 허용 (MySQL 기준)
- 테이블에 여러 개 설정 가능
- 자동으로 인덱스 생성
CREATE TABLE member (
id INT PRIMARY KEY AUTO_INCREMENT,
email VARCHAR(100) UNIQUE, -- 이메일은 중복 불가
name VARCHAR(50) NOT NULL,
phone VARCHAR(20) UNIQUE -- 전화번호도 중복 불가
);
CREATE TABLE member2 (
id INT PRIMARY KEY,
email VARCHAR(100) UNIQUE, -- 이메일은 중복 불가
name VARCHAR(50) NOT NULL,
phone VARCHAR(20) UNIQUE -- 전화번호도 중복 불가
);
FOREIGN KEY (외래 키)
역할: 다른 테이블의 PK 를 참조하여 관계 형성
특징:
- 참조하는 값은 상대 테이블에 반드시 존재해야 함
- NULL 허용 가능
- 데이터 무결성 보장
CREATE TABLE orders (
id INT PRIMARY KEY AUTO_INCREMENT,
member_id INT NOT NULL,
amount INT NOT NULL,
FOREIGN KEY (member_id) REFERENCES member(id)
-- orders.member_id 는 member.id 에 있는 값만 가능
);
세 가지 키 비교
| PRIMARY KEY | UNIQUE KEY | FOREIGN KEY | |
| 역할 | 행 고유 식별 | 중복 값 방지 | 테이블 간 관계 |
| 중복 | 불가 | 불가 | 가능 |
| NULL | 불가 | 허용 | 허용 |
| 개수 | 테이블당 1개 | 여러 개 가능 | 여러 개 가능 |
CASCADE 필요성
use shop;
show tables;
-- member 회원가입
-- orders 테일 1번 회원이 주문한 목록 데이터가 있다고 가정
-- 두 테이블에 FK 관계일 때 member 테이블에 접근해서 1번 회원을 삭제할 수 있을까요?
select * from member;
select * from orders;
insert into orders(member_id, total_price) values (1, 10000);
-- FK 위반 why? orders 테이블에 member id 인 1번 데이터가 존재 하기 때문에
-- member 테이블에 1번 회원을 삭제하면 하면 orders 테이블에 member_id 1 은 무의미한 데이터가 된다.
delete from member where id = 1;
-- 2번은 바로 삭제 가능한가?
delete from member where id = 2;
-- 결론 orders 테이블에 존재하는 member_id 의 값 1을 먼저 삭제하고 member 테이블에 pk 인 1번 회원을 삭제할 수 있다.
-- orders 테이블에 데이터 삭제
delete from orders where member_id = 1;
ON DELETE CASCADE - 연쇄 삭제, ON UPDATE CASCADE - (연쇄 수정)
-- [준비] 현재 orders 테이블에 걸린 정확한 FK 이름을 확인합니다.
-- 결과창의 'Create Table' 항목에서 CONSTRAINT `제약조건명` 부분을 찾으세요.
SHOW CREATE TABLE orders;
-- [단계 1] 기존의 제약 조건을 삭제합니다.
-- (보통 자동 생성된 이름은 orders_ibfk_1 같은 형태입니다.)
ALTER TABLE orders DROP FOREIGN KEY orders_ibfk_1;
-- [단계 2] CASCADE 옵션을 추가하여 제약 조건을 새로 정의합니다.
-- 제약 조건 이름(fk_orders_member)을 직접 정해주면 나중에 관리하기 훨씬 편합니다.
ALTER TABLE orders
ADD CONSTRAINT fk_orders_member
FOREIGN KEY (member_id) REFERENCES member(id)
ON DELETE CASCADE -- 부모 삭제 시 자식도 삭제
ON UPDATE CASCADE; -- 부모 PK 수정 시 자식 FK도 수정
-- [단계 3] 테스트: 부모(member) 데이터 수정 시 연쇄 반응 확인
-- 1번 회원의 ID를 99로 바꿔봅니다.
UPDATE member SET id = 99 WHERE id = 1;
-- 자식(orders) 테이블을 조회하면 member_id가 자동으로 99로 바뀌어 있습니다.
SELECT * FROM orders WHERE member_id = 99;
-- [단계 4] 테스트: 부모 데이터 삭제 시 연쇄 삭제 확인
-- 99번 회원을 삭제합니다.
DELETE FROM member WHERE id = 99;
-- 자식 테이블에서 해당 주문들이 흔적도 없이 사라졌는지 확인합니다.
SELECT * FROM orders;
핵심 요약
PRIMARY KEY
행을 고유하게 식별, 중복/NULL 불가, 테이블당 1개
UNIQUE KEY
중복 값 방지, NULL 여러 개 허용, 테이블에 여러 개 가능
실무 예: 이메일, 전화번호, 사용자명
FOREIGN KEY
다른 테이블의 PK 참조
없는 값 참조 → INSERT 오류
참조 중인 행 삭제 → DELETE 오류 (CASCADE 설정 시 함께 삭제)'MySQL' 카테고리의 다른 글
| MySQL 기초 복습 - 12 (0) | 2026.04.03 |
|---|---|
| 인덱스(Index) - 11 (0) | 2026.04.03 |
| UPDATE 와 DELETE - 9 (0) | 2026.04.03 |
| SELECT 와 WHERE - 8 (0) | 2026.04.03 |
| INSERT 구문과 제약 조건 -7 (0) | 2026.04.02 |