Kubernetes 的用法和解析 -- 3

一.Secret 实现
1.1 secret  详解

secret用来保存小片敏感数据的k8s资源,例如密码,token,或者秘钥。这类数据当然也可以存放在Pod或者镜像中,但是放在Secret中是为了更方便的控制如何使用数据,并减少暴露的风险。
 
 用户可以创建自己的secret,系统也会有自己的secret。
 Pod需要先引用才能使用某个secret

Pod使用secret方式:

 作为volume的一个域被一个或多个容器挂载 

內建的Secrets:

由ServiceAccount创建的API证书附加的秘钥k8s自动生成的用来访问apiserver的Secret,所有Pod会默认使用这个Secret与apiserver通信  

创建自己的Secret:

 方式1:使用kubectl create secret命令
方式2:yaml文件创建Secret 

1.2 secret 使用

创建Secret

假如某个Pod要访问数据库,需要用户名密码,现在我们分别设置这个用户名和密码 Secret 对象要求这些数据必须是经过 Base64 转码的,以免出现明文密码显示的安全隐患。

# 创建一个secret.yaml文件,内容用base64编码:明文显示容易被别人发现,这里先转码。
[root@kub-k8s-master ~]# echo -n 'admin' | base64
YWRtaW4=
[root@kub-k8s-master ~]# echo -n '1f2d1e2e67df' | base64
MWYyZDFlMmU2N2Rm

创建一个secret.yaml文件,内容用base64编码

[root@kub-k8s-master prome]# vim secret.yml
---
apiVersion: v1
kind: Secret
metadata:name: mysecret
type: Opaque  #模糊
data:username: YWRtaW4=password: MWYyZDFlMmU2N2Rm

创建:

[root@kub-k8s-master prome]# kubectl apply -f secret.yml 
secret/mysecret created

解析Secret中内容,还是经过编码的---需要解码

# 查看secret
[root@kub-k8s-master ~]# kubectl get secrets
NAME                  TYPE                                  DATA   AGE
default-token-7vc82   kubernetes.io/service-account-token   3      30h
mysecret              Opaque                                2      6s# 查看secret详细信息
[root@kub-k8s-master prome]# kubectl get secret mysecret -o yaml
apiVersion: v1
data:password: MWYyZDFlMmU2N2Rmusername: YWRtaW4=
kind: Secret
metadata:creationTimestamp: "2023-10-21T03:07:56Z"name: mysecretnamespace: defaultresourceVersion: "162855"selfLink: /api/v1/namespaces/default/secrets/mysecretuid: 36bcd07d-92eb-4755-ac0a-a5843ed986dd
type: Opaque

手动base64解码方式:

[root@kub-k8s-master ~]# echo 'MWYyZDFlMmU2N2Rm' | base64 --decode

1.3 使用Secret 

secret可以作为数据卷挂载或者作为环境变量暴露给Pod中的容器使用,也可以被系统中的其他资源使用。 

一个Pod中引用Secret的列子:

创建一个Secret,多个Pod可以引用同一个Secret

修改Pod的定义,在spec.volumes[]加一个volume,给这个volume起个名字,spec.volumes[].secret.secretName记录的是要引用的Secret名字

[root@kub-k8s-master prome]# vim pod_use_secret.yaml
apiVersion: v1
kind: Pod
metadata:name: mypod
spec:containers:- name: testredisimage: daocloud.io/library/redisvolumeMounts:    #挂载一个卷- name: foo     #这个名字需要与定义的卷的名字一致mountPath: "/etc/foo"  #挂载到容器里哪个目录下,随便写readOnly: truevolumes:     #数据卷的定义- name: foo   #卷的名字这个名字自定义secret:    #卷是直接使用的secret。secretName: mysecret   #调用刚才定义的secret创建:
[root@kub-k8s-master prome]# kubectl apply -f pod_use_secret.yaml 
pod/mypod created
[root@kub-k8s-master prome]# kubectl exec -it mypod /bin/bash
root@mypod:/data# cd /etc/foo/
root@mypod:/etc/foo# ls
password  username
root@mypod:/etc/foo# cat password 
1f2d1e2e67df

结果中看到,保存在 Etcd 里的用户名和密码信息,已经以文件的形式出现在了容器的 Volume 目录里。
而这个文件的名字,就是 kubectl create secret 指定的 Key,或者说是 Secret 对象的 data 字段指定的 Key。

每一个被引用的Secret都要在spec.volumes中定义
 如果Pod中的多个容器都要引用这个Secret那么每一个容器定义中都要指定自己的volumeMounts,但是Pod定义中声明一次spec.volumes就好了。 

映射secret key到指定的路径

可以控制secret key被映射到容器内的路径,利用spec.volumes[].secret.items来修改被映射的具体路径

[root@kub-k8s-master prome]# kubectl delete -f pod_use_secret.yaml 
pod "mypod" deleted
[root@kub-k8s-master prome]# vim pod_use_secret.yaml
---
apiVersion: v1
kind: Pod
metadata:name: mypod
spec:containers:- name: testredisimage: daocloud.io/library/redisvolumeMounts:- name: foomountPath: "/etc/foo"readOnly: truevolumes:- name: foosecret:secretName: mysecretitems:   #定义一个items- key: username   #将那个key重新定义到那个目录下path: my-group/my-username  #相对路径,相对于/etc/foo的路径2.创建
[root@kub-k8s-master prome]# kubectl apply -f pod_use_secret.yaml 
pod/mypod created
3.从volume中读取secret的值
[root@kub-k8s-master prome]# kubectl exec -it mypod /bin/bash                         
root@mypod:/data# cd /etc/foo/my-group
root@mypod:/etc/foo/my-group# ls
my-username
root@mypod:/etc/foo/my-group# cat my-username 
admin
root@mypod:/etc/foo/my-group#

username被映射到了文件/etc/foo/my-group/my-username而不是/etc/foo/username,而password没有被使用,这种方式每个key的调用需要单独用key像username一样调用

被挂载的secret内容自动更新

也就是如果修改一个Secret的内容,那么挂载了该Secret的容器中也将会取到更新后的值,但是这个时间间隔是由kubelet的同步时间决定的。

