برنامه نویسی

خدمات مدیریت کلیدی در Kubernetes – قسمت 2

به سری ما در مورد خدمات مدیریت کلیدی (KMS) در Kubernetes خوش آمدید! در قسمت 1 ، ما زمینه را گذاشتیم. اکنون ، در قسمت 2 ، ما در حال غوطه ور شدن به مفهوم مهم رمزگذاری در حالت استراحت هستیم.

رمزگذاری در حالت استراحت دقیقاً چیست؟

به عبارت ساده ، رمزگذاری در حالت استراحت در Kubernetes به نحوه سرور API قبل از ذخیره در ETCD ، داده ها را رمزگذاری می کندبشر به عنوان مغز خوشه Kubernetes خود فکر کنید – این جایی است که تمام داده های پیکربندی خوشه ای شما ، حالت و اسرار زندگی می کنند.

به طور پیش فرض ، سرور API Kubernetes منابع را در ETCD ذخیره می کند متن سادهبشر این بدان معناست که اگر کسی دسترسی غیرمجاز به ETCD شما را بدست آورد ، می تواند تمام داده های حساس شما ، از جمله رازها را بدون هیچ تلاشی بخواند. این یک خطر امنیتی قابل توجه است.

در حالی که رمزگذاری در استراحت مربوط به هر منبع Kubernetes است ، در این سری ، ما همچنان به آن توجه خواهیم کرد اسرار به دلیل ماهیت ذاتی آنها.

خبر خوب این است که Kubernetes راهی برای رمزگذاری این داده ها قبل از بازدید و غیره فراهم می کند. این در درجه اول از طریق --encryption-provider-config استدلال به kube-apiserver فرآیند ، که به یک پرونده پیکربندی اشاره می کند.

معرفی رمزنگاری کنفرانس

در Kubernetes ، رمزگذاری در رفتار استراحت با استفاده از یک EncryptionConfiguration منبع این پیکربندی قدرتمند به شما امکان می دهد تا مشخص کنید که کدام منابع باید رمزگذاری شوند و با استفاده از کدام ارائه دهندگان رمزگذاری.

بیایید برای درک ساختار آن به یک پیکربندی مثال نگاه کنیم:

# CAUTION: This is an example configuration and should NOT be used for production clusters without careful consideration.
apiVersion: apiserver.config.k8s.io/v1
kind: EncryptionConfiguration
resources:
  - resources:
      - secrets
      - configmaps
      - pandas.awesome.bears.example # An example custom resource API
    providers:
      # The 'identity' provider stores resources as plain text (no encryption).
      # If listed first, it means data is NOT encrypted.
      - identity: {}
      - aesgcm:
          keys:
            - name: key1
              secret: c2VjcmV0IGlzIHNlY3VyZQ== # Base64 encoded key
            - name: key2
              secret: dGhpcyBpcyBwYXNzd29yZA== # Base64 encoded key
      - aescbc:
          keys:
            - name: key1
              secret: c2VjcmV0IGlzIHNlY3VyZQ== # Base64 encoded key
            - name: key2
              secret: dGhpcyBpcyBwYXNzd29yZA== # Base64 encoded key
      - secretbox:
          keys:
            - name: key1
              secret: YWJjZGVmZ2hpamtsbW5vcHFyc3R1dnd4eXoxMjM0NTY= # Base64 encoded key
  - resources:
      - events
    providers:
      - identity: {} # Do not encrypt Events
  - resources:
      - '*.apps' # Wildcard match (Kubernetes 1.27+)
    providers:
      - aescbc:
          keys:
          - name: key2
            secret: c2VjcmV0IGlzIHNlY3VyZSwgb3IgaXMgYXQ/Cg==
  - resources:
      - '*.*' # Wildcard match (Kubernetes 1.27+)
    providers:
      - aescbc:
          keys:
          - name: key3
            secret: c2VjcmV0IGlzIHNlY3VyZSwgSSB0aGluaw==
حالت تمام صفحه را وارد کنید

از حالت تمام صفحه خارج شوید

