Kubernetes 资源管理:Secrets、命名与命名空间
1. 管理 Kubernetes 中的 Secrets
1.1 Secrets 概述
Kubernetes 的 Secrets 以键值对的形式管理信息,其中值是经过编码的。使用 Secrets 可以避免在配置文件中设置敏感值或在命令行中输入它们,从而降低凭证泄露的风险,并使资源配置更加有序。目前,Secrets 有三种类型:
- Opaque:默认类型,数据不会显示。
- Service account token
- Docker authentication
1.2 使用 Secrets 前的准备
- 大小限制 :每个 Secret 有 1 MB 的大小限制,虽然可以在单个 Secret 中定义多个键值对,但总大小不能超过 1 MB。
- 创建顺序 :由于 Secret 对于容器来说就像一个卷,因此需要在依赖它的 Pod 之前创建 Secret。
1.3 创建 Secret
只能使用配置文件来生成 Secret。以下是一个简单的示例:
// A simple file for configuring secret
# cat secret-test.json
{
"kind": "Secret",
"apiVersion": "v1",
"metadata": {
"name": "secret-test"
},
"type": "Opaque",
"data": {
"username": "YW15Cg==",
"password": " UGEkJHcwcmQhCg=="
}
}
可以通过以下命令对值进行 Base64 编码:
# echo "amy" | base64
YW15Cg==
使用以下命令创建 Secret 并检查其状态:
# kubectl create -f secret-test.json
secret "secret-test" created
# kubectl get secret
NAME TYPE DATA AGE
secret-test Opaque 2 39s
# kubectl describe secret secret-test
Name: secret-test
Namespace: default
Labels: <none>
Annotations: <none>
Type: Opaque
Data
====
password: 10 bytes
username: 4 bytes
1.4 在容器中使用 Secret
为了让 Pod 获取 Secret 信息,需要将 Secret 数据作为文件挂载到容器中。以下是一个示例配置文件:
# cat pod-secret.json
{
"kind": "Pod",
"apiVersion": "v1",
"metadata": {
"name": "pod-with-secret"
},
"spec": {
"volumes": [
{
"name": "secret-volume",
"secret": {
"secretName": "secret-test"
}
}
],
"containers": [
{
"name": "secret-test-pod",
"image": "nginx",
"volumeMounts": [
{
"name": "secret-volume",
"readOnly": true,
"mountPath": "/tmp/secret-volume"
}
]
}
]
}
}
验证容器中 Secret 内容是否已解密:
// login to node and enable bash process with new tty
# docker exec -it <CONTAINER_ID> bash
root@pod-with-secret:/# ls /tmp/secrets/
password username
root@pod-with-secret:/# cat /tmp/secrets/password
Pa$$w0rd!
root@pod-with-secret:/# cat /tmp/secrets/username
amy
1.5 删除 Secret
可以使用以下命令删除 Secret:
# kubectl delete -f secret-test.json
secret "secret-test" deleted
1.6 Secrets 的工作原理
为了降低 Secret 内容泄露的风险,Kubernetes 系统不会将 Secret 数据保存在磁盘上,而是存储在内存中。Kubernetes API 服务器会将 Secret 推送到运行所需容器的节点上,节点将数据存储在 tmpfs 中,当容器被销毁时,tmpfs 中的数据会被清除。
1.7 其他注意事项
- 避免创建大尺寸或大量小尺寸的 Secret :由于 Secret 存储在节点的内存中,减少 Secret 的总大小有助于节省资源并保持良好的性能。
- 服务账户 :可以通过创建不同的服务账户来实现不同的身份验证。以下是创建服务账户的示例:
# example of service account creation
$ cat serviceaccount.yaml
apiVersion: v1
kind: ServiceAccount
metadata:
name: test-account
# create service account named test-account
$ kubectl create -f serviceaccount.yaml
serviceaccount "test-account" created
可以使用以下命令查看和删除服务账户:
$ kubectl get serviceaccounts
NAME SECRETS AGE
default 0 18d
test-account 0 37s
$ kubectl delete serviceaccount test-account
serviceaccount "test-account" deleted
2. Kubernetes 中的命名规则
2.1 命名概述
在创建 Kubernetes 对象(如 Pod、Replication Controller 和 Service)时,可以为其分配名称。Kubernetes 中的名称在空间上是唯一的,即在同一 Pod 中不能使用相同的名称。
2.2 命名限制
- 名称长度最多为 253 个字符。
- 只能包含小写字母、数字。
- 中间可以包含特殊字符,但只能是连字符 (-) 和点 (.)。
2.3 命名示例
2.3.1 成功创建 Pod
# cat my-pod.yaml
apiVersion: v1
kind: Pod
metadata:
name: my-pod
spec:
containers:
- name: my-container
image: nginx
# kubectl create -f my-pod.yaml
pod "my-pod" created
# kubectl get pods
NAME READY STATUS RESTARTS AGE
my-pod 0/1 Running 0 4s
# kubectl describe pod my-pod
Name: my-pod
Namespace: default
Image(s): nginx
Node: ip-10-96-219-25/10.96.219.25
Start Time: Wed, 16 Dec 2015 00:46:33 +0000
Labels: <none>
Status: Running
Reason:
Message:
IP: 192.168.34.35
Replication Controllers: <none>
Containers:
my-container:
Container ID: docker://5501d115703e334ae44c1541b990a7e22ce4f310226ea
fea206594e4c85c90d9
Image: nginx
Image ID: docker://6ffc02088cb870652eca9ccd4c4fb582f75b29af2879792
ed09bb46fd1c898ef
State: Running
Started: Wed, 16 Dec 2015 00:46:34 +0000
Ready: True
Restart Count: 0
Environment Variables:
2.3.2 命名冲突导致创建失败
# cat duplicate.yaml
apiVersion: v1
kind: Pod
metadata:
name: my-pod
spec:
containers:
- name: my-container
image: nginx
- name: my-container
image: centos
command: ["/bin/sh", "-c", "while : ;do curl http://localhost:80/;
sleep 3; done"]
# kubectl create -f duplicate.yaml
The Pod "my-pod" is invalid.
spec.containers[1].name: duplicate value 'my-container'
You can add the -validate flag
For example: kubectl create -f duplicate.yaml -validate
Use a schema to validate the input before sending it
2.3.3 不同类型对象使用相同名称
# cat nginx.yaml
apiVersion: v1
kind: ReplicationController
metadata:
name: my-nginx
spec:
replicas: 2
selector:
sel : my-selector
template:
metadata:
labels:
sel : my-selector
spec:
containers:
- name: my-container
image: nginx
---
apiVersion: v1
kind: Service
metadata:
name: my-nginx
spec:
ports:
- protocol: TCP
port: 80
nodePort: 30080
type: NodePort
selector:
sel: my-selector
# kubectl create -f nginx.yaml
replicationcontroller "my-nginx" created
service "my-nginx" created
# kubectl get rc
CONTROLLER CONTAINER(S) IMAGE(S) SELECTOR REPLICAS AGE
my-nginx my-container nginx sel=my-selector 2 8s
# kubectl get service
NAME CLUSTER_IP EXTERNAL_IP PORT(S) SELECTOR
AGE
kubernetes 192.168.0.1 <none> 443/TCP <none>
6d
my-nginx 192.168.38.134 nodes 80/TCP sel=my-selector
14s
2.4 命名建议
-
建议使用能够方便查找和识别容器镜像的命名方式,如
memcached-pod1、haproxy.us-west、my-project1.mysql。 -
避免使用包含大写字母、下划线或点在最后的名称,如
Memcache-pod1、haproxy.us_west、my-project1.mysql.。 - 如果需要分配环境、版本或应用角色等信息,可以使用标签(Label)。
- 如果只需要分配应用名称,可以使用命名空间(Namespace)。
3. Kubernetes 中的命名空间管理
3.1 命名空间概述
在 Kubernetes 集群中,资源的名称在命名空间内是唯一的。使用 Kubernetes 命名空间可以在同一集群中为不同环境隔离命名空间,从而灵活地创建隔离环境并将资源分配给不同的项目和团队。
3.2 准备工作
-
默认情况下,Kubernetes 会创建一个名为
default的命名空间,未指定命名空间创建的对象将被放入该命名空间。 -
Kubernetes 还会创建一个名为
kube-system的初始命名空间,用于存放 Kubernetes 系统对象。 - 命名空间的名称必须是 DNS 标签,且满足以下规则:
- 最多 63 个字符。
-
匹配正则表达式
[a-z0-9]([-a-z0-9]*[a-z0-9])。
3.3 创建命名空间
# cat newNamespace.yaml
apiVersion: v1
kind: Namespace
metadata:
name: new-namespace
# kubectl create -f newNamespace.yaml
3.4 查看命名空间
# kubectl get namespaces
NAME LABELS STATUS AGE
default <none> Active 8d
new-namespace <none> Active 12m
3.5 在命名空间中运行资源
# kubectl run nginx --image=nginx --namespace=new-namespace
查看 Pod 时,如果不指定命名空间,可能看不到新命名空间中的 Pod:
# kubectl get pods
NAME READY STATUS
RESTARTS AGE
使用
--all-namespaces
或指定命名空间查看 Pod:
# kubectl get pods --all-namespaces
NAMESPACE NAME READY STATUS RESTARTS AGE
new-namespace nginx-ns0ig 1/1 Running 0 17m
# kubectl get pods --namespace=new-namespace
NAME READY STATUS RESTARTS AGE
nginx-ns0ig 1/1 Running 0 18m
3.6 指定命名空间创建资源
使用配置文件创建资源时,可以通过
--namespace
参数指定命名空间:
# kubectl create -f myResource.yaml --namespace=new-namespace
3.7 更改默认命名空间
3.7.1 查找当前上下文
# kubectl config view | grep current-context
current-context: ""
3.7.2 设置新的上下文
# kubectl config set-context <current context or new context name>
--namespace=new-namespace
3.7.3 查看当前配置
# kubectl config view
apiVersion: v1
clusters: []
contexts:
- context:
cluster: ""
namespace: new-namespace
user: ""
name: new-context
current-context: ""
kind: Config
preferences: {}
users: []
3.7.4 切换上下文
# kubectl config use-context new-context
3.7.5 验证当前上下文
# kubectl config view | grep current-context
current-context: new-context
3.7.6 查看 Pod
# kubectl get pods
NAME READY STATUS RESTARTS AGE
nginx-ns0ig 1/1 Running 0 54m
3.8 删除命名空间
# kubectl delete namespaces new-namespace
namespace "new-namespace" deleted
删除命名空间后,该命名空间下的所有资源都会被删除。如果尝试在已删除的命名空间中创建资源,会出现错误:
# kubectl run nginx --image=nginx
Error from server: namespaces "new-namespace" not found
可以将默认命名空间切换回
default
:
# kubectl config set-context new-context --namespace=""
context "new-context" set.
# kubectl run nginx --image=nginx
replicationcontroller "nginx" created
# kubectl describe pods nginx-ymqeh
Name: nginx-ymqeh
Namespace: default
Image(s): nginx
Node: ip-10-96-219-156/10.96.219.156
Start Time: Sun, 20 Dec 2015 16:13:33 +0000
Labels: run=nginx
Status: Running
...
3.9 资源配额限制
有时需要通过命名空间来限制每个团队的资源配额。默认情况下,资源配额和限制未设置。在设置限制之前,需要启用 Kubernetes API 服务器中的
LimitRanger
:
# kube-apiserver --admission-control=LimitRanger
或在配置文件中设置:
# cat /etc/kubernetes/apiserver
...
# default admission control policies
KUBE_ADMISSION_CONTROL="--admission_control=NamespaceLifecycle,NamespaceE
xists,LimitRanger,SecurityContextDeny,ResourceQuota"
...
以下是在命名空间中创建限制的示例:
# cat limits.yaml
apiVersion: v1
kind: LimitRange
metadata:
name: limits
namespace: new-namespace
spec:
limits:
- max:
cpu: "2"
memory: 1Gi
min:
cpu: 200m
memory: 6Mi
type: Pod
- default:
cpu: 300m
memory: 200Mi
defaultRequest:
cpu: 200m
memory: 100Mi
max:
cpu: "2"
memory: 1Gi
min:
cpu: 100m
memory: 3Mi
type: Container
# kubectl create -f limits.yaml
limitrange "limits" created
# kubectl get LimitRange --namespace=new-namespace
NAME AGE
limits 22m
# kubectl describe namespace new-namespace
Name: new-namespace
Labels: <none>
Status: Active
No resource quota.
Resource Limits
Type Resource Min Max Request Limit Limit/Request
---- -------- --- --- ------- ----- -------------
Pod memory 6Mi 1Gi - - -
Pod cpu 200m 2 - - -
Container cpu 100m 2 200m 300m -
Container memory 3Mi 1Gi 100Mi 200Mi -
在该命名空间中创建的所有 Pod 和容器都必须遵循这些资源限制,否则会抛出验证错误。
总结
本文详细介绍了 Kubernetes 中 Secrets、命名和命名空间的使用方法。通过合理使用这些功能,可以提高 Kubernetes 集群的安全性、可管理性和资源利用率。在实际应用中,需要根据具体需求和场景,灵活运用这些特性,以实现高效的资源管理。
流程图:创建 Secret 流程
graph LR
A[准备配置文件] --> B[检查大小限制]
B --> C[创建 Secret]
C --> D[验证 Secret 状态]
D --> E[挂载到容器]
E --> F[验证容器中 Secret 内容]
表格:命名规则总结
| 规则 | 详情 | 示例 |
|---|---|---|
| 长度 | 最多 253 个字符 | |
| 字符 | 小写字母、数字 | |
| 特殊字符 | 中间可包含连字符 (-) 和点 (.) |
memcached-pod1
|
| 冲突 | 同一 Pod 中不能使用相同名称 | |
| 不同类型对象 | 不同类型对象可使用相同名称 |
my-nginx
(Replication Controller 和 Service)
|
流程图:命名空间操作流程
graph LR
A[创建命名空间] --> B[查看命名空间]
B --> C[在命名空间中运行资源]
C --> D[查看资源]
D --> E{是否需要切换默认命名空间}
E -- 是 --> F[切换默认命名空间]
E -- 否 --> G[删除命名空间]
F --> D
G --> H[验证删除结果]
表格:命名空间资源配额限制总结
| 资源类型 | 最小限制 | 最大限制 | 默认请求 | 默认限制 |
|---|---|---|---|---|
| Pod - CPU | 200m | 2 | - | - |
| Pod - 内存 | 6Mi | 1Gi | - | - |
| Container - CPU | 100m | 2 | 200m | 300m |
| Container - 内存 | 3Mi | 1Gi | 100Mi | 200Mi |
4. 综合应用案例与最佳实践
4.1 综合应用案例
假设我们要部署一个简单的 Web 应用,该应用需要访问数据库,并且我们希望通过 Kubernetes 的资源管理功能来保证安全性和资源的合理分配。
4.1.1 创建 Secret 存储数据库凭证
首先,我们创建一个 Secret 来存储数据库的用户名和密码。
// database-secret.json
{
"kind": "Secret",
"apiVersion": "v1",
"metadata": {
"name": "database-secret"
},
"type": "Opaque",
"data": {
"db-username": "c29tZV91c2VybmFtZQ==",
"db-password": "c29tZV9wYXNzd29yZA=="
}
}
# 对值进行 Base64 编码
echo "some_username" | base64
echo "some_password" | base64
# 创建 Secret
kubectl create -f database-secret.json
4.1.2 创建命名空间
为了隔离这个 Web 应用的资源,我们创建一个新的命名空间。
# web-app-namespace.yaml
apiVersion: v1
kind: Namespace
metadata:
name: web-app-namespace
kubectl create -f web-app-namespace.yaml
4.1.3 在命名空间中部署应用
创建一个 Deployment 来部署 Web 应用,并将 Secret 挂载到容器中。
# web-app-deployment.yaml
apiVersion: apps/v1
kind: Deployment
metadata:
name: web-app-deployment
namespace: web-app-namespace
spec:
replicas: 2
selector:
matchLabels:
app: web-app
template:
metadata:
labels:
app: web-app
spec:
containers:
- name: web-app-container
image: web-app-image:latest
volumeMounts:
- name: secret-volume
readOnly: true
mountPath: "/etc/secrets"
volumes:
- name: secret-volume
secret:
secretName: database-secret
kubectl create -f web-app-deployment.yaml --namespace=web-app-namespace
4.1.4 设置资源配额限制
在命名空间中设置资源配额限制,确保应用不会过度消耗资源。
# web-app-limits.yaml
apiVersion: v1
kind: LimitRange
metadata:
name: web-app-limits
namespace: web-app-namespace
spec:
limits:
- max:
cpu: "1"
memory: 512Mi
min:
cpu: 100m
memory: 64Mi
type: Pod
- default:
cpu: 200m
memory: 128Mi
defaultRequest:
cpu: 100m
memory: 64Mi
max:
cpu: "1"
memory: 512Mi
min:
cpu: 100m
memory: 64Mi
type: Container
kubectl create -f web-app-limits.yaml --namespace=web-app-namespace
4.2 最佳实践
4.2.1 Secrets 最佳实践
- 最小化 Secret 大小 :避免创建大尺寸的 Secret,因为它们存储在节点的内存中,大尺寸的 Secret 会占用过多资源。
- 定期更新 Secret :定期更换敏感信息,如数据库密码,以提高安全性。
- 使用 Secret 版本控制 :可以通过版本控制工具(如 Git)管理 Secret 的配置文件,方便追溯和回滚。
4.2.2 命名最佳实践
-
使用有意义的名称
:名称应该能够清晰地表达对象的用途,如
web-app-pod、database-service等。 - 遵循命名规范 :严格遵守 Kubernetes 的命名限制,避免因命名问题导致创建失败。
4.2.3 命名空间最佳实践
- 合理划分命名空间 :根据不同的项目、环境(如开发、测试、生产)或团队划分命名空间,提高资源的隔离性和可管理性。
- 设置资源配额 :在每个命名空间中设置合理的资源配额,确保资源的合理分配。
5. 常见问题与解决方案
5.1 Secrets 相关问题
5.1.1 Secret 大小超过限制
如果创建 Secret 时超过了 1 MB 的大小限制,会导致创建失败。解决方案是将大的 Secret 拆分成多个小的 Secret,或者重新评估是否真的需要存储这么多信息。
5.1.2 容器无法访问 Secret
如果容器无法访问挂载的 Secret,可能是由于以下原因:
- Secret 名称或挂载路径配置错误:检查 Pod 配置文件中 Secret 的名称和挂载路径是否正确。
- Secret 未正确创建:使用
kubectl get secret
命令检查 Secret 是否存在。
5.2 命名相关问题
5.2.1 命名冲突
如果在同一 Pod 中使用了相同的名称,会导致创建失败。解决方案是检查配置文件,确保每个容器的名称唯一。
5.2.2 不符合命名规则
如果名称不符合 Kubernetes 的命名规则,如包含大写字母、下划线等,会导致创建失败。解决方案是修改名称,使其符合规则。
5.3 命名空间相关问题
5.3.1 找不到命名空间
如果在删除命名空间后,尝试在该命名空间中创建资源,会出现找不到命名空间的错误。解决方案是切换默认命名空间或指定正确的命名空间。
5.3.2 资源配额限制导致创建失败
如果在命名空间中设置了资源配额限制,而创建的资源超出了限制,会导致创建失败。解决方案是调整资源请求和限制,或者修改资源配额设置。
6. 总结与展望
6.1 总结
本文全面介绍了 Kubernetes 中 Secrets、命名和命名空间的使用方法、最佳实践以及常见问题的解决方案。通过合理使用这些功能,可以提高 Kubernetes 集群的安全性、可管理性和资源利用率。
6.2 展望
随着 Kubernetes 的不断发展,资源管理功能也将不断完善。未来,可能会出现更强大的 Secret 管理工具、更灵活的命名规则和更精细的命名空间管理功能。我们需要持续关注这些变化,不断学习和实践,以更好地应对复杂的应用场景。
流程图:综合应用案例部署流程
graph LR
A[创建 Secret] --> B[创建命名空间]
B --> C[部署应用到命名空间]
C --> D[设置资源配额限制]
D --> E[验证应用运行状态]
表格:常见问题与解决方案总结
| 问题类型 | 问题描述 | 解决方案 |
|---|---|---|
| Secrets | Secret 大小超过限制 | 拆分 Secret 或重新评估信息 |
| Secrets | 容器无法访问 Secret | 检查配置和 Secret 状态 |
| 命名 | 命名冲突 | 确保每个容器名称唯一 |
| 命名 | 不符合命名规则 | 修改名称使其符合规则 |
| 命名空间 | 找不到命名空间 | 切换默认命名空间或指定正确命名空间 |
| 命名空间 | 资源配额限制导致创建失败 | 调整资源请求和限制或修改配额设置 |
超级会员免费看

被折叠的 条评论
为什么被折叠?



