Cloud Native

OPA Gatekeeper Cloud Native Design

opa gatekeeper cloud native design
OPA Gatekeeper Cloud Native Design | SiamCafe Blog

โดย อ. บอมกิตติทัศน์เจริญพนาสิทธิ์ | อัปเดต 24 ก. พ. 2026 | อ่าน 14 นาที

OPA และ Gatekeeper คืออะไร — ภาพรวม Policy-as-Code

Open Policy Agent (OPA) เป็น General-purpose Policy Engine แบบ Open Source ที่พัฒนาโดย Styra และเป็น Graduated Project ของ CNCF (Cloud Native Computing Foundation) OPA ทำหน้าที่เป็นจุดตัดสินใจกลาง (Policy Decision Point) รับ Input เป็น JSON แล้วประเมินกับ Policy ที่เขียนด้วยภาษา Rego ให้ผลลัพธ์เป็น Allow/Deny พร้อมเหตุผล OPA สามารถใช้ได้กับทุกระบบไม่จำเป็นต้องเป็น Kubernetes เช่น API Gateway, CI/CD Pipeline, Terraform, Microservices Authorization

Gatekeeper เป็น Project ที่นำ OPA มาใช้เฉพาะกับ Kubernetes ในรูปแบบ Admission Controller ทำงานเป็น Validating Webhook ที่คอยตรวจสอบทุก Request ที่ส่งมายัง Kubernetes API Server ก่อนที่จะถูกสร้างจริงถ้า Request ไม่ผ่าน Policy จะถูกปฏิเสธทันทีพร้อมข้อความ Error ที่อธิบายว่าผิดกฎข้อใด

แนวคิด Policy-as-Code หมายถึงการเขียน Policy เป็นโค้ดที่เก็บใน Git ผ่าน Code Review และ CI/CD เหมือนกับโค้ดโปรแกรมทั่วไปทำให้ Policy มี Version Control, Audit Trail, Automated Testing และ Consistency ข้ามทุก Environment

ทำไมต้องมี Policy Enforcement บน Kubernetes

Kubernetes ให้อิสระสูงมากในการสร้าง Resource ใดก็ได้ Developer สามารถ Deploy Container ที่รันเป็น Root, ใช้ Image จาก Registry ที่ไม่น่าเชื่อถือ, ไม่ตั้ง Resource Limits, เปิด Port ที่อันตรายหรือสร้าง Service แบบ LoadBalancer ที่เปิดสู่ Internet โดยไม่ตั้งใจในองค์กรที่มี Developer หลายสิบทีมใช้ Cluster ร่วมกันการพึ่งพาแค่ความรับผิดชอบของแต่ละคนไม่เพียงพอ

Policy Enforcement ช่วยแก้ปัญหานี้โดยกำหนดกฎเกณฑ์ที่บังคับใช้อัตโนมัติตัวอย่าง Policy ที่องค์กรส่วนใหญ่ต้องการได้แก่ทุก Pod ต้องมี Resource Requests/Limits, ห้ามรัน Container เป็น Root, Image ต้องมาจาก Trusted Registry เท่านั้น, ทุก Namespace ต้องมี Label ระบุ team/cost-center, ห้ามใช้ latest Tag ต้องระบุ Version ชัดเจนและ Ingress ต้อง TLS Only

สถาปัตยกรรม Gatekeeper — Admission Webhook Flow

Gatekeeper ทำงานผ่าน Kubernetes Dynamic Admission Control Flow ดังนี้

  1. User/CI ส่ง kubectl apply ไปยัง API Server
  2. API Server ผ่าน Authentication และ Authorization (RBAC)
  3. API Server ส่ง Admission Request ไปยัง Gatekeeper Webhook
  4. Gatekeeper โหลด ConstraintTemplate + Constraint ที่เกี่ยวข้อง
  5. OPA Engine ภายใน Gatekeeper ประเมิน Rego Policy
  6. ถ้าผ่านทุก Policy → Admit (สร้าง Resource ได้)
  7. ถ้าไม่ผ่าน → Deny พร้อม Error Message กลับไปยัง User

Gatekeeper ประกอบด้วย 3 Component หลักคือ Controller Manager จัดการ CRD (ConstraintTemplate, Constraint) และ Sync ข้อมูล Resource เข้า OPA Cache, Audit Controller ตรวจสอบ Resource ที่มีอยู่แล้วว่าผ่าน Policy หรือไม่ (Background Scan) และ Webhook Server รับ Admission Request จาก API Server แล้วประเมิน Policy

ติดตั้ง Gatekeeper บน Kubernetes Cluster