غذای اصلی از EncryptionConfiguration:

  • resources: این آرایه مشخص می کند که از منابع Kubernetes می خواهید رمزگذاری را برای آن استفاده کنید. شما می توانید منابع خاص را هدف قرار دهید (به عنوان مثال ، secrets) ، یا از مسابقات Wildcard استفاده کنید (به عنوان مثال ، '*.apps'با '*.*') موجود در Kubernetes 1.27 و بعد.

  • providers: این یک لیست سفارش داده شده از ارائه دهندگان رمزگذاری است. Kubernetes سعی در استفاده از اولین ارائه دهنده در لیست برای رمزگذاری داده های جدید دارد. هنگام رمزگشایی ، ارائه دهندگان را به ترتیب تلاش می کند تا یک نفر موفق شود.

  • identity: {}: این ارائه دهنده معنی دارد بدون رمزگذاری؛ داده ها در متن ساده ذخیره می شوند. اگر این اولین ارائه دهنده یک منبع باشد ، به این معنی است که داده های جدید برای آن منبع رمزگذاری نمی شوند.

  • aesgcm, aescbc, secretbox: اینها الگوریتم های رمزگذاری متفاوت هستند. شما کلیدهای نامگذاری شده را تعریف می کنید (base64 رمزگذاری شده) برای هر یک.

نسخه ی نمایشی: رمزگذاری اسرار در Minikube

بیایید با استفاده از یک خوشه minikube برای دیدن رمزگذاری در حالت استراحت در یک نمونه عملی قدم بزنیم.

1. خوشه minikube خود را شروع کنید:
اطمینان حاصل کنید که خوشه Minikube شما در حال اجرا است.

2. ایجاد کنید EncryptionConfiguration پرونده:
یک پرونده به نام ایجاد کنید encryption-conf.yaml با محتوای زیر:

apiVersion: apiserver.config.k8s.io/v1
kind: EncryptionConfiguration
resources:
  - resources:
      - secrets # We are only encrypting secrets for this demo
    providers:
      - aescbc: # Using AES-CBC encryption
          keys:
            - name: key1
              # IMPORTANT: This is a randomly generated key.
              # Use a strong, unique, and base64-encoded key in production.
              secret: lvAp17Ae2o/yTdxz2qyC6zjVzuS+sBdhkwCccgsSsUg=
      - identity: {} # Fallback to identity (plaintext) if AES-CBC fails, or for older data
حالت تمام صفحه را وارد کنید

از حالت تمام صفحه خارج شوید

درک پیکربندی نسخه ی نمایشی:

  • ما به طور خاص هدف قرار می دهیم secrets برای رمزگذاری

  • ما در حال استفاده از aescbc ارائه دهنده با یک کلید واحد به نام Key1. به یاد داشته باشید که از یک کلید واقعاً تصادفی و قوی برای محیط های تولید استفاده کنید! در secret مقدار باید Base64 رمزگذاری شود.

  • در identity: {} ارائه دهنده به عنوان یک برگشتی گنجانده شده است. این برای چرخش صاف و رمزگشایی داده های قدیمی بسیار مهم است ، یا اگر ارائه دهنده رمزگذاری اولیه با یک مسئله روبرو شود.

3. سرور API را پیکربندی کنید تا از پیکربندی رمزگذاری استفاده کنید:
اکنون ، ما باید بگوییم kube-apiserver برای استفاده از این پرونده پیکربندی. در Minikube ، می توانید با اصلاح تعریف POD سرور API به این هدف برسید.

اول ، پیدا کردن kube-apiserver تعریف POD (معمولاً در آن است /etc/kubernetes/manifests/ در گره هواپیمای کنترل).

بعد ، شما باید اصلاح کنید kube-apiserver مانیفست غلاف استاتیک شامل موارد --encryption-provider-config استدلال کنید و دایرکتوری حاوی خود را سوار کنید encryption-conf.yaml پرونده

در اینجا مثالی از چگونگی kube-apiserver قطعه مانیفست غلاف به دنبال اصلاح است:

apiVersion: v1
kind: Pod
metadata:
  labels:
    component: kube-apiserver
    tier: control-plane
  name: kube-apiserver
  namespace: kube-system
spec:
  containers:
  - command:
    - kube-apiserver
    # ... other kube-apiserver arguments
    - --encryption-provider-config=/etc/kubernetes/enc/encryption-conf.yaml # <--- Add this line
    volumeMounts:
    - mountPath: /etc/kubernetes/enc # <--- Mount path for your config file
      name: enc-vol
      readOnly: true
    # ... other volume mounts
  volumes:
  - hostPath:
      path: /etc/kubernetes/encryption # <--- Host path where your config file lives
      type: DirectoryOrCreate
    name: enc-vol
  # ... other volumes
