مصادقة Kubernetes مع GitHub OAuth و Dex

أقدم انتباهك إلى برنامج تعليمي لتوليد الوصول إلى مجموعة Kubernetes باستخدام Dex و dex-k8s-Authentator و GitHub.

مصادقة Kubernetes مع GitHub OAuth و Dex
الدردشة المحلية من Kubernetes باللغة الروسية تیلیجرام

مقدمة

نستخدم Kubernetes لإنشاء بيئات ديناميكية لفريق التطوير وضمان الجودة. لذلك نريد منحهم حق الوصول إلى الكتلة لكل من لوحة القيادة و kubectl. على عكس OpenShift نفسه ، لا تملك Vanilla Kubernetes مصادقة أصلية ، لذلك نستخدم أدوات الجهات الخارجية لهذا الغرض.

في هذا التكوين نستخدم:

حاولنا استخدام Google OIDC ، لكننا للأسف فشلت لبدء المجموعات ، لذلك كان التكامل مع GitHub مناسبًا لنا تمامًا. بدون تعيين المجموعة ، لن يكون من الممكن إنشاء سياسات RBAC قائمة على المجموعة.

إذن ، كيف تعمل عملية ترخيص Kubernetes في التمثيل المرئي:

مصادقة Kubernetes مع GitHub OAuth و Dex
عملية التفويض

مزيد من التفاصيل ونقطة بنقطة:

  1. يقوم المستخدم بتسجيل الدخول إلى dex-k8s-Authenticator (login.k8s.example.com)
  2. يقوم dex-k8s-Authenticator بإعادة توجيه الطلب إلى Dex (dex.k8s.example.com)
  3. يقوم Dex بإعادة التوجيه إلى صفحة تسجيل الدخول إلى GitHub
  4. ينشئ GitHub معلومات التفويض المطلوبة ويعيدها إلى Dex
  5. يمرر Dex المعلومات المستلمة إلى المصادقة dex-k8s
  6. يحصل المستخدم على رمز OIDC المميز من GitHub
  7. يضيف dex-k8s-Authentator رمزًا مميزًا إلى kubeconfig
  8. kubectl يمرر الرمز المميز إلى KubeAPIServer
  9. KubeAPIServer على أساس الرمز الذي تم تمريره يعيد الوصول إلى kubectl
  10. يصل المستخدم من kubectl

الإجراءات التحضيرية

بالطبع ، لدينا بالفعل مجموعة Kubernetes مثبتة (k8s.example.com) ، وكذلك HELM المثبتة مسبقًا. لدينا أيضًا منظمة على GitHub (super-org).
إذا لم يكن لديك HELM ، فقم بتثبيته بسيطة جدا.

نحتاج أولاً إلى إعداد GitHub.