1.设置base64加密
[root@kub-k8s-master prome]# echo mahong | base64
bWFob25n
2.将admin替换成mahong
[root@kub-k8s-master prome]# vim secret.yml
---
apiVersion: v1
kind: Secret
metadata:name: mysecret
type: Opaque
data:username: bWFob25n   #修改为mahong的base64加密后的password: MWYyZDFlMmU2N2Rm1.创建
[root@kub-k8s-master prome]# kubectl apply -f secret.yml 
Warning: kubectl apply should be used on resource created by either kubectl create --save-config or kubectl apply
secret/mysecret configured
2.连接pod容器
[root@kub-k8s-master prome]# kubectl exec -it mypod /bin/bash
root@mypod:/data# cd /etc/foo/my-group
root@mypod:/etc/foo/my-group# ls
my-username
root@mypod:/etc/foo/my-group# cat my-username 
mahong

  以环境变量的形式使用Secret

[root@kub-k8s-master prome]# kubectl delete -f pod_use_secret.yaml 
pod "mypod" deleted
[root@kub-k8s-master prome]# vim pod_use_secret.yaml
---
apiVersion: v1
kind: Pod
metadata:name: mypod
spec:containers:- name: testredisimage: daocloud.io/library/redisenv:  #定义环境变量- name: SECRET_USERNAME   #创建新的环境变量名称valueFrom:secretKeyRef:     #调用的key是什么name: mysecret       #变量的值来自于mysecretkey: username       #username里面的值2.创建使用secret的pod容器
[root@kub-k8s-master prome]# kubectl apply -f pod_use_secret.yaml 
pod/mypod created
3.连接
[root@kub-k8s-master prome]# kubectl exec -it mypod /bin/bash 
root@mypod:/data# echo $SECRET_USERNAME   #打印一下定义的变量
mahong

 1.4 实战案例

1.创建数据库用户的密码secret
[root@kub-k8s-master test]# echo -n 'Mawenbao@123' | base64
TWF3ZW5iYW9AMTIz
[root@kub-k8s-master test]# cat secret.yml 
apiVersion: v1
kind: Secret
metadata:name: mysql-secret
type: Opaque
data:password: TWF3ZW5iYW9AMTIz[root@kub-k8s-master test]# kubectl apply -f secret.yml2.创建数据库并使用secret
[root@kub-k8s-master test]# cat mysql.yaml 
apiVersion: v1
kind: Pod
metadata:name: my-mysql
spec:containers:- name: mysqlimage: daocloud.io/library/mysql:5.7ports:- containerPort: 3306env:- name: MYSQL_ROOT_PASSWORDvalueFrom:secretKeyRef:name: mysql-secretkey: password
[root@kub-k8s-master test]# kubectl apply -f myslq.yaml
[root@kub-k8s-master test]# kubectl get pod -o wide 
NAME       READY   STATUS    RESTARTS   AGE     IP            NODE    NOMINATED NODE   READINESS GATES
my-mysql   1/1     Running   0          2m47s   10.244.2.13   node2   <none>           <none>测试:
[root@kub-k8s-master test]# mysql -uroot -p'Mawenbao@123' -h 10.244.2.13 -P3306

二.ConfigMap详解 

ConfigMap与 Secret 类似,用来存储配置文件的kubernetes资源对象,所有的配置内容都存储在etcd中。

 与 Secret 的区别:

ConfigMap 保存的是不需要加密的、应用所需的配置信息。

ConfigMap 的用法几乎与 Secret 完全相同:可以使用 kubectl create configmap 从文件或者目录创建 ConfigMap,也可以直接编写 ConfigMap 对象的 YAML 文件。

2.1 创建ConfigMap的方式 

创建ConfigMap的方式有4种:

命令行方式
方式1:通过直接在命令行中指定configmap参数创建,即--from-literal
方式2:通过指定文件创建,即将一个配置文件创建为一个ConfigMap,--from-file=<文件>
方式3:通过指定目录创建,即将一个目录下的所有配置文件创建为一个ConfigMap,--from-file=<目录>
配置文件方式
方式4:事先写好标准的configmap的yaml文件,然后kubectl create -f 创建

 

2.2 通过命令行参数创建

创建命令:

[root@kub-k8s-master prome]# kubectl create configmap test-configmap --from-literal=user=admin --from-literal=pass=1122334
configmap/test-configmap created

 结果如下面的data内容所示:

[root@kub-k8s-master prome]# kubectl get configmap test-configmap -o yaml
apiVersion: v1
data:pass: "1122334"user: admin
kind: ConfigMap
metadata:creationTimestamp: "2019-10-21T07:48:15Z"name: test-configmapnamespace: defaultresourceVersion: "187590"selfLink: /api/v1/namespaces/default/configmaps/test-configmapuid: 62a8a0d0-fab9-4159-86f4-a06aa213f4b1
2.3 通过指定文件创建

编辑文件server.conf内容如下:

[root@kub-k8s-master prome]# vim server.conf
server {
listen 80;
server_name localhost;
location / {
root /var/www/html;
index index.html index.htm;
}
}

创建(可以有多个--from-file):

[root@kub-k8s-master prome]# kubectl create configmap test-config2 --from-file=server.conf
configmap/test-config2 created

结果如下面data内容所示:

[root@kub-k8s-master prome]# kubectl get configmap test-config2 -o yaml
apiVersion: v1
data:server.conf: |server {listen 80;server_name localhost;localtion / {root /var/www/html;index index.html index.htm;}}
kind: ConfigMap
metadata:creationTimestamp: "2023-10-21T08:01:43Z"name: test-config2namespace: defaultresourceVersion: "188765"selfLink: /api/v1/namespaces/default/configmaps/test-config2uid: 790fca12-3900-4bf3-a017-5af1070792e5

通过指定文件创建时,configmap会创建一个key/value对,key是文件名,value是文件内容。

2.4 指定目录创建

configs 目录下的config-1和config-2内容如下所示:

