클러스터를 운영한다는 건 결국 '땅을 나누고(Namespace), 울타리를 치는(ResourceQuota), 세부 규칙을 정하는(LimitRange)' 관리의 연속이다. 클라우드 네이티브 환경에서 자원 고갈은 곧 서비스 장애로 이어진다.
이를 위한 클러스터 자원 관리의 3대 핵심 오브젝트인 Namespace, ResourceQuota, LimitRange를 알아보자
0. 왜 자원을 제한하고 구역을 나누는가?

쿠버네티스 클러스터의 CPU와 메모리는 모든 파드가 공유하는 유한한 자원이다.
- 즉, 클러스터라는 전체 사용할 수 있는 자원이 있다는건 알고 있다.
- 일반적으로 Memory, CPU가 있고,
- 여러 Namespaces가 있고, 그 안에는 여러 파드들이 있다.
- 이 파드들이 클러스터의 자원들을 공유해서 사용하는데.
- 안의 파드들이 클러스터 자원을 모두 사용해버리면 다른 파드 입장에선 더 이상 쓸 자원이 없어서 자원이 필요할 때 문제가 발생하게 된다.
- 그래서 등장한 해결 방안이 Resource Quota, Litimit Range로 한계를 설정하는 것이다.
- 자원 독점 방지: 특정 네임스페이스의 파드가 클러스터 자원을 전부 써버리면 다른 파드들이 굶어 죽게 된다.
- 3번째 파드를 보면 5개의 자원 중 4개를 독점 중이다.
- 리소스 쿼터(ResourceQuota)의 역할: 이걸 네임스페이스마다 달면, 네임스페이스마다 '최대 한계(2개)'라는 울타리를 친다. 즉, 자원이 부족해서 문제가 될지언정, 해당 구역의 자원이 다른 구역에 영향을 끼치지 못하게 격리되는 것이다.
- 그렇다면 다른 문제도 있다. 최대 2개를 받은 네임스페이스가 2개의 자원을 이미 모두 사용하고 있다. 그러면 다른 파드들은 해당 네임스페이스에 못 들어오게된다.
- 리미트 레인지(LimitRange)의 역할: 그래서 등장했다. 네임스페이스 내부로 들어오는 개별 파드의 '크기'를 제한한다. 너무 큰 파드 하나가 네임스페이스를 장악해 다른 파드들이 못 들어오는 사태를 막기 위함이다.
- 리소스 쿼터(ResourceQuota)의 역할: 이걸 네임스페이스마다 달면, 네임스페이스마다 '최대 한계(2개)'라는 울타리를 친다. 즉, 자원이 부족해서 문제가 될지언정, 해당 구역의 자원이 다른 구역에 영향을 끼치지 못하게 격리되는 것이다.
- 3번째 파드를 보면 5개의 자원 중 4개를 독점 중이다.
- 확장성: 이 제한 기능들은 네임스페이스뿐만 아니라 클러스터 전체 자원에도 적용할 수 있다.
1. 네임스페이스 (Namespace)

- 이름 중복 방지: 한 네임스페이스 내에서 같은 타입의 오브젝트(예: Pod)는 이름을 중복해서 쓸 수 없지만, 다른 네임스페이스라면 가능하다.
- 자원 분리: 서비스와 파드의 연결(Selector-Label)은 기본적으로 네임스페이스를 넘어서지 못한다.
- 일괄 삭제: 네임스페이스를 지우면 그 안의 모든 자원이 함께 삭제되므로 운영 시 매우 유의해야 한다.
- 네트워크 통신: 기본적으로는 IP를 통해서는 타 네임스페이스 파드와 통신이 가능하지만, NetworkPolicy로 이를 차단할 수 있다.
- 즉, 대부분의 자원들은 그 네임스페이스 안에서만 사용할 수가 있는 것이다.
- 예외: 노드(Node)나 퍼시스턴트 볼륨(PV)은 특정 네임스페이스에 속하지 않는 클러스터 공용 오브젝트다.
- YAML은 그냥 kind와 name만 지정해주는 것을 볼 수 있다.
- 파드나 서비스를 만들 때는 속할 네임스페이스를 지정하는 것.
- labes와 selector의 값이 같은 파드를 가르켜도 결국에는 다른 네임스페이스(nm-1 / nm-2)에 있기 때문에 무용지물이다.
2. 리소스 쿼터 (ResourceQuota)