حالت تمام صفحه را وارد کنید

از حالت تمام صفحه خارج شوید

مهم: شما باید خود را قرار دهید encryption-conf.yaml پرونده در /etc/kubernetes/encryption دایرکتوری در Minikube VM (یا گره کنترل هواپیمای کنترل برای یک خوشه کامل) برای hostPath میزان صدا برای کار صحیح.

پس از صرفه جویی در تغییرات ، kube-apiserver POD با استفاده از پیکربندی رمزگذاری جدید ، به طور خودکار مجدداً راه اندازی می شود.

4. ایجاد یک راز:
بیایید یک راز جدید در یک فضای نام آزمایش ایجاد کنیم:

kubectl create namespace test
kubectl -n=test create secret generic new-secret --from-literal=key1=supersecret
حالت تمام صفحه را وارد کنید

از حالت تمام صفحه خارج شوید

5. راز را بازیابی کنید (همانطور که توسط kubectl):
حال ، بیایید راز را با استفاده از kubectl:

kubectl get secret new-secret -o yaml -n test
حالت تمام صفحه را وارد کنید

از حالت تمام صفحه خارج شوید

خروجی مشابه این را دریافت خواهید کرد:

apiVersion: v1
data:
  key1: c3VwZXJzZWNyZXQ= # Still base64 encoded!
kind: Secret
metadata:
  creationTimestamp: "2025-05-31T10:50:26Z"
  name: new-secret
  namespace: test
  resourceVersion: "6614"
  uid: a8655bde-be5f-4624-b905-61524de56ebe
type: Opaque
حالت تمام صفحه را وارد کنید

از حالت تمام صفحه خارج شوید

توجه کنید که data زمینه هنوز نشان می دهد مقدار رمزگذاری شده BASE64بشر این بسیار مهم است: kubectl همیشه اسرار را به شکل رمزگذاری شده Base64 خود نشان می دهد. این خروجی به ما نمی گوید که آیا راز در حالت استراحت در ETCD رمزگذاری شده است یا خیر.

6. رمزگذاری در ETCD را تأیید کنید:
اینجاست که جادو اتفاق می افتد! ما مستقیماً بازرسی خواهیم کرد که راز در ETCD ذخیره می شود.
ابتدا ، به etcd-minikube غلاف:

kubectl -n=kube-system exec -it etcd-minikube -- sh
حالت تمام صفحه را وارد کنید

از حالت تمام صفحه خارج شوید

سپس ، استفاده کنید etcdctl برای بازیابی مقدار خام راز از ETC:

ETCDCTL_API=3 etcdctl --cacert /var/lib/minikube/certs/etcd/ca.crt --cert /var/lib/minikube/certs/etcd/server.crt --key /var/lib/minikube/certs/etcd/server.key get /registry/secrets/test/new-secret
حالت تمام صفحه را وارد کنید

از حالت تمام صفحه خارج شوید

خروجی را مشاهده خواهید کرد که چیزی شبیه به این است:

/registry/secrets/test/new-secret
k8s:enc:aescbc:v1:key1:??|??
حالت تمام صفحه را وارد کنید

از حالت تمام صفحه خارج شوید

این تفاوت کلیدی است!

  • بدون EncryptionConfiguration، داده های موجود در ETCD به راحتی قابل خواندن خواهد بود.

  • با EncryptionConfiguration کاربردی ، یک رشته رشته غیرقابل خواندن و زباله را با آن مشاهده می کنید k8s:enc:aescbc:v1:key1:بشر

این پیشوند به شما می گوید:

  • k8s:enc: این داده ها توسط Kubernetes رمزگذاری شده است.
  • aescbc: الگوریتم رمزگذاری مورد استفاده AES-CBC است.
  • v1: نسخه طرح رمزگذاری.
  • key1: کلید خاص (Key1 از ما EncryptionConfiguration) که برای رمزگذاری استفاده شده است.

این تأیید می کند که راز شما اکنون است رمزگذاری شده در استراحت در ETCD!

نوشته های مشابه

دیدگاهتان را بنویسید

نشانی ایمیل شما منتشر نخواهد شد. بخش‌های موردنیاز علامت‌گذاری شده‌اند *

دکمه بازگشت به بالا