[root@kub-k8s-master prome]# mkdir config
[root@kub-k8s-master prome]# cd config/
[root@kub-k8s-master config]# vim config1
aaa
bbb
c=d
[root@kub-k8s-master config]# vim config2
eee
fff
h=k

 创建:

[root@kub-k8s-master config]# cd ..
[root@kub-k8s-master prome]# kubectl create configmap test-config3 --from-file=./config
configmap/test-config3 created

 结果下面data内容所示:

[root@kub-k8s-master prome]# kubectl get configmap test-config3 -o yaml
apiVersion: v1
data:config1: |aaabbbc=dconfig2: |eeefffh=k
kind: ConfigMap
metadata:creationTimestamp: "2023-10-21T08:20:42Z"name: test-config3namespace: defaultresourceVersion: "190420"selfLink: /api/v1/namespaces/default/configmaps/test-config3uid: 6e00fded-80a8-4297-aeb3-4c48795e6eb9

指定目录创建时,configmap内容中的各个文件会创建一个key/value对,key是文件名,value是文件内容。

2.5 通过yaml文件创建

yaml文件内容如下: 注意其中一个key的value有多行内容时的写法

[root@kub-k8s-master prome]# vim configmap.yaml
---
apiVersion: v1
kind: ConfigMap
metadata:name: test-config4namespace: default
data:cache_host: memcached-gcxtcache_port: "11211"cache_prefix: gcxtmy.cnf: |[mysqld]log-bin = mysql-binhaha = hehe

 创建:

[root@kub-k8s-master prome]# kubectl apply -f configmap.yaml 
configmap/test-config4 created

 结果如下面data内容所示:

[root@kub-k8s-master prome]# kubectl get configmap test-config4 -o yaml
apiVersion: v1
data:cache_host: memcached-gcxtcache_port: "11211"cache_prefix: gcxtmy.cnf: |[mysqld]log-bin = mysql-binhaha = hehe
kind: ConfigMap
metadata:annotations:kubectl.kubernetes.io/last-applied-configuration: |{"apiVersion":"v1","data":{"cache_host":"memcached-gcxt","cache_port":"11211","cache_prefix":"gcxt","my.cnf":"[mysqld]\nlog-bin = mysql-bin\nhaha = hehe\n"},"kind":"ConfigMap","metadata":{"annotations":{},"name":"test-config4","namespace":"default"}}creationTimestamp: "2023-10-21T08:30:24Z"name: test-config4namespace: defaultresourceVersion: "191270"selfLink: /api/v1/namespaces/default/configmaps/test-config4uid: 2a8cd6e7-db2c-4781-b005-e0b76d26394b

 查看configmap的详细信息:

# kubectl describe configmap

2.6 使用ConfigMap 

使用ConfigMap的方式,一种是通过环境变量的方式,直接传递pod,另一种是使用volume的方式挂载入到pod内

示例ConfigMap文件:

[root@kub-k8s-master prome]# vim config-map.yml
---
apiVersion: v1
kind: ConfigMap
metadata:name: config-mapnamespace: default
data:special.how: veryspecial.type: charm  创建  
[root@kub-k8s-master prome]# kubectl apply -f config-map.yml 
configmap/config-map created
2.6.1 通过变量使用

(1) 使用valueFrom、configMapKeyRef、name、key指定要用的key:

1.设置指定变量的方式
[root@kub-k8s-master prome]# vim testpod.yml
---
apiVersion: v1
kind: Pod
metadata:name: dapi-test-pod
spec:containers:- name: test-containerimage: daocloud.io/library/nginxenv:   #专门在容器里面设置变量的关键字- name: SPECIAL_LEVEL_KEY   #这里的-name,是容器里设置的新变量的名字valueFrom:configMapKeyRef:name: config-map   #这里是来源于哪个configMapkey: special.how      #configMap里的key- name: SPECIAL_TYPE_KEYvalueFrom:configMapKeyRef:name: config-mapkey: special.typerestartPolicy: Never创建pod
[root@kub-k8s-master prome]# kubectl apply -f testpod.yml 
pod/dapi-test-pod created

测试:

[root@kub-k8s-master prome]# kubectl exec -it dapi-test-pod /bin/bash
root@dapi-test-pod:/# echo $SPECIAL_TYPE_KEY
charm

(2) 通过envFrom、configMapRef、name使得configmap中的所有key/value对儿  都自动变成环境变量:

[root@kub-k8s-master prome]# kubectl delete -f testpod.yml 
pod "dapi-test-pod" deleted
[root@kub-k8s-master prome]# cp testpod.yml testpod.yml.bak
[root@kub-k8s-master prome]# vim testpod.yml
---
apiVersion: v1
kind: Pod
metadata:name: dapi-test-pod
spec:containers:- name: test-containerimage: daocloud.io/library/nginxenvFrom:- configMapRef:name: config-maprestartPolicy: Never

 这样容器里的变量名称直接使用configMap里的key名:

[root@kub-k8s-master prome]# kubectl apply -f testpod.yml
pod/dapi-test-pod created.
[root@kub-k8s-master prome]# kubectl exec -it dapi-test-pod /bin/bash
root@dapi-test-pod:/# env
HOSTNAME=dapi-test-pod
NJS_VERSION=0.3.3
NGINX_VERSION=1.17.1
KUBERNETES_PORT_443_TCP_PROTO=tcp
KUBERNETES_PORT_443_TCP_ADDR=10.96.0.1
PKG_RELEASE=1~stretch
KUBERNETES_PORT=tcp://10.96.0.1:443
PWD=/
special.how=very
HOME=/root
KUBERNETES_SERVICE_PORT_HTTPS=443
KUBERNETES_PORT_443_TCP_PORT=443
KUBERNETES_PORT_443_TCP=tcp://10.96.0.1:443
TERM=xterm
SHLVL=1
KUBERNETES_SERVICE_PORT=443
PATH=/usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin:/sbin:/bin
special.type=charm
KUBERNETES_SERVICE_HOST=10.96.0.1
_=/usr/bin/env
2.6.2 作为volume挂载使用

(1) 把1.4中test-config4所有key/value挂载进来:

[root@kub-k8s-master prome]# kubectl delete -f testpod.yml
pod "dapi-test-pod" deleted
[root@kub-k8s-master prome]# vim volupod.yml
---
apiVersion: v1
kind: Pod
metadata:name: nginx-configmap
spec:containers:- name: nginx-configmapimage: daocloud.io/library/nginxvolumeMounts:- name: config-volume4mountPath: "/tmp/config4"volumes:- name: config-volume4configMap:name: test-config4创建pod
[root@kub-k8s-master prome]# kubectl apply -f volupod.yml 
pod/nginx-configmap created

进入容器中/tmp/config4查看:

[root@kub-k8s-master prome]#  kubectl  exec -it nginx-configmap /bin/bash
root@nginx-configmap:/# ls /tmp/config4/
cache_host  cache_port	cache_prefix  my.cnf
root@nginx-configmap:/# cat /tmp/config4/cache_host 
memcached-gcxt
root@nginx-configmap:/#

可以看到,在config4文件夹下以每一个key为文件名,value为内容,创建了多个文件。

2.7 实战案例 

创建configmap
[root@kub-k8s-master configmap]# vim configmap.yaml
---
apiVersion: v1
kind: ConfigMap
metadata:name: nginx-server-confnamespace: default
data:index.html: |Hello, cloud computingHello, Mr. Wang[root@kub-k8s-master configmap]# kubectl apply -f configmap.yaml[root@kub-k8s-master configmap]# kubectl get configmap
NAME                DATA   AGE
nginx-server-conf   2      7s
[root@kub-k8s-master configmap]# kubectl get configmap nginx-server-conf -o yaml使用configmap
[root@kub-k8s-master configmap]# vim pod.yaml
---
apiVersion: v1
kind: Pod
metadata:name: test-webapp
spec:containers:- name: nginx-appimage: daocloud.io/library/nginxports:- containerPort: 80volumeMounts:- name: nginx-volumemountPath: "/usr/share/nginx/html"volumes:- name: nginx-volumeconfigMap:name: nginx-server-conf
[root@kub-k8s-master configmap]# kubectl apply -f pod.yaml
[root@kub-k8s-master configmap]# kubectl get pod 
NAME          READY   STATUS    RESTARTS   AGE
test-webapp   1/1     Running   0          6s
[root@kub-k8s-master configmap]# kubectl exec -it test-webapp /bin/bash
root@test-webapp:/# cd /usr/share/nginx/html/
root@test-webapp:/usr/share/nginx/html# ls
index.html
root@test-webapp:/usr/share/nginx/html# cat index.html 
Hello, cloud computing
Hello, Mr. Wang[root@kub-k8s-master configmap]# curl 10.244.2.25
Hello, cloud computing
Hello, Mr. Wang

三.Downward API 

Downward API
用于在容器中获取 POD 的基本信息,kubernetes原生支持

Downward API提供了两种方式用于将 POD 的信息注入到容器内部:
1.环境变量:用于单个变量,可以将 POD 信息直接注入容器内部。
2.Volume挂载:将 POD 信息生成为文件,直接挂载到容器内部中去。

3.1 目前 Downward API 支持的字段 

1. 使用 fieldRef 可以声明使用:
spec.nodeName - 宿主机名字
status.hostIP - 宿主机 IP
metadata.name - Pod 的名字
metadata.namespace - Pod 的 Namespace
status.podIP - Pod 的 IP
spec.serviceAccountName - Pod 的 Service Account 的名字
metadata.uid - Pod 的 UID
metadata.labels['<KEY>'] - 指定 <KEY> 的 Label 值
metadata.annotations['<KEY>'] - 指定 <KEY> 的 Annotation 值
metadata.labels - Pod 的所有 Label
metadata.annotations - Pod 的所有 Annotation

上面这个列表的内容,随着 Kubernetes 项目的发展肯定还会不断增加。所以这里列出来的信息仅供参考,在使用 Downward API 时,还是要记得去查阅一下官方文档。

# 所有基本信息可以使用下面的方式去查看(describe方式看不出来):
[root@kub-k8s-master configmap]# kubectl  get pod test-webapp -o yaml
apiVersion: v1
kind: Pod
metadata:annotations:kubectl.kubernetes.io/last-applied-configuration: |{"apiVersion":"v1","kind":"Pod","metadata":{"annotations":{},"name":"test-webapp","namespace":"default"},"spec":{"containers":[{"image":"daocloud.io/library/nginx","name":"nginx-app","volumeMounts":[{"mountPath":"/usr/share/nginx/html","name":"nginx-volume"}]}],"volumes":[{"configMap":{"name":"nginx-server-conf"},"name":"nginx-volume"}]}}creationTimestamp: "2021-02-21T09:44:51Z"name: test-webappnamespace: defaultresourceVersion: "270687"selfLink: /api/v1/namespaces/default/pods/test-webappuid: ed92d685-f800-464f-95dc-d6aa5f92fc9c
......
3.2 实战案例

使用fieldRef获取 POD 的基本信息,以环境变量的方式实现

[root@kub-k8s-master prome]# vim test-env-pod.yml
---
apiVersion: v1
kind: Pod
metadata:name: test-env-podnamespace: kube-system
spec:containers:- name: test-env-podimage: daocloud.io/library/nginxenv:- name: POD_NAME   #第一个环境变量的名字valueFrom:      #使用valueFrom方式设置fieldRef:    #关联一个字段metadata.namefieldPath: metadata.name  #这个字段从当前运行的pod详细信息查看- name: POD_NAMESPACEvalueFrom:fieldRef:fieldPath: metadata.namespace- name: POD_IPvalueFrom:fieldRef:fieldPath: status.podIP

注意: POD 的 name 和 namespace 属于元数据,是在 POD 创建之前就已经定下来了的,所以使用 metadata 获取就可以了,但是对于 POD 的 IP 则不一样,因为POD IP 是不固定的,POD 重建了就变了,它属于状态数据,所以使用 status 去获取。 

创建上面的 POD:

[root@kub-k8s-master prome]#  kubectl apply -f test-env-pod.yml
pod/test-env-pod created

