Kubernetes-godkendelse med GitHub OAuth og Dex

Jeg præsenterer for din opmærksomhed en vejledning til generering af adgang til en Kubernetes-klynge ved hjælp af Dex, dex-k8s-authenticator og GitHub.

Kubernetes-godkendelse med GitHub OAuth og Dex
Lokal meme fra den russisksprogede Kubernetes chatter ind Telegram

Indledning

Vi bruger Kubernetes til at skabe dynamiske miljøer for udviklingsteamet og QA. Så vi ønsker at give dem adgang til klyngen til både dashboard og kubectl. I modsætning til den samme OpenShift har vanilla Kubernetes ikke indbygget godkendelse, så vi bruger tredjepartsværktøjer til dette.

I denne konfiguration bruger vi:

  • dex-k8s-autenticator  - webapplikation til generering af kubectl config
  • Dex - OpenID Connect udbyder
  • GitHub - simpelthen fordi vi bruger GitHub i vores virksomhed

Vi forsøgte at bruge Google OIDC, men desværre mislykkedes at starte dem med grupper, så integrationen med GitHub passede os fint. Uden gruppekortlægning vil det ikke være muligt at oprette gruppebaserede RBAC-politikker.

Så hvordan fungerer vores Kubernetes-godkendelsesproces i en visuel repræsentation:

Kubernetes-godkendelse med GitHub OAuth og Dex
Autorisationsproces

Lidt flere detaljer og punkt for punkt:

  1. Bruger logger på dex-k8s-authenticator (login.k8s.example.com)
  2. dex-k8s-authenticator omdirigerer anmodningen til Dex (dex.k8s.example.com)
  3. Dex omdirigerer til GitHub-loginsiden
  4. GitHub genererer de nødvendige autorisationsoplysninger og returnerer dem til Dex
  5. Dex videregiver den modtagne information til dex-k8s-authenticator
  6. Brugeren får OIDC-token fra GitHub
  7. dex-k8s-authenticator tilføjer token til kubeconfig
  8. kubectl sender token til KubeAPIServer
  9. KubeAPIServer baseret på det beståede token returnerer adgang til kubectl
  10. Brugeradgange fra kubectl

Forberedende handlinger

Selvfølgelig har vi allerede en Kubernetes-klynge installeret (k8s.example.com), samt HELM forudinstalleret. Vi har også en organisation på GitHub (super-org).
Hvis du ikke har HELM, skal du installere det meget enkel.

Først skal vi konfigurere GitHub.

Gå til siden med organisationsindstillinger, (https://github.com/organizations/super-org/settings/applications) og opret en ny applikation (Authorized OAuth App):
Kubernetes-godkendelse med GitHub OAuth og Dex
Opret en ny app på GitHub

Udfyld felterne med de påkrævede URL'er, for eksempel:

  • Hjemmeside-URL: https://dex.k8s.example.com
  • Autorisationstilbagekalds-URL: https://dex.k8s.example.com/callback

Vær forsigtig med links, det er vigtigt ikke at miste skråstreger.

Som svar på den udfyldte formular vil GitHub generere Client ID и Client secret, gem dem et sikkert sted, de vil være nyttige for os (f.eks. bruger vi Vault for at holde på hemmeligheder):

Client ID: 1ab2c3d4e5f6g7h8
Client secret: 98z76y54x32w1

Forbered DNS-poster for underdomæner login.k8s.example.com и dex.k8s.example.com, samt SSL-certifikater for indtrængen.

Lad os oprette SSL-certifikater:

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

Klyngeudsteder med titel le-clusterissuer burde allerede eksistere, hvis ikke, opret det ved hjælp af 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-konfiguration

For at kubeAPIServer skal fungere, skal du konfigurere OIDC og opgradere klyngen:

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

Vi bruger sparke at udvide klynger, men det fungerer på samme måde for andre klyngeledere.

Dex-konfiguration og dex-k8s-autenticator

For at Dex skal fungere, skal du have et certifikat og en nøgle fra Kubernetes-masteren, vi trækker det ud derfra:

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

Klon dex-k8s-authenticator-depotet:

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

Ved hjælp af værdier-filer kan vi fleksibelt opsætte variabler for vores HELM diagrammer.

Lad os beskrive konfigurationen for 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

Og for dex-k8s-autenticator:

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

Installer Dex og dex-k8s-authenticator:

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

Lad os tjekke servicen af ​​tjenesterne (Dex skal returnere kode 400, og dex-k8s-authenticator skal returnere kode 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 konfiguration

Opret en ClusterRole for gruppen, i vores tilfælde med skrivebeskyttet adgang:

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

Lad os oprette en konfiguration til 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

Nu er vi klar til test.

Tests

Gå til login-sidenhttps://login.k8s.example.com) og log ind med en GitHub-konto:

Kubernetes-godkendelse med GitHub OAuth og Dex
Autorisationsside

Kubernetes-godkendelse med GitHub OAuth og Dex
Autorisationsside omdirigeret til GitHub

Kubernetes-godkendelse med GitHub OAuth og Dex
 Følg de genererede instruktioner for at få adgang

Efter at have kopieret og indsat fra websiden kan vi bruge kubectl til at administrere vores klyngresourcer:

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"

Og det virker, alle GitHub-brugere i vores organisation kan se ressourcer og logge ind på pods, men de har ikke tilladelse til at ændre dem.

Kilde: www.habr.com

Tilføj en kommentar