- 네임스페이스 총량 제한: 해당 네임스페이스에 들어갈 모든 파드의 리퀘스트(Request)와 리미트(Limit) 합계에 한계를 hard라는 속성으로 설정한다.
- 스펙 명시 필수: 쿼터가 걸린 네임스페이스에 파드를 만들려면 반드시 자원 사용량(spec.resources.requests, limits)을 명시해야 하며, 이를 누락하거나 쿼터를 초과하면 생성이 거부된다.
- 제한 대상: CPU, 메모리, 스토리지뿐만 아니라 파드나 서비스 같은 오브젝트의 개수도 제한할 수 있다.
3. 리미트 레인지 (LimitRange)

- 파드 자원 체크: 개별 파드가 가진 리미트 값이 설정된 min(최소)보다 작거나 max(최대)보다 크면 생성이 차단된다.
- 비율 제한: maxLimitRequestRatio를 통해 Request 대비 Limit의 비율(예: 3배 이하)을 강제할 수 있다.
- Pod2는 limits가 requests보다 4배 이상이므로 거부된다.
- 자동 할당: Pod3 처럼 파드에 자원 설정을 안 했을 경우에 유용한, 자동으로 옵션들이 적용되는 defaultRequest와 default(Limit) 값을 설정할 수 있다.
💡 꼬리 질문
Q: 네임스페이스에 ResourceQuota만 설정되어 있고 파드에 자원 명시를 깜빡했다면 생성이 거부되는데, 이때 관리자가 파드에 일일이 자원 설정을 추가하지 않고도 자동으로 배포되게 하려면 어떻게 해야 할까?
결론: 해당 네임스페이스에 LimitRange의 default 설정을 추가하면 된다.
- 상호 보완: ResourceQuota는 자원 명시를 강제하고 없으면 차단하지만, LimitRange는 명시되지 않은 자원을 자동으로 채워주는 역할을 한다.
- 동작 원리: 사용자가 자원 설정 없이 파드를 생성 요청하면, Admission Controller 단계에서 LimitRange의 default 값이 파드 스펙에 주입된다. 이후 ResourceQuota는 이 주입된 값을 바탕으로 총량 합계를 계산하여 생성을 허용하게 된다.
1. Namespace: 논리적 격리와 한계