انتقل إلى صفحة إعدادات المؤسسة ، (https://github.com/organizations/super-org/settings/applications) وأنشئ تطبيقًا جديدًا (تطبيق OAuth المعتمد):
مصادقة Kubernetes مع GitHub OAuth و Dex
أنشئ تطبيقًا جديدًا على GitHub

املأ الحقول بعناوين URL المطلوبة ، على سبيل المثال:

  • رابط الصفحة الرئيسية: https://dex.k8s.example.com
  • عنوان URL لمعاودة الاتصال: https://dex.k8s.example.com/callback

كن حذرًا مع الروابط ، فمن المهم ألا تفقد الشرطة المائلة.

استجابة للنموذج المكتمل ، سيقوم GitHub بإنشاء ملف Client ID и Client secret، احفظها في مكان آمن ، فستكون مفيدة لنا (على سبيل المثال ، نستخدم ملفات قبو لحفظ الأسرار):

Client ID: 1ab2c3d4e5f6g7h8
Client secret: 98z76y54x32w1

قم بإعداد سجلات DNS للنطاقات الفرعية login.k8s.example.com и dex.k8s.example.com، وكذلك شهادات SSL للدخول.

لنقم بإنشاء شهادات SSL:

cat <<EOF | kubectl create -f -
apiVersion: certmanager.k8s.io/v1alpha1
kind: Certificate
metadata:
  name: cert-auth-dex
  namespace: kube-system
spec:
  secretName: cert-auth-dex
  dnsNames:
    - dex.k8s.example.com
  acme:
    config:
    - http01:
        ingressClass: nginx
      domains:
      - dex.k8s.example.com
  issuerRef:
    name: le-clusterissuer
    kind: ClusterIssuer
---
apiVersion: certmanager.k8s.io/v1alpha1
kind: Certificate
metadata:
  name: cert-auth-login
  namespace: kube-system
spec:
  secretName: cert-auth-login
  dnsNames:
    - login.k8s.example.com
  acme:
    config:
    - http01:
        ingressClass: nginx
      domains:
      - login.k8s.example.com
  issuerRef:
    name: le-clusterissuer
    kind: ClusterIssuer
EOF
kubectl describe certificates cert-auth-dex -n kube-system
kubectl describe certificates cert-auth-login -n kube-system

ClusterIser مع العنوان le-clusterissuer يجب أن يكون موجودًا بالفعل ، إذا لم يكن موجودًا ، فقم بإنشائه باستخدام HELM:

helm install --namespace kube-system -n cert-manager stable/cert-manager
cat << EOF | kubectl create -f -
apiVersion: certmanager.k8s.io/v1alpha1
kind: ClusterIssuer
metadata:
  name: le-clusterissuer
  namespace: kube-system
spec:
  acme:
    server: https://acme-v02.api.letsencrypt.org/directory
    email: [email protected]
    privateKeySecretRef:
      name: le-clusterissuer
    http01: {}
EOF

تكوين KubeAPIServer

لكي يعمل kubeAPIServer ، تحتاج إلى تكوين OIDC وترقية المجموعة:

kops edit cluster
...
  kubeAPIServer:
    anonymousAuth: false
    authorizationMode: RBAC
    oidcClientID: dex-k8s-authenticator
    oidcGroupsClaim: groups
    oidcIssuerURL: https://dex.k8s.example.com/
    oidcUsernameClaim: email
kops update cluster --yes
kops rolling-update cluster --yes

نحن نستخدم ركلة لتوسيع المجموعات ، ولكنها تعمل بنفس الطريقة مع مديري المجموعات الأخرى.

تكوين Dex و dex-k8s-Authentator

لكي يعمل Dex ، يجب أن يكون لديك شهادة ومفتاح من خبير Kubernetes ، وسنقوم بسحبه من هناك:

sudo cat /srv/kubernetes/ca.{crt,key}
-----BEGIN CERTIFICATE-----
AAAAAAAAAAABBBBBBBBBBCCCCCC
-----END CERTIFICATE-----
-----BEGIN RSA PRIVATE KEY-----
DDDDDDDDDDDEEEEEEEEEEFFFFFF
-----END RSA PRIVATE KEY-----

استنساخ مستودع المصادقة dex-k8s:

git clone [email protected]:mintel/dex-k8s-authenticator.git
cd dex-k8s-authenticator/

بمساعدة ملفات القيم ، يمكننا إعداد متغيرات بشكل مرن لملفات مخططات هيلم.

دعنا نصف تكوين Dex:

cat << EOF > values-dex.yml
global:
  deployEnv: prod
tls:
  certificate: |-
    -----BEGIN CERTIFICATE-----
    AAAAAAAAAAABBBBBBBBBBCCCCCC
    -----END CERTIFICATE-----
  key: |-
    -----BEGIN RSA PRIVATE KEY-----
    DDDDDDDDDDDEEEEEEEEEEFFFFFF
    -----END RSA PRIVATE KEY-----
ingress:
  enabled: true
  annotations:
    kubernetes.io/ingress.class: nginx
    kubernetes.io/tls-acme: "true"
  path: /
  hosts:
    - dex.k8s.example.com
  tls:
    - secretName: cert-auth-dex
      hosts:
        - dex.k8s.example.com
serviceAccount:
  create: true
  name: dex-auth-sa
config: |
  issuer: https://dex.k8s.example.com/
  storage: # https://github.com/dexidp/dex/issues/798
    type: sqlite3
    config:
      file: /var/dex.db
  web:
    http: 0.0.0.0:5556
  frontend:
    theme: "coreos"
    issuer: "Example Co"
    issuerUrl: "https://example.com"
    logoUrl: https://example.com/images/logo-250x25.png
  expiry:
    signingKeys: "6h"
    idTokens: "24h"
  logger:
    level: debug
    format: json
  oauth2:
    responseTypes: ["code", "token", "id_token"]
    skipApprovalScreen: true
  connectors:
  - type: github
    id: github
    name: GitHub
    config:
      clientID: $GITHUB_CLIENT_ID
      clientSecret: $GITHUB_CLIENT_SECRET
      redirectURI: https://dex.k8s.example.com/callback
      orgs:
      - name: super-org
        teams:
        - team-red
  staticClients:
  - id: dex-k8s-authenticator
    name: dex-k8s-authenticator
    secret: generatedLongRandomPhrase
    redirectURIs:
      - https://login.k8s.example.com/callback/
envSecrets:
  GITHUB_CLIENT_ID: "1ab2c3d4e5f6g7h8"
  GITHUB_CLIENT_SECRET: "98z76y54x32w1"
EOF

وللمصادق dex-k8s:

cat << EOF > values-auth.yml
global:
  deployEnv: prod
dexK8sAuthenticator:
  clusters:
  - name: k8s.example.com
    short_description: "k8s cluster"
    description: "Kubernetes cluster"
    issuer: https://dex.k8s.example.com/
    k8s_master_uri: https://api.k8s.example.com
    client_id: dex-k8s-authenticator
    client_secret: generatedLongRandomPhrase
    redirect_uri: https://login.k8s.example.com/callback/
    k8s_ca_pem: |
      -----BEGIN CERTIFICATE-----
      AAAAAAAAAAABBBBBBBBBBCCCCCC
      -----END CERTIFICATE-----
ingress:
  enabled: true
  annotations:
    kubernetes.io/ingress.class: nginx
    kubernetes.io/tls-acme: "true"
  path: /
  hosts:
    - login.k8s.example.com
  tls:
    - secretName: cert-auth-login
      hosts:
        - login.k8s.example.com
EOF

قم بتثبيت Dex و dex-k8s-Authentator:

helm install -n dex --namespace kube-system --values values-dex.yml charts/dex
helm install -n dex-auth --namespace kube-system --values values-auth.yml charts/dex-k8s-authenticator

دعنا نتحقق من إمكانية خدمة الخدمات (يجب أن يُرجع Dex الرمز 400 ، ويجب أن يُرجع المصادقة dex-k8s الرمز 200):

curl -sI https://dex.k8s.example.com/callback | head -1
HTTP/2 400
curl -sI https://login.k8s.example.com/ | head -1
HTTP/2 200

تكوين RBAC

قم بإنشاء ClusterRole للمجموعة ، في حالتنا مع حق الوصول للقراءة فقط:

cat << EOF | kubectl create -f -
apiVersion: rbac.authorization.k8s.io/v1
kind: ClusterRole
metadata:
  name: cluster-read-all
rules:
  -
    apiGroups:
      - ""
      - apps
      - autoscaling
      - batch
      - extensions
      - policy
      - rbac.authorization.k8s.io
      - storage.k8s.io
    resources:
      - componentstatuses
      - configmaps
      - cronjobs
      - daemonsets
      - deployments
      - events
      - endpoints
      - horizontalpodautoscalers
      - ingress
      - ingresses
      - jobs
      - limitranges
      - namespaces
      - nodes
      - pods
      - pods/log
      - pods/exec
      - persistentvolumes
      - persistentvolumeclaims
      - resourcequotas
      - replicasets
      - replicationcontrollers
      - serviceaccounts
      - services
      - statefulsets
      - storageclasses
      - clusterroles
      - roles
    verbs:
      - get
      - watch
      - list
  - nonResourceURLs: ["*"]
    verbs:
      - get
      - watch
      - list
  - apiGroups: [""]
    resources: ["pods/exec"]
    verbs: ["create"]
EOF

لنقم بإنشاء تكوين لـ ClusterRoleBinding:

cat <<EOF | kubectl create -f -
apiVersion: rbac.authorization.k8s.io/v1beta1
kind: ClusterRoleBinding
metadata:
  name: dex-cluster-auth
  namespace: kube-system
roleRef:
  apiGroup: rbac.authorization.k8s.io
  kind: ClusterRole
  name: cluster-read-all
subjects:
  kind: Group
  name: "super-org:team-red"
EOF

الآن نحن جاهزون للاختبار.

اختبارات

اذهب إلى صفحة تسجيل الدخولhttps://login.k8s.example.com) وقم بتسجيل الدخول باستخدام حساب GitHub:

مصادقة Kubernetes مع GitHub OAuth و Dex
صفحة التفويض

مصادقة Kubernetes مع GitHub OAuth و Dex
تمت إعادة توجيه صفحة التفويض إلى GitHub

مصادقة Kubernetes مع GitHub OAuth و Dex
 اتبع التعليمات التي تم إنشاؤها للوصول

بعد النسخ واللصق من صفحة الويب ، يمكننا استخدام kubectl لإدارة موارد المجموعة الخاصة بنا:

kubectl get po
NAME                READY   STATUS    RESTARTS   AGE
mypod               1/1     Running   0          3d

kubectl delete po mypod
Error from server (Forbidden): pods "mypod" is forbidden: User "[email protected]" cannot delete pods in the namespace "default"

وهو يعمل ، يمكن لجميع مستخدمي GitHub في مؤسستنا رؤية الموارد وتسجيل الدخول إلى البودات ، لكن ليس لديهم إذن بتغييرها.

المصدر: www.habr.com

إضافة تعليق