วิธีติดตั้งที่แนะนำคือใช้ Helm Chart

# เพิ่ม Helm Repository
helm repo add gatekeeper https://open-policy-agent.github.io/gatekeeper/charts
helm repo update

# ติดตั้ง Gatekeeper
helm install gatekeeper gatekeeper/gatekeeper \
 --namespace gatekeeper-system \
 --create-namespace \
 --set replicas=3 \
 --set audit.replicas=1 \
 --set audit.logLevel=INFO

# ตรวจสอบว่าติดตั้งสำเร็จ
kubectl get pods -n gatekeeper-system
# ควรเห็น gatekeeper-controller-manager และ gatekeeper-audit

# ตรวจสอบ CRD
kubectl get crd | grep gatekeeper
# constrainttemplates.templates.gatekeeper.sh
# configs.config.gatekeeper.sh

หลังติดตั้งเสร็จ Gatekeeper จะลงทะเบียนเป็น Validating Webhook กับ API Server อัตโนมัติทุก Request ที่สร้าง/แก้ไข Resource จะถูกส่งผ่าน Gatekeeper ก่อน

ภาษา Rego — พื้นฐานที่ต้องรู้

Rego เป็นภาษา Declarative ที่ออกแบบมาเฉพาะสำหรับเขียน Policy มีลักษณะคล้าย Datalog ไม่ใช่ภาษาแบบ Imperative อย่าง Python หรือ Go จึงมี Learning Curve ค่อนข้างสูงแต่เมื่อเข้าใจแนวคิดแล้วจะเขียนได้กระชับมาก

# ตัวอย่าง Rego พื้นฐาน

# กฎ: ห้าม Container รันเป็น Root
package kubernetes.admission

# Violation จะถูกสร้างเมื่อพบ Container ที่รัน root
violation[{"msg": msg}] {
 container := input.review.object.spec.containers[_]
 container.securityContext.runAsUser == 0
 msg := sprintf("Container '%v' must not run as root (UID 0)", [container.name])
}

# กฎ: ต้องมี Resource Limits
violation[{"msg": msg}] {
 container := input.review.object.spec.containers[_]
 not container.resources.limits
 msg := sprintf("Container '%v' must have resource limits", [container.name])
}

# กฎ: ห้ามใช้ :latest tag
violation[{"msg": msg}] {
 container := input.review.object.spec.containers[_]
 endswith(container.image, ":latest")
 msg := sprintf("Container '%v' uses :latest tag, must specify version", [container.name])
}

หลักการสำคัญของ Rego ที่ต้องเข้าใจได้แก่ Rules เป็น Declarative บอกว่า "อะไรเป็น True" ไม่ใช่ "ทำอะไรทีละขั้น", Iteration แบบ Implicit ใช้ [_] วนลูป Array อัตโนมัติ, Unification ใช้ := กำหนดค่าและ == เปรียบเทียบและ Short-circuit ถ้าเงื่อนไขบรรทัดใดเป็น False กฎทั้งหมดจะไม่ถูก Trigger

ConstraintTemplate — สร้าง Policy Template

ConstraintTemplate เป็น CRD ของ Gatekeeper ที่ใช้กำหนด "ประเภทของ Policy" โดยเขียน Rego Logic ไว้ภายในพร้อมกำหนด Parameter Schema สำหรับให้ Customize ได้

apiVersion: templates.gatekeeper.sh/v1
kind: ConstraintTemplate
metadata:
 name: k8srequiredlabels
spec:
 crd:
 spec:
 names:
 kind: K8sRequiredLabels
 validation:
 openAPIV3Schema:
 type: object
 properties:
 labels:
 type: array
 items:
 type: string
 description: "List of required labels"
 targets:
 - target: admission.k8s.gatekeeper.sh
 rego: |
 package k8srequiredlabels

 violation[{"msg": msg, "details": {"missing_labels": missing}}] {
 provided := {label | input.review.object.metadata.labels[label]}
 required := {label | label := input.parameters.labels[_]}
 missing := required - provided
 count(missing) > 0
 msg := sprintf("Resource missing required labels: %v", [missing])
 }

ConstraintTemplate ข้างต้นสร้าง "ประเภท Policy" ชื่อ K8sRequiredLabels ที่ตรวจว่า Resource มี Label ครบตามที่กำหนดหรือไม่จะเห็นว่า Rego Logic ใช้ input.parameters.labels อ้างอิง Parameter ที่จะถูกกำหนดตอนสร้าง Constraint ทำให้ Template นี้ Reusable ได้เช่นบังคับ Label ต่างกันสำหรับ Namespace ต่างกัน