apiVersion: v1
kind: Namespace
metadata:
name: nm-1
네임스페이스는 앱 간의 논리적 구분을 위한 그룹 개념이다. 하지만 모든 것이 완벽하게 격리되는 것은 아니라는 점을 명심하자.
- 이름 유일성: 한 네임스페이스 내에서 같은 종류의 오브젝트는 이름이 중복될 수 없다. 만약 동일한 이름의 파드를 생성하려 하면 에러가 발생한다.
apiVersion: v1
kind: Pod
metadata:
name: pod-1
namespace: nm-1
labels:
app: pod
spec:
containers:
- name: container
image: kubetm/app
ports:
- containerPort: 8080
apiVersion: v1
kind: Service
metadata:
name: svc-1
namespace: nm-1
spec:
selector:
app: pod
ports:
- port: 9000
targetPort: 8080
- 연결의 제한: 서비스의 셀렉터(Selector)와 파드의 라벨(Label) 연결은 오직 같은 네임스페이스 상에서만 유효하다.
격리되지 않는 자원 (주의!)
1. IP 통신: 파드의 IP나 서비스의 IP를 알면 네임스페이스가 달라도 기본적으로 통신을 막지 않는다.
- Namespace(nm-2):Pod(pod-1)에 들어가서 타 Namespace(nm-1)에 있는 Pod(pod-2)를 호출하는 등
2. NodePort: 노드 포트는 클러스터 전역 자원이다. 특정 네임스페이스에서 30001번 포트를 선점하면 다른 네임스페이스에서는 해당 포트를 쓸 수 없다.
apiVersion: v1
kind: Service
metadata:
name: svc-2
namespace: nm-1
spec:
ports:
- port: 9000
targetPort: 8080
nodePort: 30001
type: NodePort
---
apiVersion: v1
kind: Service
metadata:
name: svc-2namespace: nm-2
spec:
ports:
- port: 9000
targetPort: 8080
nodePort: 30001
type: NodePort
3. Volume (hostPath): 노드의 특정 경로를 공유하는 hostPath 볼륨은 네임스페이스가 달라도 동일한 노드 경로를 바라본다면 데이터가 그대로 공유된다.
apiVersion: v1
kind: Pod
metadata:
name: pod-2
namespace: nm-1
spec:
nodeSelector:
kubernetes.io/hostname: k8s-worker1
containers:
- name: container
image: kubetm/init
volumeMounts:
- name: host-path
mountPath: /mount1
volumes:
- name : host-path
hostPath:
path: /node-v
type: DirectoryOrCreate
---
apiVersion: v1
kind: Pod
metadata:
name: pod-2
namespace: nm-2
spec:
nodeSelector:
kubernetes.io/hostname: k8s-worker1
containers:
- name: container
image: kubetm/init
volumeMounts:
- name: host-path
mountPath: /mount1
volumes:
- name : host-path
hostPath:
path: /node-v
type: DirectoryOrCreate
- 일괄 삭제: 네임스페이스를 삭제하면 그 안에 소속된 모든 오브젝트가 자동으로 삭제되니 운영 시 각별히 주의해야 한다.
2. ResourceQuota: 네임스페이스 총량 제한 (상세코드)

네임스페이스별 자원 사용량이나 오브젝트 개수를 제한한다.
apiVersion: v1
kind: Namespace
metadata:
name: nm-3
apiVersion: v1
kind: ResourceQuota
metadata:
name: rq-1
namespace: nm-3
spec:
hard:
requests.memory: 1Gi
limits.memory: 1Gi
apiVersion: v1
kind: Pod
metadata:
name: pod-3
namespace: nm-3
spec:
containers:
- name: container
image: kubetm/app
resources:
requests:
memory: 0.5Gi
limits:
memory: 0.5Gi
- 자원 명시 필수: 리소스 쿼터가 설정된 네임스페이스에 파드를 만들 때는 반드시 resources.requests와 limits를 명시해야 한다. 명시하지 않으면 생성이 거부된다.
- 초과 시 차단: 설정된 총량(예: 메모리 1Gi)을 넘어서는 자원을 요청하는 파드는 생성 단계에서 차단된다.
apiVersion: v1
kind: ResourceQuota
metadata:
name: rq-2
namespace: nm-3
spec:
hard:
cpu: 4 # 1-1. 컴퓨팅 리소스 제한 (얼마나 무거운가)
memory: 4Gi # 1-2. 컴퓨팅 리소스 제한
pods: 2 # 2. 객체 수 제한 (몇 개나 되는가)
secrets: 5 # (심지어 시크릿 개수도 제한 가능)
- 개수 제한: 메모리뿐만 아니라 생성 가능한 파드의 개수 자체도 제한할 수 있다.
1. Pod 생성 → 2. ResourceQuota 생성 → 3. Pod 생성
- 실무 팁 (예외 상황): 리소스 쿼터를 만들기 전에 이미 존재하는 파드들은 쿼터 규칙의 적용을 받지 않고 그대로 살아남는다.
- Resource가 명시되어 있지 않는 Pod가 있는 상태이다
- ResourceQuota를 만든다.
- 기존 Pod는 ResourceQuota 규칙과 상관이 없다. 벗어난다.
- 이 경우 쿼터에 명시된 한계보다 더 많은 자원을 쓰는 상태가 발생할 수 있으므로, 쿼터 설정 전에는 네임스페이스를 비워두는 것이 정석이다.
3. LimitRange: 개별 파드의 제약 조건