POD 创建成功后,查看:

[root@kub-k8s-master prome]# kubectl exec -it test-env-pod /bin/bash -n kube-system
root@test-env-pod:/# env | grep POD
POD_NAME=test-env-pod
POD_NAMESPACE=kube-system
POD_IP=10.244.1.35
root@test-env-pod:/#

Volume挂载

通过Downward API将 POD 的 Label、等信息通过 Volume 以文件的形式挂载到容器的某个文件中去,然后在容器中打印出该文件的值来验证。

[root@kub-k8s-master prome]# vim test-volume-pod.yaml
---
apiVersion: v1
kind: Pod
metadata:name: test-volume-podnamespace: kube-systemlabels:k8s-app: test-volumenode-env: test
spec:containers:- name: test-volume-pod-containerimage: daocloud.io/library/nginxvolumeMounts:- name: podinfomountPath: /etc/podinfovolumes:- name: podinfodownwardAPI:items:- path: "labels"fieldRef:fieldPath: metadata.labels

创建上面的 POD :

[root@kub-k8s-master prome]# kubectl apply -f test-volume-pod.yaml pod/test-volume-pod created
[root@kub-k8s-master prome]# kubectl get pod -n kube-system
[root@k8s-master prome]# kubectl exec -it test-volume-pod /bin/bash -n kube-system

Secret、ConfigMap,以及 Downward API 这三种 Projected Volume 定义的信息,大多还可以通过环境变量的方式出现在容器里。但是,通过环境变量获取这些信息的方式,不具备自动更新的能力。一般情况下,建议使用 Volume 文件的方式获取这些信息。 

 

 

四.ServiceAccount详解
官方文档地址:Configure Service Accounts for Pods | Kubernetes

k8s中提供了良好的多租户认证管理机制,如RBAC、ServiceAccount还有各种Policy等。 

什么是 Service Account ?

 Pod里的进程也可以与 apiserver 联系。 当它们在联系 apiserver 的时候,它们就会被认证为一个特定的 Service Account。

使用场景:

Service Account它并不是给kubernetes集群的用户使用的,而是给pod里面的进程使用的,它为pod提供必要的身份认证。----专门为pod里面的进程和apiserver通信提供认证的。 

Service account与User account区别:

1. User account是为人设计的,而service account则是为Pod中的进程调用Kubernetes API或其他外部服务而设计的

2. User account是跨namespace的,而service account则是仅局限它所在的namespace; ​ 3. 每个namespace都会自动创建一个default service account     ​

4. Token controller检测service account的创建,并为它们创建secret

4.1 Service Account应用示例

Service Account(服务账号)示例

因为平时系统会使用默认service account,我们不需要自己创建,感觉不到service account的存在,本实验是使用自己手动创建的service account

1、创建serviceaccount
[root@kub-k8s-master ~]# kubectl create serviceaccount mysa
serviceaccount/mysa created
# yaml 方法创建
[root@kub-k8s-master ~]# vim mysa.yml
apiVersion: v1
kind: ServiceAccount
metadata:name: mysanamespace: default2、查看mysa
[root@kub-k8s-master ~]# kubectl describe sa mysa
Name:                mysa
Namespace:           default
Labels:              <none>
Annotations:         <none>  
Image pull secrets:  <none>
Mountable secrets:   mysa-token-cknwf
Tokens:              mysa-token-cknwf
Events:              <none>
3、查看mysa自动创建的secret
[root@kub-k8s-master ~]# kubectl  get secret
NAME                  TYPE                                  DATA   AGE
db-user-pass          Opaque                                2      11h
default-token-6svwp   kubernetes.io/service-account-token   3      4d23h
mysa-token-cknwf      kubernetes.io/service-account-token   3      76s
mysecret              Opaque                                2      11h
mysecret-01           Opaque                                2      6h58m
pass                  Opaque                                1      7h6m
user                  Opaque                                1      7h7m4、创建角色和绑定
[root@kub-k8s-master ~]# vim role.yml
apiVersion: rbac.authorization.k8s.io/v1
kind: Role
metadata:namespace: defaultname: mysa-role
rules:
- apiGroups: [""]resources: ["pods"]verbs: ["get", "watch", "list"]
---
apiVersion: rbac.authorization.k8s.io/v1
kind: RoleBinding
metadata:name: mysa-bindingnamespace: default
subjects:
- kind: ServiceAccountname: mysanamespace: default
roleRef:kind: Rolename: mysa-roleapiGroup: rbac.authorization.k8s.io
5、使用mysa的sa资源配置pod
[root@kub-k8s-master ~]# cd prome/
[root@kub-k8s-master prome]# vim mysa-pod.yaml
apiVersion: v1
kind: Pod
metadata:name: mysa-pod
spec:serviceAccountName: mysacontainers:- name: appimage: 10.36.192.206:8088/newrain857/kubectlcommand: ["tail","-f","/dev/null"]6、导入
[root@kub-k8s-master prome]# kubectl apply -f .
pod/mysa-pod created
role.rbac.authorization.k8s.io/mysa-role created
rolebinding.rbac.authorization.k8s.io/mysa-binding created
serviceaccount/mysa created
7、查看
[root@kub-k8s-master prome]# kubectl get pod mysa-pod -o yaml
8、测试
[root@kube-master sa]# kubectl exec -it mysa-pod /bin/sh
/ # kubectl get pod
NAME             READY   STATUS    RESTARTS      AGE
nginx            1/1     Running   1 (50m ago)   17h
mysa-pod   1/1     Running   0             9m5s
/ # kubectl delete pod nginx
Error from server (Forbidden): pods "nginx" is forbidden: User "system:serviceaccount:default:pod-reader" cannot delete resource "pods" in API group "" in the namespace "default"# 可以看到,我们已经成功限制了pod对资源的访问

五.RBAC 详解(基于角色的访问控制) 

在Kubernetes中,授权有ABAC(基于属性的访问控制)、RBAC(基于角色的访问控制)、Webhook、Node、AlwaysDeny(一直拒绝)和AlwaysAllow(一直允许)这6种模式。

