1. 程式人生 > 其它 >k8s授權管理介紹與實戰(RBAC)

k8s授權管理介紹與實戰(RBAC)

授權管理

授權發生在認證成功之後,通過認證就可以知道請求使用者是誰, 然後Kubernetes會根據事先定義的授權策略來決定使用者是否有許可權訪問,這個過程就稱為授權。

每個傳送到ApiServer的請求都帶上了使用者和資源的資訊:比如傳送請求的使用者、請求的路徑、請求的動作等,授權就是根據這些資訊和授權策略進行比較,如果符合策略,則認為授權通過,否則會返回錯誤。

API Server目前支援以下幾種授權策略:

- AlwaysDeny:表示拒絕所有請求,一般用於測試
- AlwaysAllow:允許接收所有請求,相當於叢集不需要授權流程(Kubernetes預設的策略)
- ABAC:基於屬性的訪問控制,表示使用使用者配置的授權規則對使用者請求進行匹配和控制
- Webhook:通過呼叫外部REST服務對使用者進行授權 - Node:是一種專用模式,用於對kubelet發出的請求進行訪問控制 - RBAC:基於角色的訪問控制(kubeadm安裝方式下的預設選項)
RBAC

RBAC(Role-Based Access Control) 基於角色的訪問控制,主要是在描述一件事情:給哪些物件授予了哪些許可權

其中涉及到了下面幾個概念:

- 物件:User、Groups、ServiceAccount
- 角色:代表著一組定義在資源上的可操作動作(許可權)的集合
- 繫結:將定義好的角色跟使用者繫結在一起

RBAC引入了4個頂級資源物件:

- Role、ClusterRole:角色,用於指定一組許可權
- RoleBinding、ClusterRoleBinding:角色繫結,用於將角色(許可權)賦予給物件
Role、ClusterRole

一個角色就是一組許可權的集合,這裡的許可權都是許可形式的(白名單)。

# Role只能對名稱空間內的資源進行授權,需要指定nameapce

kind: Role
apiVersion: rbac.authorization.k8s.io/v1beta1
metadata:
  namespace: dev
  name: authorization-role
rules:
- apiGroups: [""]  # 支援的API組列表,"" 空字串,表示核心API群
  resources: [
"pods"] # 支援的資源物件列表 verbs: ["get", "watch", "list"] # 允許的對資源物件的操作方法列表

# ClusterRole可以對叢集範圍內資源、跨namespaces的範圍資源、非資源型別進行授權

kind: ClusterRole
apiVersion: rbac.authorization.k8s.io/v1beta1
metadata:
 name: authorization-clusterrole
rules:
- apiGroups: [""]
  resources: ["pods"]
  verbs: ["get", "watch", "list"]

需要詳細說明的是,rules中的引數:

- apiGroups: 支援的API組列表
  " ","apps", "autoscaling", "batch"
  
- resources:支援的資源物件列表
  "services", "endpoints", "pods","secrets","configmaps","crontabs","deployments","jobs",
  "nodes","rolebindings","clusterroles","daemonsets","replicasets","statefulsets",
  "horizontalpodautoscalers","replicationcontrollers","cronjobs"

- verbs:對資源物件的操作方法列表
  "get", "list", "watch", "create", "update", "patch", "delete", "exec"
RoleBinding、ClusterRoleBinding

角色繫結用來把一個角色繫結到一個目標物件上,繫結目標可以是User、Group或者ServiceAccount。

# RoleBinding可以將同一namespace中的subject繫結到某個Role下,則此subject即具有該Role定義的許可權

kind: RoleBinding
apiVersion: rbac.authorization.k8s.io/v1beta1
metadata:
  name: authorization-role-binding
  namespace: dev
subjects:
- kind: User
  name: heima
  apiGroup: rbac.authorization.k8s.io
roleRef:
  kind: Role
  name: authorization-role
  apiGroup: rbac.authorization.k8s.io

# ClusterRoleBinding在整個叢集級別和所有namespaces將特定的subject與ClusterRole繫結,授予許可權

kind: ClusterRoleBinding
apiVersion: rbac.authorization.k8s.io/v1beta1
metadata:
 name: authorization-clusterrole-binding
subjects:
- kind: User
  name: heima
  apiGroup: rbac.authorization.k8s.io
