Connectors CSI 驱动
概述
Connectors CSI Driver 是基于 Container Storage Interface (CSI) 规范实现的存储驱动。它可以将 Connector 中的配置作为卷挂载到 Kubernetes 工作负载中。主要特性包括:
- 将 Connector 中的配置文件挂载到 Pod 中
- 支持在配置文件中进行动态变量渲染,以自动注入运行时信息
- 支持同时挂载多个配置文件
所有配置数据都来自与 Connector 关联的 ConnectorClass configuration。
快速开始
1. 创建一个 ConnectorClass
首先,创建一个包含 Git 配置的 ConnectorClass:
cat << EOF | kubectl apply -f -
apiVersion: connectors.alauda.io/v1alpha1
kind: ConnectorClass
metadata:
name: my-git
spec:
address:
type: string
configurations:
- name: config
data:
.gitconfig: |
this is git config
EOF
2. 创建一个 Connector
然后,创建一个连接到 GitHub 的 Connector:
cat << EOF | kubectl apply -f -
apiVersion: connectors.alauda.io/v1alpha1
kind: Connector
metadata:
name: git-connector
spec:
address: https://github.com
connectorClassName: my-git
EOF
3. 创建一个使用 CSI Driver 的 Pod
创建一个挂载该配置的 Pod:
cat << EOF | kubectl create -f -
apiVersion: v1
kind: Pod
metadata:
name: csi-demo
namespace: default
spec:
restartPolicy: Never
containers:
- name: web
image: bitnami/git:2.47.1
imagePullPolicy: IfNotPresent
command: ["sleep", "3600"]
volumeMounts:
- name: git-config
mountPath: /tmp/config
volumes:
- name: git-config
csi:
readOnly: true
driver: connectors-csi
volumeAttributes:
connectors: "default/git-connector"
configuration.names: "config"
EOF
验证挂载的文件:
# 列出所有挂载的文件(包括内置配置)
kubectl exec -ti csi-demo -- ls -l /tmp/config
# 查看来自 ConnectorClass 的自定义配置
kubectl exec -ti csi-demo -- cat /tmp/config/.gitconfig
内置配置
CSI Driver 默认会自动提供内置配置文件,并将其挂载到 Pod 中。
你可以在 configuration.names 中使用 !<fileName> 排除指定的挂载文件(例如 !context.token),这同样适用于内置文件以及由 configuration.names 选中的 ConnectorClass 渲染文件。
正向代理用法:
# 方案 1
export http_proxy=$(cat /{mount-path}/http.proxy)
export https_proxy=$(cat /{mount-path}/https.proxy)
# 方案 2
source /{mount-path}/.env
反向代理用法:
export TOKEN=$(cat /{mount-path}/context.token)
export SERVER=$(cat /{mount-path}/connector.status.proxyAddress)
{cli} --server $SERVER --token $TOKEN
CSI 卷参数
卷参数
卷属性
示例
挂载单个配置:
volumes:
- name: config
csi:
driver: connectors-csi
readOnly: true
volumeAttributes:
connectors: "my-connector"
configuration.names: "config1"
挂载多个配置:
volumes:
- name: config
csi:
driver: connectors-csi
readOnly: true
volumeAttributes:
connectors: "my-connector"
configuration.names: "config1,config2"
挂载多个 connector 进行代理身份验证:
volumes:
- name: config
csi:
driver: connectors-csi
readOnly: true
volumeAttributes:
connectors: "namespace1/connector1,namespace2/connector2"
configuration.names: "config1,config2"
排除指定的挂载文件:
volumes:
- name: config
csi:
driver: connectors-csi
readOnly: true
volumeAttributes:
connectors: "my-connector"
configuration.names: "config1,!config1.conf"
仅挂载内置配置,同时排除一个内置文件:
volumes:
- name: config
csi:
driver: connectors-csi
readOnly: true
volumeAttributes:
connectors: "my-connector"
configuration.names: "!context.token"
注意:
- 如果省略
configuration.names,则仅挂载内置配置
- 当多个配置包含同名文件时,后面的配置会覆盖前面的配置
- 排除项(
!<fileName>)会在配置收集和合并后,应用于最终挂载的文件名。
- 如果指定了要包含的配置名称但未找到任何匹配项,即使提供了排除项,请求也会失败。
connectors 参数用于指定多个 connector 以挂载配置。
configuration.params
configuration.params 允许调用方在挂载时向配置模板传递运行时参数。ConnectorClass 中的每个配置都可以声明一组命名参数;在创建 CSI 卷时,configuration.params 会为这些参数提供值。
格式
该值是一个 以配置名称为键 的 JSON 对象,其中每个值都是一个键值对对象:
configuration.params: '{"<configName>": {"key": "value", ...}, ...}'
示例 — 在一次挂载中,将 mirrorRepository 传递给 settings 配置,并将 registry 传递给 npmrc 配置:
volumeAttributes:
configuration.names: "settings,npmrc"
configuration.params: '{"settings": {"mirrorRepository": "maven-public"}, "npmrc": {"registry": "npm-proxy"}}'
按配置名称进行作用域划分后,无论挂载了多少个 connector 或它们的名称是什么,参数都能保持稳定。与 connector 相关的值应放在 Connector.spec.params 中,并可在模板中通过 .connectors[i].spec.params 访问。
默认值的工作方式
当 ConnectorClass 配置为某个参数声明了默认值,而调用方未提供该参数时,CSI Driver 会在渲染模板之前自动注入默认值。此时无需在 configuration.params 中显式提供该值。
示例 — strictSSL 的默认值为 "true",因此可以省略:
# 这等同于传入 '{"npmrc": {"registry": "npm-proxy", "strictSSL": "true"}}'
configuration.params: '{"npmrc": {"registry": "npm-proxy"}}'
模板中可用的变量
处理完成后,提供的参数(以及默认参数)在配置模板中可通过 .configurations.<paramName> 访问:
{{ .configurations.mirrorRepository }}
{{ .configurations.registry }}
多个 Connector
Connectors CSI Driver 支持将多个 Connector 用于配置。你可以使用 connectors 卷属性指定多个 Connector,格式为 namespace/name 或 name;如果省略命名空间,则使用 Pod 的命名空间。多个 Connector 之间应以逗号分隔。
INFO
在一个 CSI 卷中使用多个 Connector 之前,请先在 connectors-config 中启用 enable-multi-connector 功能开关。详情请参阅 Feature Flags。
volumes:
- name: config
csi:
driver: connectors-csi
readOnly: true
volumeAttributes:
connectors: "namespace1/connector1,namespace2/connector2"
configuration.names: "config1,config2"
当指定多个 Connector 时,CSI Driver 会根据 configuration.names 属性合并配置文件。合并行为的详细说明请参见 Configuration Merging 部分。
WARNING
可列出的 connector 数量没有严格限制;不过,请避免指定过多 Connector,以防请求头过大以及其他与代理相关的问题。
配置合并
当指定多个 Connector 时,CSI Driver 会根据 configuration.names 属性合并所有指定 Connector 的配置文件。
配置文件的处理可能存在多种场景;以下情况说明了各自的行为。
相同的配置名称
对于配置名称相同的 Connector,当指定多个 Connector 时,它们的配置数据会合并为一个配置文件。
配置模板应支持为多个 Connector 渲染数据,以便单个文件可以包含多个 connector 的专属数据集。
例如:
apiVersion: connectors.alauda.io/v1alpha1
kind: ConnectorClass
metadata:
name: multi-connector
spec:
configurations:
- name: config
data:
.multi-connector-config: |
{{- range .connectors }}
# Configuration for Connector: {{ .name }}
param_name = {{ .name }}
param_value = {{ .spec.address }}
{{- end }}
在上面的示例中,配置文件 .multi-connector-config 将包含 connectors 卷属性中指定的每个 Connector 的内容段。
kubectl exec -ti pod-name -- ls -l /mount-path/
# 输出:
# - .multi-connector-config
WARNING
如果合并后的 connector 来自不同的 ConnectorClass,且它们具有同名配置文件,则后面的 ConnectorClass 中的配置会覆盖前面的 ConnectorClass 中的配置。因此,在这种情况下建议使用不同的配置文件名,以避免冲突。
不同的配置名称
当指定的 Connector 具有不同的配置名称时,CSI Driver 会分别挂载所有配置。
apiVersion: connectors.alauda.io/v1alpha1
kind: ConnectorClass
metadata:
name: connector-a
spec:
configurations:
- name: config-a
data:
config.xml: |
{{- range .connectors }}
# Configuration for Connector: {{ .name }}
param_name = {{ .name }}
param_value = {{ .spec.address }}
{{- end }}
---
apiVersion: connectors.alauda.io/v1alpha1
kind: ConnectorClass
metadata:
name: connector-b
spec:
configurations:
- name: config-b
data:
settings.json: |
{"connectors": [
{{- range .connectors }}
{"name": "{{ .name }}", "address": "{{ .spec.address }}"},
{{- end }}
]}
当同时使用 connectors 和 configuration names 进行挂载时:
- name: config
csi:
driver: connectors-csi
readOnly: true
volumeAttributes:
connectors: "namespace-a/connector-a,namespace-b/connector-b"
configuration.names: "config-a,config-b"
挂载后的卷将同时包含 config.xml 和 settings.json,并分别填充各自对应 Connector 的数据。
kubectl exec -ti pod-name -- ls -l /mount-path/
# 输出:
# - config.xml
# - settings.json
配置文件渲染
CSI Driver 在挂载配置文件时会使用 Go template 语法进行变量渲染。
可用变量
内置函数
有关支持的函数,请参阅 sprig。
例如:b64enc:对字符串进行 Base64 编码
关于代理服务
Connectors 为每个 Connector 提供代理服务,使客户端能够访问目标资源,而无需存储原始凭据。更多详情请参阅 connectors-proxy。
配置示例
固定内容
apiVersion: connectors.alauda.io/v1alpha1
kind: ConnectorClass
metadata:
name: my-git
spec:
address:
type: string
configurations:
- name: config
data:
.gitconfig: |
this is git config
使用 connector.spec.params
以下 ConnectorClass 定义了一个参数 sslVerify,用于控制 git clone 期间的 SSL 校验。
kind: ConnectorClass
metadata:
name: git
spec:
params:
- name: sslVerify
type: string
default: "true"
configurations:
- name: config
data:
.gitconfig: |
{{ $sslVerify := "true" -}}
{{- range .connector.spec.params }}{{- if eq .name "sslVerify" }}{{$sslVerify = .value }}{{ end }}{{- end }}
[http]
sslVerify = {{ $sslVerify }}
使用代理服务和令牌
以下 ConnectorClass 提供了一个名为 .gitconfig 的文件,它会通过代理服务和令牌自动注入请求头,并在 git clone 期间替换 git URL。
kind: ConnectorClass
metadata:
name: git
spec:
configurations:
- name: config
data:
.gitconfig: |
[http]
extraHeader = Authorization: Basic {{ printf ":%s" .context.token | b64enc }}
{{- range .connectors }}
[url "{{ .status.proxyAddress }}"]
insteadOf = {{.spec.address}}
{{- end }}
后续步骤