RBAC基于角色的访问控制--全拼Role-Based Access Control----做权限控制的,顾名思义就是通过给角色赋予相应的权限,从而使得该角色具有访问相关资源的权限。

k8s里面有两种用户,一种是User,一种就是service account(服务使用的账号)。
User account是为人设计的属于用户账户(个人使用的账号),此外User Account是跨Namespace的,而ServiceAccount则是仅局限它所在的Namespace。

在RABC API中,通过如下的步骤进行授权:
1)定义角色:在定义角色时会指定此角色对于资源的访问控制的规则;
2)绑定角色:将主体与角色进行绑定,对用户进行访问授权。

 

在K8s中这些资源分属于两个级别,名称空间(role/rolebinding)和集群级别(clusterrole/clusterrolebinding)这两个都是标准的K8s资源,可以直接定义。

Role与ClusterRole
 Role普通角色:一个Role对象只能用于授予对某一单一命名空间中资源的访问权限,普通角色只是在当前的名称空间生效。
 ClusterRole集群角色:整个Kubernetes集群范围内有效的角色则通过ClusterRole对象实现,可以访问整个集群资源。
 简介
role/ClusterRole:
    1、允许的操作,如get,list,update,create,delete等权限
    2、允许操作的对象,如pod,svc等资源

rolebinding:将哪个用户绑定到哪个role上
clusterrolebinding:绑定到集群角色上
   如果使用clusterrolebinding绑定到clusterrole上,表示绑定的用户拥有所有namespace的权限
   
 #这里面有哪些重要的东西:role,clusterrole,binding,账号。 

5.1 创建k8s账号与RBAC授权使用 