roleRef:
  kind: ClusterRole
  name: authorization-clusterrole
  apiGroup: rbac.authorization.k8s.io
RoleBinding引用ClusterRole進行授權

RoleBinding可以引用ClusterRole,對屬於同一名稱空間內ClusterRole定義的資源主體進行授權。

一種很常用的做法就是,叢集管理員為叢集範圍預定義好一組角色(ClusterRole),然後在多個名稱空間中重複使用這些ClusterRole。

這樣可以大幅提高授權管理工作效率,也使得各個名稱空間下的基礎性授權規則與使用體驗保持一致。

# 雖然authorization-clusterrole是一個叢集角色,但是因為使用了RoleBinding

# 所以heima只能讀取dev名稱空間中的資源

kind: RoleBinding
apiVersion: rbac.authorization.k8s.io/v1beta1
metadata:
  name: authorization-role-binding-ns
  namespace: dev
subjects:
- kind: User
  name: heima
  apiGroup: rbac.authorization.k8s.io
roleRef:
  kind: ClusterRole
  name: authorization-clusterrole
  apiGroup: rbac.authorization.k8s.io

實戰:建立一個只能管理dev空間下Pods資源的賬號

1) 建立賬號

# 1) 建立證書

[root@master pki]# cd /etc/kubernetes/pki/
[root@master pki]# (umask 077;openssl genrsa -out devman.key 2048)

# 2) 用apiserver的證書去簽署

# 2-1) 簽名申請,申請的使用者是devman,組是devgroup
[root@master pki]# openssl req -new -key devman.key -out devman.csr -subj "/CN=devman/O=devgroup"

# 2-2) 簽署證書
[root@master pki]# openssl x509 -req -in devman.csr -CA ca.crt -CAkey ca.key -CAcreateserial -out devman.crt -days 3650

# 3) 設定叢集、使用者、上下文資訊

[root@master pki]# kubectl config set-cluster kubernetes --embed-certs=true --certificate-authority=/etc/kubernetes/pki/ca.crt --server=https://192.168.1.50:6443
[root@master pki]# kubectl config set-credentials devman --embed-certs=true --client-certificate=/etc/kubernetes/pki/devman.crt --client-key=/etc/kubernetes/pki/devman.key
[root@master pki]# kubectl config set-context devman@kubernetes --cluster=kubernetes --user=devman

# 切換賬戶到devman

[root@master pki]# kubectl config use-context devman@kubernetes

# 檢視dev下pod,發現沒有許可權

[root@master pki]# kubectl get pods -n dev

# 切換到admin賬戶

[root@master pki]# kubectl config use-context kubernetes-admin@kubernetes
2) 建立Role和RoleBinding,為devman使用者授權
kind: Role
apiVersion: rbac.authorization.k8s.io/v1beta1
metadata:
  namespace: dev
  name: dev-role
rules:
- apiGroups: [""]
  resources: ["pods"]
  verbs: ["get", "watch", "list"]
  
---

kind: RoleBinding
apiVersion: rbac.authorization.k8s.io/v1beta1
metadata:
  name: authorization-role-binding
  namespace: dev
subjects:
- kind: User
  name: devman
  apiGroup: rbac.authorization.k8s.io
roleRef:
  kind: Role
  name: dev-role
  apiGroup: rbac.authorization.k8s.io


建立
[root@master pki]# kubectl create -f dev-role.yaml
3) 切換賬戶,再次驗證
# 切換賬戶到devman
[root@master pki]# kubectl config use-context devman@kubernetes

# 再次檢視
[root@master pki]# kubectl get pods -n dev

# 為了不影響後面的學習,切回admin賬戶
[root@master pki]# kubectl config use-context kubernetes-admin@kubernetes

參考

黑馬B站k8s課程https://www.bilibili.com/video/BV1Qv41167ck/
https://gitee.com/yooome/golang/blob/main/k8s%E8%AF%A6%E7%BB%86%E6%95%99%E7%A8%8B-%E8%B0%83%E6%95%B4%E7%89%88/k8s%E8%AF%A6%E7%BB%86%E6%95%99%E7%A8%8B.md
https://www.yuque.com/fairy-era/yg511q/xyqxge