Constraint — บังคับใช้ Policy จริง

Constraint เป็น Instance ของ ConstraintTemplate ที่กำหนด Parameter และ Scope ว่าจะบังคับใช้กับ Resource ประเภทไหนใน Namespace ไหน

apiVersion: constraints.gatekeeper.sh/v1beta1
kind: K8sRequiredLabels
metadata:
 name: ns-must-have-team-label
spec:
 enforcementAction: deny # deny | dryrun | warn
 match:
 kinds:
 - apiGroups: [""]
 kinds: ["Namespace"]
 parameters:
 labels:
 - "team"
 - "cost-center"
 - "environment"

Constraint นี้บังคับว่าทุก Namespace ต้องมี Label team, cost-center และ environment ถ้าสร้าง Namespace โดยไม่มี Label เหล่านี้จะถูก Deny ทันที

enforcementAction มี 3 ค่าที่สำคัญมาก deny ปฏิเสธ Request ทันที, dryrun อนุญาตแต่บันทึก Violation ไว้ใน Audit Log เหมาะกับการทดสอบ Policy ใหม่ก่อน Enforce จริงและ warn อนุญาตแต่แสดง Warning ให้ User เห็น

ตัวอย่าง Policy ที่ใช้บ่อย 10 ข้อ

#Policyเหตุผล
1ห้าม Container รันเป็น Rootลดความเสี่ยง Container Escape
2ต้องมี Resource Requests/Limitsป้องกัน Noisy Neighbor, ช่วย Scheduler
3Image ต้องมาจาก Trusted Registryป้องกัน Supply Chain Attack
4ห้ามใช้ :latest TagReproducibility, Rollback ได้
5ทุก Resource ต้องมี Required LabelsCost Allocation, Team Ownership
6ห้ามสร้าง Service type LoadBalancerใช้ Ingress Controller แทน
7ห้าม HostNetwork, HostPID, HostIPCIsolation ระหว่าง Pod กับ Node
8ต้องมี Liveness/Readiness ProbeSelf-healing, Graceful Deployment
9PDB ต้องมีก่อน Deploy ได้ป้องกัน Downtime ตอน Node Drain
10ห้าม Privilege Escalationป้องกัน Container ได้ Root บน Host

Gatekeeper มี Library ของ ConstraintTemplate สำเร็จรูปที่ชื่อ Gatekeeper Library (github.com/open-policy-agent/gatekeeper-library) รวม Policy ที่ใช้บ่อยกว่า 30 ข้อสามารถนำมาใช้ได้ทันทีโดยไม่ต้องเขียน Rego เอง

Audit Mode — ตรวจสอบ Resource ที่มีอยู่แล้ว

Gatekeeper ไม่ได้ตรวจแค่ Resource ใหม่เท่านั้นแต่ยังมี Audit Controller ที่ Scan Resource ที่มีอยู่แล้วในระบบว่าผ่าน Policy ปัจจุบันหรือไม่ผลลัพธ์ Audit จะถูกเก็บไว้ใน Status ของ Constraint

# ดูผล Audit ของ Constraint
kubectl get k8srequiredlabels ns-must-have-team-label -o yaml

# ส่วน status.violations จะแสดง Resource ที่ไม่ผ่าน
# status:
# totalViolations: 3
# violations:
# - enforcementAction: deny
# kind: Namespace
# name: default
# message: "Resource missing required labels: {team, cost-center}"

# ดูสรุป Violation ทุก Constraint
kubectl get constraints -o wide

วิธีใช้ Audit ในทางปฏิบัติคือเมื่อสร้าง Policy ใหม่ให้ตั้ง enforcementAction: dryrun ก่อนแล้วรอ Audit รอบถัดไป (Default ทุก 60 วินาที) ดูว่ามี Resource กี่ตัวที่ไม่ผ่านแก้ไขให้ผ่านหมดแล้วค่อยเปลี่ยนเป็น deny

Mutation — แก้ไข Resource อัตโนมัติ

นอกจาก Validation แล้ว Gatekeeper ยังรองรับ Mutation ซึ่งเป็นการแก้ไข Resource อัตโนมัติก่อนสร้างเช่นเพิ่ม Label ที่ขาด, ตั้ง Default Security Context, Inject Sidecar

apiVersion: mutations.gatekeeper.sh/v1
kind: Assign
metadata:
 name: default-security-context
spec:
 applyTo:
 - groups: [""]
 kinds: ["Pod"]
 versions: ["v1"]
 match:
 scope: Namespaced
 kinds:
 - apiGroups: [""]
 kinds: ["Pod"]
 location: "spec.containers[name:*].securityContext.runAsNonRoot"
 parameters:
 assign:
 value: true