네임스페이스에 들어올 수 있는 개별 파드의 자원 크기를 체크하고 제어한다.
apiVersion: v1
kind: LimitRange
metadata:
name: lr-1
namespace: nm-5
spec:
limits:
- type: Container
min:
memory: 0.1Gi
max:
memory: 0.4Gi
maxLimitRequestRatio:
memory: 3
defaultRequest:
memory: 0.1Gi
default:
memory: 0.2Gi
- 최소/최대(min/max) 제한: 컨테이너가 가질 수 있는 자원의 최소값과 최대값을 강제한다. 최대값(max)을 초과하거나 비율(maxLimitRequestRatio)을 어긴 파드는 생성이 금지된다.
- 기본값(Default) 할당: 파드 정의서에 리소스 설정을 누락했을 때 자동으로 적용될 defaultRequest와 default(Limit) 값을 지정할 수 있다.
apiVersion: v1
kind: Namespace
metadata:
name: nm-6
-----
apiVersion: v1
kind: LimitRange
metadata:
name: lr-5
namespace: nm-6
spec:
limits:
- type: Container
min:
memory: 0.1Gi
max:
memory: 0.5Gi
maxLimitRequestRatio:
memory: 1
defaultRequest:
memory: 0.5Gi
default:
memory: 0.5Gi
----
apiVersion: v1
kind: LimitRange
metadata:
name: lr-3
namespace: nm-6
spec:
limits:
- type: Container
min:
memory: 0.1Gi
max:
memory: 0.3Gi
maxLimitRequestRatio:
memory: 1
defaultRequest:
memory: 0.3Gi
default:
memory: 0.3Gi
- 중복 설정의 위험 (주의): 위와 같이 한 네임스페이스(nm-6)에 여러 개의 리미트 레인지(lr-5, lr-3)를 적용할 수 있다. 이 경우 쿠버네티스는 가장 엄격한 기준(더 작은 max 값 등)을 적용한다. 이는 예상치 못한 생성 에러를 유발할 수 있으므로 관리가 매우 까다롭다.
- 예를 들면, 위의 상황에서 0.5Gi를 적용하려고 할때, 0.5Gi가 설정된 lr-5가 있어도 lr-3에 있는 0.3Gi가 더 엄격하기 때문에 lr-3이 적용된 것이다.
💡 꼬리 질문
Q: 리소스 쿼터가 적용된 네임스페이스에 파드를 배포할 때, 왜 리미트 레인지를 함께 설정하는 것이 운영상 더 효율적일까?
결론: 사용자 경험을 개선하고 배포 실패율을 낮추기 위해서다.
- 리소스 쿼터만 단독으로 있으면 모든 사용자가 일일이 자원 스펙을 기입해야 하고, 누락 시 배포가 실패한다.
- 하지만 리미트 레인지의 default 설정을 함께 두면, 자원 정보를 깜빡하고 넣지 않은 파드에도 자동으로 적절한 자원량이 주입된다.
- 결과적으로 리소스 쿼터의 '자원 명시 필수' 제약을 자동으로 통과하게 만들어주므로, 운영 자동화 측면에서 훨씬 유리하다.
위 학습용 정리 내용 및 사진 자료는 "인프런_대세는 쿠버네티스(https://inf.run/Lv5RV)" 강의를 소스로 작성하였습니다.
'Cloud Native > Kubernetes' 카테고리의 다른 글
| 7. Deployment - Recreate, RollingUpdate (0) | 2026.01.23 |
|---|---|
| 6. ReplicaSet - Template, Replicas, Selector (0) | 2026.01.22 |
| 4. ConfigMap, Secret - Env, Mount (0) | 2026.01.18 |
| 3. Volume - emptyDir, hostPath, PV/PVC (0) | 2026.01.16 |
| 2. Service - ClusterIP, NodePort, LoadBalancer (0) | 2026.01.16 |