升级 Kubernetes 上的 AISIX 网关
通过 api7/aisix Helm Chart 安装的 AISIX 网关,应作为独立 Release 升级。本流程将连接 AISIX Enterprise 或 AISIX Cloud 的 0.12.0 或更高版本网关,或 1.4、1.5 版本的开源 AISIX 网关升级至本版本。滚动更新前,开源 AISIX 网关使用目标镜像校验声明式资源;连接控制面的网关则跳过该校验,因为配置来自控制面。在 OKD 上运行的网关还需要完成 OKD 中的平台检查。
对于连接控制面的网关,升级起点取决于产品。AISIX Enterprise 应先按照升级 AISIX Enterprise操作,在升级后的控制面验证通过后再回到本页。AISIX Cloud 的控制面由 API7 运维,其网关可直接从本流程开始。
前提条件
升级前,请完成以下准备:
- 配置
kubectl,使其能够访问包含 AISIX 的集群和命名空间。 - 安装 Helm 3.15 或更新的 Helm 3 版本、cURL 和
jq。对于 AISIX OSS,还需安装 Docker 来校验资源。 - 阅读已安装版本之后每个版本的发布说明,并依次应用所需配置或可观测性变更。
- 确认负载均衡器会移除
/readyz检查失败的 Pod。 - 对于多副本部署,若限流计数或缓存条目必须跨副本保持一致,请确认已配置共享 Redis。如果计划在升级前增加单副本部署的副本数,请先配置共享 Redis,或明确接受临时的各副本独立行为。参见准备 AISIX 网关生产环境。
示例使用 aisix-dp 作为 Release 和命名空间,与网 关安装指南及控制台生成的 Helm 命令一致。如果安装时使用了其他值,请运行 helm list -A,找到 CHART 列为 aisix-<version> 的 Release,并在整个流程中使用其名称和命名空间。值错误会导致 helm upgrade 报告 Release 没有已部署修订,下面的 Deployment 查询也会为空。
设置示例使用的 Release 信息:
export GATEWAY_NAMESPACE="aisix-dp"
export GATEWAY_RELEASE="aisix-dp"
export TARGET_VERSION="1.6.0"
export GATEWAY_UPGRADE_TIMEOUT="60m"
60 分钟超时是针对 Chart 默认值的保守起始预算。默认配置包括两个副本、每个 Pod 1,230 秒的终止上限,以及五分钟的启动探针预算。它并非预期执行时长。
Kubernetes 可以让 Pod 终止过程相互重叠,Helm 也不要求旧 Pod 结束后才认为更新后的 Deployment 已就绪。修改副本数、更新策略、终止宽限期、探针预算,或者镜像拉取和调度变慢时,请重新计算超时。
请确认集群能够调度滚动更新多出的那个 Pod;超时设得再长也解决不了配额或容量拒绝。原子升级失败时,Helm 回滚可能再用掉一整个超时周期,因此请在维护窗口中预留这段时间。
刷新 API7 Chart 仓库,并确认目标 Chart 可用:
helm repo add api7 https://charts.api7.ai
helm repo update
helm show chart api7/aisix --version "$TARGET_VERSION"
记录当前 Release
记录已安装的 Chart 版本和应用版本:
helm list -n "$GATEWAY_NAMESPACE"
kubectl get pods -n "$GATEWAY_NAMESPACE"
根据 Helm Release 标签解析 Deployment 名称。即使 Chart 使用了名称覆盖项,这种方式也有效:
export GATEWAY_DEPLOYMENT="$(kubectl get deployment -n "$GATEWAY_NAMESPACE" \
-l "app.kubernetes.io/instance=$GATEWAY_RELEASE,app.kubernetes.io/component=gateway" \
-o jsonpath='{.items[0].metadata.name}')"
printf 'Gateway: %s\n' "$GATEWAY_DEPLOYMENT"
如果该值为空,请停止,并核实 Release 名称和命名空间。
仅保存用户提供的 values。文件可能包含凭据,请使用严格权限创建。不要通过 helm get values --all 导出所有计算后的默认值;沿用旧默认值可能使新 Chart 的默认值无法生效。
umask 077
touch gateway-values.yaml
chmod 600 gateway-values.yaml
helm get values "$GATEWAY_RELEASE" -n "$GATEWAY_NAMESPACE" -o yaml > gateway-values.yaml
将此文件与升级记录一起保留,观察期结束后移除本地副本。
检查 values 是否固定了镜像标签:
helm get values "$GATEWAY_RELEASE" -n "$GATEWAY_NAMESPACE" -o json \
| jq '{gateway_image_tag: (.image.tag // "")}'
空标签使用目标 Chart 的应用版本。如果该值固定了旧 AISIX 镜像,请从保存的 values 中移除,或更新为目标版本。保留有意使用的自定义仓库,并为自定义构建使用兼容目标版本的标签。
渲染目标网关镜像
渲染目标 Deployment,并记录 Helm 将应用的精确网关镜像。这样可以保留 Chart 的镜像注册表设置,以及有意配置的仓库或标签覆盖项:
TARGET_GATEWAY_IMAGE="$(
helm template "$GATEWAY_RELEASE" api7/aisix \
--namespace "$GATEWAY_NAMESPACE" \
--version "$TARGET_VERSION" \
--values gateway-values.yaml \
--show-only templates/deployment.yaml \
| awk '
$1 == "-" && $2 == "name:" && $3 == "aisix" { in_gateway = 1; next }
in_gateway && $1 == "image:" { gsub(/"/, "", $2); print $2; exit }
'
)"
export TARGET_GATEWAY_IMAGE
if [ -z "$TARGET_GATEWAY_IMAGE" ]; then
echo "Target gateway image was not rendered" >&2
else
printf 'Target gateway image: %s\n' "$TARGET_GATEWAY_IMAGE"
fi
如果没有渲染出目标网关镜像,请不要继续。
校验 AISIX OSS 资源
本节仅适用于 AISIX OSS。对于连接 AISIX Enterprise 或 AISIX Cloud 的网关,请继续检查目标 Release。
确定 Release 使用的资源 来源,但不要打印内联资源文档:
helm get values "$GATEWAY_RELEASE" -n "$GATEWAY_NAMESPACE" -o json \
| jq '{inline_resources: (((.standalone.resources // {}) | length) > 0), existing_secret: (.standalone.existingSecret // ""), existing_config_map: (.standalone.existingConfigMap // "")}'
export TARGET_RESOURCES_FILE="$(mktemp "$PWD/aisix-resources.XXXXXX")"
chmod 600 "$TARGET_RESOURCES_FILE"
根据报告的来源选择命令。对于内联资源,请渲染目标 Chart 管理的 Secret,并提取完整文档:
helm template "$GATEWAY_RELEASE" api7/aisix \
--namespace "$GATEWAY_NAMESPACE" \
--version "$TARGET_VERSION" \
--values gateway-values.yaml \
--show-only templates/secret.yaml \
| awk '
/^ resources\.yaml: \|$/ { in_resources = 1; next }
in_resources && /^---$/ { exit }
in_resources { sub(/^ /, ""); print }
' > "$TARGET_RESOURCES_FILE"
对于已有的 Secret 或 ConfigMap,请把占位符替换为上一条 jq 命令报告的名称:
# 选择其中一条命令。
kubectl get secret -n "$GATEWAY_NAMESPACE" \
<existing-secret-name> \
-o jsonpath='{.data.resources\.yaml}' \
| base64 --decode > "$TARGET_RESOURCES_FILE"
kubectl get configmap -n "$GATEWAY_NAMESPACE" \
<existing-config-map-name> \
-o jsonpath='{.data.resources\.yaml}' > "$TARGET_RESOURCES_FILE"
使用从目标 Deployment 渲染结果中记录的 TARGET_GATEWAY_IMAGE 校验提取出的文档。导出资源文件引用的每个环境变量,并为每个变量添加一个 -e 选项。示例使用 OPENAI_API_KEY 和 CALLER_API_KEY,请替换为文件实际使用的变量。
该命令把文档以流的方式传入短生命周期的容器,而不是把 主机文件 bind mount 进去。这样网关镜像就能读取该文档,而无需放宽主机文件权限或修改其 SELinux 标签。
docker run --rm -i \
-e OPENAI_API_KEY \
-e CALLER_API_KEY \
--entrypoint /bin/sh "$TARGET_GATEWAY_IMAGE" \
-c 'umask 077; cat > /tmp/resources.yaml && exec /usr/local/bin/aisix validate --resources /tmp/resources.yaml' \
< "$TARGET_RESOURCES_FILE" && {
rm -f "$TARGET_RESOURCES_FILE" &&
unset TARGET_RESOURCES_FILE
}
继续之前,请解决所有校验错误。校验失败时会保留提取出的文件以供检查,并返回非零状态。如果资源文件不引用环境变量,请省略 -e 选项。
检查目标 Release
更改 Release 前,请让 Helm 针对实际集群渲染升级结果。--dry-run=server 允许集群查询和 OpenAPI 校验,--hide-secret 则防止 Helm 将渲染出的 Secret 输出到终端或 CI 日志:
helm upgrade "$GATEWAY_RELEASE" api7/aisix \
--namespace "$GATEWAY_NAMESPACE" \
--version "$TARGET_VERSION" \
--values gateway-values.yaml \
--dry-run=server \
--hide-secret
该命令不会将渲染对象提交给准入控制。解决所有报告的错误后再继续。
升级网关
运行 Helm 之前,先打开第二个终端观察网关 Pod,并让它一直运行到 Helm 返回:
kubectl get pods -n "$GATEWAY_NAMESPACE" \
-l "app.kubernetes.io/instance=$GATEWAY_RELEASE,app.kubernetes.io/component=gateway" \
--watch
如果新 Pod 停滞或重启,请按 Ctrl+C 停止观察,或打开第三个终端。在原终端中的 Helm 仍等待时,记录 Pod 描述与日志。原子回滚可能在 Helm 命令返回前移除失败的目标 Pod;参见排查未就绪的网关。
在原终端中运行升级:
helm upgrade "$GATEWAY_RELEASE" api7/aisix \
--namespace "$GATEWAY_NAMESPACE" \
--version "$TARGET_VERSION" \
--values gateway-values.yaml \
--atomic \
--timeout "$GATEWAY_UPGRADE_TIMEOUT"
--atomic 会阻塞,直到目标版本就绪,或失败后 Helm 完成回滚。如果命令以非零状态退出,不要将之后成功的 kubectl rollout status 当作目标版本成功的证明,它可能报告的是已恢复的修订。请保留 Helm 运行期间记录的诊断信息,然后检查 Release 历史并验证恢复后的网关 Release:
helm history "$GATEWAY_RELEASE" -n "$GATEWAY_NAMESPACE"
使用默认滚动更新策略和就绪探针时,新网关在加载可用配置前不会加入 Service 端点。请保持 readinessProbe.enabled 为 true;若升级必须避免流量中断,不要选择 Recreate 策略。单副本部署在唯一 Pod 被替换期间仍可能发生中断。
如果 Helm 命令成功,请确认目标滚动更新已完成,且每个网关 Pod 都已就绪:
kubectl rollout status -n "$GATEWAY_NAMESPACE" \
"deployment/$GATEWAY_DEPLOYMENT" \
--timeout="$GATEWAY_UPGRADE_TIMEOUT"
kubectl get pods -n "$GATEWAY_NAMESPACE"
验证升级
将 AISIX_PROXY 设置为网关源站地址,不带结尾斜杠,然后列出调用方可用的模型:
export AISIX_PROXY="YOUR_AISIX_GATEWAY_URL"
export AISIX_API_KEY="<caller-api-key>"
curl -fsS "$AISIX_PROXY/v1/models" \
-H "Authorization: Bearer $AISIX_API_KEY"
为列出的某个模型发送已知可成功的推理请求。检查部署依赖的访问日志、指标和其他遥测。请保留已保存的 values,直到网关在变更策略规定的观察期内运行正常。
对于连接 AISIX Enterprise 或 AISIX Cloud 的网关,还需在控制台中确认每个已升级网关报告目标版本,且状态健康。
回滚
如果 Helm 原子升级失败,它会自动恢复之前的 Release。请先诊断失败原因,再重试。
成功升级后若需回滚,请确定之前的修订并恢复:
helm history "$GATEWAY_RELEASE" -n "$GATEWAY_NAMESPACE"
helm rollback "$GATEWAY_RELEASE" <previous-revision> \
--namespace "$GATEWAY_NAMESPACE" \
--wait \
--timeout "$GATEWAY_UPGRADE_TIMEOUT"
确认恢复后的 Pod 就绪,并重新执行流量验证。
排查未就绪的网关
停止观察后,趁 Helm 仍在等待,针对观察中报告的新目标 Pod 运行以下诊断命令;也可以在第三个终端中运行。原子升级失败返回后,失败的 Pod 可能已经不存在;这时 请使用已记录的输出和事件,再用上面的 Release 历史命令确认恢复后的修订版本。
kubectl get events -n "$GATEWAY_NAMESPACE" --sort-by=.lastTimestamp
kubectl get pods -n "$GATEWAY_NAMESPACE" \
-l "app.kubernetes.io/instance=$GATEWAY_RELEASE,app.kubernetes.io/component=gateway"
kubectl describe pod -n "$GATEWAY_NAMESPACE" <non-ready-gateway-pod>
kubectl logs -n "$GATEWAY_NAMESPACE" \
<non-ready-gateway-pod> \
--all-containers \
--tail=300
如果容器发生过重启,请使用 kubectl describe pod 确定容器名称,再通过 kubectl logs --previous 读取该容器的上一次日志。
对于 AISIX OSS 资源校验错误,请确认保存的 standalone values 指向完整资源文件,并确认网关可以访问每个已配置的上游端点。
对于连接 AISIX Enterprise 或 AISIX Cloud 的网关,请验证 Pod 可以通过双向 TLS 访问现有数据面管理器端点。如果端点使用 Route,请确认 Route 使用 TLS passthrough。无论哪种情况,均需确认端点主机名仍与网关配置中的地址一致。