Mutation นี้จะเพิ่ม runAsNonRoot: true ให้กับทุก Container ที่ไม่ได้ตั้งค่านี้ไว้ทำให้ไม่ต้องพึ่ง Developer ว่าจะจำตั้ง Security Context หรือไม่ระบบจะตั้งให้อัตโนมัติ

Gatekeeper vs Kyverno — เปรียบเทียบ

คุณสมบัติGatekeeper (OPA)Kyverno
ภาษา PolicyRego (Declarative)YAML (Native K8s)
Learning Curveสูง (ต้องเรียน Rego)ต่ำ (ใช้ YAML ปกติ)
ขอบเขตการใช้งานKubernetes + ระบบอื่นๆเฉพาะ Kubernetes
Mutationรองรับ (v3.7+)รองรับ (ตั้งแต่แรก)
Generationไม่รองรับรองรับ (สร้าง Resource ใหม่)
Image Verificationต้องใช้ร่วมกับ SigstoreBuilt-in Cosign/Notary
CNCF StatusGraduatedIncubating
Communityใหญ่กว่า, มีมานานกว่าเติบโตเร็ว, Active

คำแนะนำคือถ้าต้องการ Policy Engine ที่ใช้ได้ทั้งใน Kubernetes, API Gateway, Terraform, CI/CD Pipeline ให้เลือก OPA/Gatekeeper เพราะ Rego ใช้ได้ทุกที่ถ้าต้องการความง่ายและใช้เฉพาะ Kubernetes ให้เลือก Kyverno

Best Practices สำหรับ Production

Troubleshooting ปัญหาที่พบบ่อย

สรุปและแหล่งเรียนรู้เพิ่มเติม

OPA Gatekeeper เป็นเครื่องมือสำคัญสำหรับการบังคับใช้ Policy บน Kubernetes Cluster ในระดับ Production การเข้าใจ Rego, ConstraintTemplate และ Constraint จะช่วยให้สร้าง Guard Rail ที่ป้องกัน Misconfiguration, Security Risk และ Compliance Issue ได้อย่างมีประสิทธิภาพเมื่อรวมกับ GitOps จะได้ระบบ Policy-as-Code ที่ Auditable, Testable และ Versionable ครบถ้วน

แหล่งเรียนรู้เพิ่มเติมได้แก่ OPA Official Documentation (openpolicyagent.org), Gatekeeper Library (GitHub), Rego Playground สำหรับทดลองเขียน Policy และ Styra Academy สำหรับคอร์สออนไลน์ฟรีติดตามบทความใหม่ๆได้ที่ SiamCafe.net

อ. บอมกิตติทัศน์เจริญพนาสิทธิ์
IT Infrastructure Expert | Thaiware Award | ประสบการณ์กว่า 25 ปีด้าน Network, Linux, Cloud & AI — ผู้ก่อตั้ง SiamCafe.net Since 2000-2026

Q: OPA Gatekeeper คืออะไร

Kubernetes Admission Controller ที่ใช้ OPA เป็น Engine บังคับใช้ Policy บน Cluster ตรวจสอบทุก Resource ก่อนสร้างผ่าน Rego Policy Language

Q: Rego คืออะไรเขียนยากไหม

ภาษา Declarative สำหรับเขียน Policy มี Learning Curve สูงกว่า YAML แต่ทรงพลังกว่ามากใช้ Rego Playground ฝึกได้ฟรี

Q: ConstraintTemplate คืออะไร

CRD ที่กำหนด Template ของ Policy เขียน Rego Logic ไว้ภายในแล้วสร้าง Constraint จาก Template เพื่อบังคับใช้จริงแยก Logic ออกจาก Config ทำให้ Reusable

Q: Gatekeeper ต่างจาก Kyverno อย่างไร

Gatekeeper ใช้ Rego ทำงานได้ทั้งใน/นอก Kubernetes ส่วน Kyverno ใช้ YAML เรียนง่ายกว่าแต่จำกัดเฉพาะ Kubernetes ถ้าต้องการ Policy Engine เดียวใช้ได้ทุกที่เลือก OPA

Q: Gatekeeper มีผลกระทบต่อ Performance ไหม

เพิ่ม Latency ประมาณ 10-50ms ต่อ API Request ควร Monitor Webhook Latency และกำหนด Failure Policy เป็น Fail Open สำหรับ Non-critical Policy

บทความแนะนำ:

อ่านเพิ่มเติม: บทความทั้งหมด | หน้าแรก Blog