创建账号
1、创建私钥
[root@kub-k8s-master ~]# (umask 077; openssl genrsa -out soso.key 2048)
Generating RSA private key, 2048 bit long modulus
...............................+++
..........................+++
e is 65537 (0x10001)用此私钥创建一个csr(证书签名请求)文件
[root@kub-k8s-master ~]# openssl  req -new -key soso.key -out soso.csr -subj  "/CN=soso" # 这个地方是用户名拿着私钥和请求文件生成证书
[root@kub-k8s-master ~]# openssl x509 -req -in soso.csr -CA  /etc/kubernetes/pki/ca.crt  -CAkey /etc/kubernetes/pki/ca.key -CAcreateserial -out soso.crt -days 365
Signature ok
subject=/CN=soso
Getting CA Private Key生成账号
[root@kub-k8s-master ~]# kubectl config set-credentials soso --client-certificate=soso.crt --client-key=soso.key --embed-certs=true
User "soso" set.3、设置上下文环境--指的是创建这个账号的环境在当前名称空间中
[root@kub-k8s-master ~]# kubectl config set-context soso@kubernetes --cluster=kubernetes --user=soso
Context "soso@kubernetes" created.
查看当前的工作上下文
[root@kub-k8s-master ~]# kubectl config view
apiVersion: v1
clusters:
- cluster:certificate-authority-data: DATA+OMITTEDserver: https://192.168.96.10:6443
....
4、切换用户(切换上下文)
[root@kub-k8s-master ~]# kubectl  config use-context soso@kubernetes
Switched to context "soso@kubernetes".
验证是否已经切换到了新的上下文
[root@kub-k8s-master ~]# kubectl config current-context
soso@kubernetes
5.测试(还未赋予权限)
[root@kub-k8s-master ~]# kubectl  get pod
Error from server (Forbidden): pods is forbidden: User "soso" cannot list resource "pods" in API group "" in the namespace "default"
创建一个角色(role)---设置权限
1.切回管理帐号先
[root@kub-k8s-master ~]# kubectl  config use-context kubernetes-admin@kubernetes
Switched to context "kubernetes-admin@kubernetes".创建角色(命令):
[root@kub-k8s-master ~]# kubectl  create role  role-reader  --verb=get,list,watch --resource=pod,svc
role.rbac.authorization.k8s.io/role-reader created
--verb: 相当于是权限
--resource:给什么资源使用yaml文件方式:
[root@kub-k8s-master ~]# vim role.yaml
apiVersion: rbac.authorization.k8s.io/v1
kind: Role
metadata:name: role-reader
rules: #定义规则- apiGroups: [""]  #表示当前pod使用核心的APIserver组,默认用""表示就可以resources: ["pods","svc"]verbs: ["get", "list", "watch", "create", "update", "delete"] #["*"]表示所有权限[root@kub-k8s-master ~]# kubectl apply -f role.yaml 
role.rbac.authorization.k8s.io/role-reader created[root@kub-k8s-master ~]# kubectl get roles
NAME          AGE
role-reader   30s[root@kub-k8s-master ~]# kubectl describe role role-reader
Name:         role-reader
Labels:       <none>
Annotations:  kubectl.kubernetes.io/last-applied-configuration:{"apiVersion":"rbac.authorization.k8s.io/v1beta1","kind":"Role","metadata":{"annotations":{},"name":"role-reader","namespace":"default"},"...
PolicyRule:Resources  Non-Resource URLs  Resource Names  Verbs---------  -----------------  --------------  -----pods       []                 []              [get list watch create update delete]svc        []                 []              [get list watch create update delete]
2.绑定用户soso(上面创建的用户),绑定用户到role-reader
[root@kub-k8s-master ~]# kubectl  create  rolebinding myrole-binding  --role=role-reader  --user=soso
rolebinding.rbac.authorization.k8s.io/myrole-binding created
yaml文件方式:
[root@k8s-master ~]# vim role-binding.yaml
apiVersion: rbac.authorization.k8s.io/v1
kind: RoleBinding
metadata:name: myrolebind
subjects:  #定义对那个主体进行操作,有三种Subjects:Service Account、User Account、Groups
- kind: Username: sosoapiGroup: rbac.authorization.k8s.io
roleRef:  #定义使用哪个角色kind: Rolename: role-readerapiGroup: rbac.authorization.k8s.io
[root@k8s-master ~]# kubectl apply -f role-binding.yaml 
rolebinding.rbac.authorization.k8s.io/myrolebind created
[root@k8s-master ~]# kubectl get rolebinding 
NAME         AGE
myrolebind   25s
3.切换用户
[root@kub-k8s-master ~]# kubectl  config use-context soso@kubernetes
Switched to context "soso@kubernetes".
4.查看权限(只授权了default名称空间pod和svc的get,list,watch权限)
[root@kub-k8s-master ~]# kubectl  get pod
NAME                    READY   STATUS    RESTARTS   AGE
lifecycle-demo          1/1     Running   1          22h
mypod                   1/1     Running   0          8h
nginx-configmap         1/1     Running   0          4h29m
nginx-pod               1/1     Running   0          39m
[root@kub-k8s-master ~]#  kubectl  get pod -n kube-system  #无权访问kube-system
Error from server (Forbidden): pods is forbidden: User "soso" cannot list resource "pods" in API group "" in the namespace "kube-system"
[root@kub-k8s-master ~]# kubectl  delete pod nginx-pod   #无权限删除
Error from server (Forbidden): pods "nginx-pod" is forbidden: User "soso" cannot delete resource "pods" in API group "" in the namespace "default"
5.切换用户
[root@kub-k8s-master ~]# kubectl  config use-context kubernetes-admin@kubernetes
Switched to context "kubernetes-admin@kubernetes".
实验二,绑定用户到集群角色
6.删除soso账号之前绑定的rolebinding
[root@kub-k8s-master ~]# kubectl  delete rolebinding myrolebind
rolebinding.rbac.authorization.k8s.io "myrolebind" deleted
7.创建clusterrole #可以访问全部的namespace
[root@kub-k8s-master ~]# kubectl create clusterrole myclusterrole --verb=get,list,watch --resource=pod,svc
clusterrole.rbac.authorization.k8s.io/myclusterrole created
yaml文件方式:
[root@kub-k8s-master ~]# vim clusterrole.yaml
apiVersion: rbac.authorization.k8s.io/v1
kind: ClusterRole
metadata:name: myclusterrole
rules:
- apiGroups:- ""resources:- podsverbs:- get- list- watch
[root@kub-k8s-master ~]# kubectl apply -f clusterrole.yaml
[root@kub-k8s-master ~]# kubectl get clusterrole
8.绑定集群角色到用户soso
[root@kub-k8s-master ~]# kubectl  create clusterrolebinding my-cluster-rolebinding   --clusterrole=myclusterrole --user=soso
clusterrolebinding.rbac.authorization.k8s.io/my-cluster-rolebinding created
yaml文件方式:
[root@kub-k8s-master ~]# vim clusterrolebinding.yaml
apiVersion: rbac.authorization.k8s.io/v1
kind: ClusterRoleBinding
metadata:name: my-cluster-rolebinding
roleRef:apiGroup: rbac.authorization.k8s.iokind: ClusterRolename: myclusterrole
subjects:
- apiGroup: rbac.authorization.k8s.iokind: Username: soso
[root@kub-k8s-master ~]# kubectl apply -f clusterrolebinding.yaml
[root@kub-k8s-master ~]# kubectl get clusterrolebinding
9.切换账号
[root@kub-k8s-master ~]# kubectl  config use-context soso@kubernetes
Switched to context "soso@kubernetes".
10.查看权限 查看kube-system空间的pod
[root@kub-k8s-master ~]# kubectl  get pod -n kube-system
NAME                                     READY   STATUS    RESTARTS   AGE
coredns-5644d7b6d9-sm8hs                 1/1     Running   0          5d
coredns-5644d7b6d9-vddll                 1/1     Running   0          5d
etcd-kub-k8s-master                      1/1     Running   0          5d
... 
注意:11.切换为管理员用户
[root@kub-k8s-master ~]# kubectl  config use-context kubernetes-admin@kubernetes
5.2 设置上下文和账户切换

设置工作上下文(前提得有用户)

[root@kub-k8s-master ~]# kubectl  config   set-context  soso@kubernetes --cluster=kubernetes --user=soso
Context "soso@kubernetes" created.

查看当前的工作上下文

[root@kub-k8s-master ~]# kubectl config view
apiVersion: v1
clusters:
- cluster:
....

切换上下文(切换用户)

[root@kub-k8s-master ~]# kubectl config use-context soso@kubernetes
Switched to context "soso@kubernetes".

切换为管理员用户

[root@kub-k8s-master prome]# kubectl  config use-context kubernetes-admin@kubernetes
Switched to context "kubernetes-admin@kubernetes".

查看某个资源类型是由哪个apiserver版本提供

[root@kub-k8s-master ~]# kubectl explain ClusterRole

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/news/234253.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

Redis介绍与使用

1、Nosql 1.1 数据存储的发展 1.1.1 只使用Mysql 以前的网站访问量不大&#xff0c;单个数据库是完全够用的。 但是随着互联网的发展&#xff0c;就出现了很多的问题&#xff1a; 数据量太大&#xff0c;服务器放不下 访问量太大&#xff0c;服务器也承受不了 1.1.2 缓存…

移动端自适应

1.普通html页面 一般使用px定义&#xff0c;不会进行适配 移动端项目&#xff1a;从不同的终端保持页面的一致性&#xff08;自适应&#xff09;,使用rem相对单位&#xff0c;rem是相对于根节点html的font-size的值进行动态换算的值 2.普通html页面进行适配 普通页面中&…

wps三级标题不对齐

段落中设置首行缩进即可对其 效果&#xff1a; 使用格式刷去将其他三级标题同步

使用yarn安装electron时手动选择版本

访问1Password或者其他可以提供随机字符的网站&#xff0c;获取随机密码运行安装命令 操作要点&#xff0c;必须触发Couldnt find any versions for "electron" that matches "*"才算成功 将复制的随机密码粘贴到后面 例如&#xff1a;yarn add --dev elec…

AI+爬虫 爬虫宝

场景 在很多时候&#xff0c;有很多爬虫的需求&#xff0c;其实需求都是大同小异&#xff0c;不过是在某某网页上爬取某某东西。把这些东西给到业务。以往的做法是&#xff1a;每一个需求写一个c#或者python脚本或者应用&#xff0c;进行爬取&#xff0c;这相当的费时费力&…

Java中创建线程池工具类

import java.util.concurrent.*;/**多线程工具类 */ public class ThreadPoolUtils {private static int CAPACITY 10000;// 线程池核心线程数public static int CORE_POOL_SIZE 10;// 线程池最大线程数private static int MAXIMUM_POOL_SIZE 30;// 额外线程空状态生存时间p…

前端视角看待IT圈茶余饭后的鄙视链

在IT职业圈或技术圈中&#xff0c;鄙视链是一个普遍存在的现象。鄙视链是指不同职业、技术、公司等之间存在的相互鄙视、轻视的关系。虽然这种关系并不合理&#xff0c;但它确实存在&#xff0c;而且在一定程度上影响着人们的心态和行为。 作为一名前端开发者&#xff0c;我深…

Java基础知识回顾

Java基础 一、Java概述 1、Java技术体系平台 类型简介JavaSE 标准版支持面向桌面级的应用JavaEE 企业版支持为企业开发的应用JavaME 小型版运行在移动终端的平台 2、Java重要的特点 面向对象的语言&#xff08;OOP&#xff09; 健壮的语言&#xff0c;具有强类型转换、异常…

【Docker】基础篇

文章目录 Docker为什么出现容器和虚拟机关于虚拟机关于Docker二者区别&#xff1a; Docker的基本组成相关概念-镜像&#xff0c;容器&#xff0c;仓库安装Docker卸载docker阿里云镜像加速docker run的原理**为什么容器比虚拟机快**Docker的常用命令1.帮助命令2.镜像相关命令3.容…

hadoop运行jar遇到的一个报错

报错信息&#xff1a; 2023-12-19 14:28:25,893 INFO mapreduce.Job: Job job_1702967272525_0001 failed with state FAILED due to: Application application_1702967272525_0001 failed 2 times due to AM Container for appattempt_1702967272525_0001_000002 exited with…

SpringMVC拦截器

拦截器 1.拦截器概念2.拦截器开发2.1环境准备2.2拦截器开发流程 3 拦截器参数1. 前置处理方法2. 后置处理方法3 完成处理方法4.配置多个拦截器 1.拦截器概念 (1)浏览器发送一个请求会先到Tomcat的web服务器 (2)Tomcat服务器接收到请求以后&#xff0c;会去判断请求的是静态资源…

可实现RSSD云硬盘120万IOPS的SPDK IO路径优化

一. 简介 用户对超高并发、超大规模计算等需求推动了存储硬件技术的不断发展&#xff0c;存储集群的性能越来越好&#xff0c;延时也越来越低&#xff0c;对整体IO路径的性能要求也越来越高。在云硬盘场景中&#xff0c;IO请求从生成到后端的存储集群再到返回之间的IO路径比较…

【Java】网络编程-UDP字典服务器客户端简单代码编写

上文讲了UDP回响服务器客户端简单代码编写 本文将讲述UDP字典服务器客户端简单代码编写。所谓回显&#xff0c;就是指客户端向服务器发送一个报文&#xff0c;从服务器那里得到一条一模一样的回响报文 而我们的字典功能呢&#xff0c;则是实现了输入中文&#xff0c;得到对应…

MMCV,scoreSDE,rectifiedFlow代码

MMCV&#xff0c;scoreSDE&#xff0c;rectifiedFlow代码的思想都是将各种对象&#xff0c;包括函数 和模型&#xff0c;都都写到一个字典里面&#xff0c;用的时候用关键字调用。

智能物联网汽车3d虚拟漫游展示增强消费者对品牌的认同感和归属感

汽车3D虚拟展示系统是一种基于web3D开发建模和VR虚拟现实技术制作的360度立体化三维汽车全景展示。它通过计算机1:1模拟真实的汽车外观、内饰和驾驶体验&#xff0c;让消费者在购车前就能够更加深入地了解车辆的性能、特点和设计风格。 华锐视点云展平台是一个专业的三维虚拟展…

Pytorch:backward()函数详解

.backward() .backward() 是 PyTorch 中用于自动求导的函数&#xff0c;它的主要作用是计算损失函数对模型参数的梯度&#xff0c;从而实现反向传播算法。 在深度学习中&#xff0c;我们通常使用梯度下降算法来更新模型参数&#xff0c;使得模型能够逐步逼近最优解。 在梯度下…

linux中deadline调度原理与代码注释

简介 deadline调度是比rt调度更高优先级的调度&#xff0c;它没有依赖于优先级的概念&#xff0c;而是给了每个实时任务一定的调度时间&#xff0c;这样的好处是&#xff1a;使多个实时任务场景的时间分配更合理&#xff0c;不让一些实时任务因为优先级低而饿死。deadline调度…

(保姆级教程)一篇文章,搞定所有Linux命令,以及tar解压缩命令,wget、rpm等下载安装命令,Linux的目录结构,以及用户和用户组

文章目录 Linux命令1. Linux目录结构2. 基本命令&#xff08;了解&#xff09;3. 目录&#xff08;文件夹&#xff09;命令列出目录切换目录创建目录删除目录复制目录移动和重命名目录 4. 文件命令创建文件编辑文件编辑文件时的其他操作 查看文件移动/重命名文件复制文件删除文…

机器学习---聚类(原型聚类、密度聚类、层次聚类)

1. 原型聚类 原型聚类也称为“基于原型的聚类” (prototype-based clustering)&#xff0c;此类算法假设聚类结构能通过一 组原型刻画。算法过程&#xff1a;通常情况下&#xff0c;算法先对原型进行初始化&#xff0c;再对原型进行迭代更新求解。著 名的原型聚类算法&#…

git或svn提交消息时,fix、feat等命令的含义

在git或svn提交消息时&#xff0c;可以使用特定字符来表示特定的功能&#xff0c;这些字符的使用可以提高提交描述的可读性和易用性。 具体来说&#xff0c;这些命令的含义如下&#xff1a; fix: 该提交用于修复错误或问题。feat: 该提交用于添加新功能。docs: 该提交用于更新…