Helm 是 Kubernetes 的套件管理員,可協助簡化應用程式生命週期管理。 Helm 套件稱為 Chart,由 YAML 組態和範本檔案組成。 執行 Helm 作業時,Chart 會被轉譯成 Kubernetes 資訊清單檔,以觸發適當的應用程式生命週期動作。 若要與 Azure 操作員 Service Manager 進行最有效率的整合,請在開發 Helm 圖表時遵循這些建議的最佳做法。
registryPath 和 imagePullSecrets 的考量事項
每個 Helm Chart 通常都需要 registryPath 和 imagePullSecrets 參數。 最常見的是,您會在 values.yaml 檔案中公開這些參數。 起初,Azure Operator Service Manager 依賴發行者以嚴格的方式 (舊版方法) 來管理這些值,並在部署期間再將其替換為正確的 Azure 值。 但並非所有發行者都可以輕易地遵守對這些值的嚴格管理。 有些 Chart 會將 registryPath 和/或 imagePullSecrets 隱藏在條件或其他值限制之後,而這些條件或限制不一定會被滿足。 有些 Chart 會將 registryPath 和/或 imagePullSecrets 宣告為陣列,而不是作為預期的具名字串。
為了降低對發行者的合規要求,Azure Operator Service Manager 引入了兩種改進的方法:injectArtifactStoreDetail 與叢集登錄。 這些較新的方法不依賴 Helm 套件中出現的 registryPath 或 imagePullSecrets。 相反地,這些方法會使用 Webhook 將正確的 Azure 值直接注入到 Pod 作業中。
registryPath 和 imagePullSecrets 的方法摘要
目前,所有三種方法均受支援,如本文所述。 為您的網路功能 (NF) 和使用案例選擇最佳的選項。
舊版:
- 需要您在 Helm 值和部署範本中參數化
registryPath和imagePullSecrets以進行替換。 - 在 Azure Container Registry 中託管映像。
InjectArtifactStoreDetail:
- 使用 Webhook 將
registryPath和imagePullSecrets直接注入到 Pod 作業中,對 Helm 的依賴最小。 - 在 Azure Container Registry 中託管映像。
叢集登錄:
- 使用 Webhook 將
registryPath和imagePullSecrets直接注入到 Pod 作業中,對 Helm 沒有任何依賴。 - 在本機網路功能操作員 (NFO) 擴充功能中託管映像。
在所有這三種情況下,Azure Operator Service Manager 都會將您在範本中公開的任何值替換為 Azure 值。 唯一的差別在於替換的方法。
舊版對 registryPath 和 imagePullSecrets 的需求
Azure Operator Service Manager 會使用 Azure 網路功能管理員 服務來部署容器化網路功能 (CNF)。 使用舊版方法時,Azure 網路功能管理員 會在部署網路功能期間將 Azure Operator Service Manager 容器的 registryPath 和 imagePullSecrets 值替換到 Helm 作業中。
舊版方法的範例
下列 Helm 部署範本顯示了您應如何公開 registryPath 和 imagePullSecrets 的範例:
apiVersion: apps/v1
kind: Deployment
metadata:
name: nginx-deployment
labels:
app: nginx
spec:
replicas: 3
selector:
matchLabels:
app: nginx
template:
metadata:
labels:
app: nginx
spec:
{{- if .Values.global.imagePullSecrets }}
imagePullSecrets: {{ toYaml .Values.global.imagePullSecrets | nindent 8 }}
{{- end }}
containers:
- name: contosoapp
image:{{ .Values.global.registryPath }}/contosoapp:1.14.2
ports:
- containerPort: 80
下列 values.yaml 範本顯示了您可以如何提供 registryPath 和 imagePullSecrets 值的範例:
global:
imagePullSecrets: []
registryPath: ""
下列 values.schema.json 檔案顯示了您可以如何定義 registryPath 和 imagePullSecrets 值的範例:
{
"$schema": "http://json-schema.org/draft-07/schema#",
"title": "StarterSchema",
"type": "object",
"required": ["global"],
"properties": {
"global" : {
"type": "object",
"properties": {
"registryPath": {"type": "string"},
"imagePullSecrets": {"type": "string"},
}
"required": [ "registryPath", "imagePullSecrets" ],
}
}
}
下列網路功能定義版本 (NFDV) 要求承載顯示了您可以如何在部署時提供 registryPath 和 imagePullSecrets 值的範例:
"registryValuesPaths": [ "global.registryPath" ],
"imagePullSecretsValuesPaths": [ "global.imagePullSecrets" ],
在上述範例中:
-
registryPath值設定時,不需加上任何前置詞,例如https://或oci://。 如有需要,可在 Helm 套件中定義前置詞。 -
imagePullSecrets和registryPath必須在 NFDV 上線期間提供。
其他考慮
當您使用舊版方法時,請考慮下列建議事項。
避免參考外部登錄
參考外部登錄可能會導致驗證問題。 如果 deployment.yaml 使用硬式編碼的登錄路徑或外部登錄參考,則驗證會失敗。
執行手動驗證
檢閱映像和容器規範,以確保映像的前置詞為 registryPath,且 imagePullSecrets 已填入 secretName:
helm template --set "global.imagePullSecrets[0].name=<secretName>" --set "global.registry.url=<registryPath>" <release-name> <chart-name> --dry-run
以下是另一個範例︰
helm install --set "global.imagePullSecrets[0].name=<secretName>" --set "global.registry.url=<registryPath>" <release-name> <chart-name> --dry-run
kubectl create secret <secretName> regcred --docker-server=<registryPath> --dockerusername=<regusername> --docker-password=<regpassword>
使用靜態映像存放庫和標籤
每個 Helm Chart 都應包含靜態映像存放庫和標籤。 您可以透過下列其中一種方法來設定靜態值:
- 在
image行中 - 在
values.yaml中,無需在 NFDV 中公開這些值
NFDV 應對應到一組靜態的 Helm Chart 和映像。 您只需發佈新的 NFDV 即可更新 Chart 和映像,如下例所示:
image: "{{ .Values.global.registryPath }}/contosoapp:1.14.2"
image: "{{ .Values.global.registryPath }}/{{ .Values.image.repository }}:{{ .Values.image.tag}}"
YAML values.yaml
image:
repository: contosoapp
tag: 1.14.2
image: http://myUrl/{{ .Values.image.repository }}:{{ .Values.image.tag}}
injectArtifactStoreDetails 對 registryPath 和 imagePullSecrets 的需求
在某些情況下,第三方 Helm 圖表可能不完全符合 registryPath 的 Azure 操作員服務管理員需求。 在這些情況下,您可以使用 injectArtifactStoreDetails 來避免對 Helm 套件進行合規性變更。
啟用 injectArtifactStoreDetails 後,您可以使用 Webhook 方法在 Pod 作業期間動態注入正確的 registryPath 和 imagePullSecrets。 此方法會覆寫 Helm 套件中設定的值。 您仍然必須在參考 registryPath 和 imagePullSecrets 的位置使用合法的虛擬值,通常在 global 的 values.yaml 區段中。
以下 values.yaml 範例顯示了您可以如何提供 registryPath 和 imagePullSecrets 值以與 injectArtifactStoreDetails 方法相容:
global:
registryPath: "azure.io"
imagePullSecrets: ["abc123"]
附註
如果基礎 Helm 套件中的 registryPath 留空,則網站網路服務 (SNS) 部署在映像下載期間會失敗。
使用 injectArtifactStoreDetails 方法
若要啟用 injectArtifactStoreDetails,請將 NF 資源的 installOptions 區段中的 roleOverrides 參數設為 true,如下例所示:
resource networkFunction 'Microsoft.HybridNetwork/networkFunctions@2023-09-01' = {
name: nfName
location: location
properties: {
nfviType: 'AzureArcKubernetes'
networkFunctionDefinitionVersionResourceReference: {
id: nfdvId
idType: 'Open'
}
allowSoftwareUpdate: true
nfviId: nfviId
deploymentValues: deploymentValues
configurationType: 'Open'
roleOverrideValues: [
// Use inject artifact store details feature on test app 1
'{"name":"testapp1", "deployParametersMappingRuleProfile":{"helmMappingRuleProfile":{"options":{"installOptions":{"atomic":"false","wait":"false","timeout":"60","injectArtifactStoreDetails":"true"},"upgradeOptions": {"atomic": "false", "wait": "true", "timeout": "100", "injectArtifactStoreDetails": "true"}}}}}'
]
}
}
附註
Helm Chart 套件仍必須公開格式正確的 registryPath 和 imagePullSecrets 值。
叢集登錄對 registryPath 和 imagePullSecrets 的需求
使用叢集登錄時,映像會從 Azure Container Registry 複製到 Nexus Kubernetes 叢集上的本機 Docker 存放庫。 您可以使用 Webhook 方法在 Pod 作業期間動態注入正確的 registryPath 和 imagePullSecrets 值。 此方法會覆寫 Helm 套件中設定的值。 您仍然必須在參考 registryPath 和 imagePullSecrets 的位置使用合法的虛擬值,通常在 global 的 values.yaml 區段中。
以下 values.yaml 範例顯示了您可以如何提供 registryPath 和 imagePullSecrets 值以與叢集登錄方法相容:
global:
registryPath: "azure.io"
imagePullSecrets: ["abc123"]
附註
如果基礎 Helm 套件中的 registryPath 留空,則 SNS 部署在映像下載期間會失敗。
如需使用叢集登錄的詳細資訊,請參閱概念文件。
不變性限制的建議
不變性限制可防止變更檔案或目錄。 例如,無法變更或重新命名不可變的檔案。 您應該避免使用可變的標籤,例如 latest、 dev 或 stable。 例如,如果 deployment.yaml 將 latest 用於 .Values.image.tag,則部署會失敗。
image: "{{ .Values.global.registryPath }}/{{ .Values.image.repository }}:{{ .Values.image.tag}}"
CRD 宣告和使用分割的建議
我們建議將客戶資源定義 (CRD) 的宣告和使用分割成個別的 Helm Chart,以支援更新。 如需詳細資訊,請參閱有關分離 Chart 的 Helm 文件。
映像版本標記的建議
為確保部署的一致性和可預測性,我們建議對所有容器映像採取以下措施:
- 避免在生產環境中使用
:latest。- 使用 latest 可能會導致非預期的行為,因為 latest 背後的實際映像可能會在未通知的情況下變更。
- 在叢集登錄設定中,如果標籤值變更但標籤名稱保持不變,則叢集登錄不會重新下載更新後的映像。
- 這可能會導致執行過時或不一致的映像。
- 相反地,請始終使用不可變標籤,例如
:1.4.2 - 確保每次組建都產生一個唯一的標籤,不要覆寫現有的標籤。
這些做法有助於防止發生部署問題,並提高可追溯性、復原安全和安全合規性。
nfApplication 順序排序建議
依預設,CNF 應用程式會根據它們出現在 NFDV 中的順序來安裝或更新。 針對刪除作業,CNF 應用程式會以指定的反向順序來刪除。 如果您需要定義與預設值不同的 CNF 應用程式特定順序,請使用 dependsOnProfile 來定義安裝、更新和刪除作業的唯一順序。
如何使用 dependsOnProfile
您可以在 NFDV 中使用 dependsOnProfile 來控制 CNF 應用程式的 Helm 執行順序。 在下列範例中:
- 在安裝作業期間,CNF 應用程式會依下列順序部署:
dummyApplication1、dummyApplication2、dummyApplication。 - 在更新作業期間,CNF 應用程式會依下列順序更新:
dummyApplication2、dummyApplication1、dummyApplication。 - 在刪除工作期間,CNF 應用程式會依下列順序刪除:
dummyApplication2、dummyApplication1、dummyApplication。
{
"location": "eastus",
"properties": {
"networkFunctionTemplate": {
"networkFunctionApplications": [
{
"dependsOnProfile": {
"installDependsOn": [
"dummyApplication1",
"dummyApplication2"
],
"uninstallDependsOn": [
"dummyApplication1"
],
"updateDependsOn": [
"dummyApplication1"
]
},
"name": "dummyApplication"
},
{
"dependsOnProfile": {
"installDependsOn": [
],
"uninstallDependsOn": [
"dummyApplication2"
],
"updateDependsOn": [
"dummyApplication2"
]
},
"name": "dummyApplication1"
},
{
"dependsOnProfile": null,
"name": "dummyApplication2"
}
],
"nfviType": "AzureArcKubernetes"
},
"networkFunctionType": "ContainerizedNetworkFunction"
}
}
dependsOnProfile 的常見錯誤
目前,如果 NFDV 中提供的 dependsOnProfile 程式碼無效,則 NF 作業會失敗,並出現驗證錯誤。 驗證錯誤的訊息會顯示在作業狀態資源中,且看起來類似下列範例:
{
"id": "/providers/Microsoft.HybridNetwork/locations/EASTUS2EUAP/operationStatuses/ca051ddf-c8bc-4cb2-945c-a292bf7b654b*C9B39996CFCD97AB3A121AE136ED47F67BB13946C573EF90628C47628BC5EF5F",
"name": "ca051ddf-c8bc-4cb2-945c-a292bf7b654b*C9B39996CFCD97AB3A121AE136ED47F67BB13946C573EF90628C47628BC5EF5F",
"resourceId": "/subscriptions/aaaa0a0a-bb1b-cc2c-dd3d-eeeeee4e4e4e/resourceGroups/xinrui-publisher/providers/Microsoft.HybridNetwork/networkfunctions/testnfDependsOn02",
"status": "Failed",
"startTime": "2023-07-17T20:48:01.4792943Z",
"endTime": "2023-07-17T20:48:10.0191285Z",
"error": {
"code": "DependenciesValidationFailed",
"message": "CyclicDependencies: Circular dependencies detected at hellotest."
}
}
採用 Helm 4 的最佳實務
自 2016 年 Kubernetes 首次發佈以來,Helm 一直是 Kubernetes 的標準套件管理器。 其演進一路緊隨 Kubernetes 本身的發展:
- Helm v2(2016–2019):引入基於圖表的應用程式封裝,但依賴伺服器端元件(Tiller),造成安全性與多租戶問題。
- Helm v3(2019–2025):移除 Tiller,轉為僅限客戶端的模式,安全性與易用性提升。 此版本成為業界標準,並在保持向下相容的同時累積了漸進式的改進。
經過近六年的 Helm v3 開發,專案累積了技術債務、架構限制和安全挑戰,無法在不引入破壞性變更的情況下解決。 這種情況導致 Helm v4 於 2025 年底釋出。
Helm 4 代表什麼
Helm 4 是一次重要的架構演進,而非漸進式升級。 其主要目標為:
- 與現代 Kubernetes 部署模式對齊
- 移除 Helm v3 的舊有行為
- 提升擴充性、可維護性與安全性
Helm 4 引入的主要變更包括:
- Server-Side 應用(SSA):取代舊有的三方合併方法,並將部署與 Kubernetes 原生的調和語意對齊。
- 重新設計的插件系統:引入更具擴充性的架構,包含可選的基於 WebAssembly 的插件,以提升隔離性與彈性。
- 提升資源追蹤:利用更新的 Kubernetes 狀態機制,如 kstatus,提供更精確的部署狀態報告。
- 內部現代化:消除技術債務,為未來創新與效能提升奠定基礎。
重要的是,Helm 4 維持與現有 Helm v3 圖表的相容性,使組織能逐步採用 Helm 4,無需立即更改圖表或部署產物。
與AOSM出版社的關聯
AOSM團隊計畫透過兩個重要里程碑來支援Helm 4:
- 首先,AOSM 團隊發布了一個包含 Helm 4.1.4 的 NFO 版本,並以「相容模式」運作。此模式保留 Helm 3.18 的行為,因此出版商可在不修改現有圖表或瑕疵的情況下採用 Helm 4。
- 你今天就可以在 UKSouth 實驗室搶先測試這個 NFO 版本。
- 其次,AOSM 團隊發布了 NFO 版本,移除相容性自訂並啟用完整的 Helm 4 行為。 發行者可在準備就緒後採用此版本,但須了解圖表和成品可能需要變更。
- AOSM 團隊計劃於 2026 年第四季將此 NFO 版本供出版商測試。
發佈者在 NFO 安裝期間選擇 Helm 行為時,仍可保有彈性。 NFO 預設為「相容模式」,並提供安裝選項以啟用完整的 Helm 4 行為。 此能力具有叢集範圍,意即叢集內所有部署必須使用相同的 Helm 操作模式。
相容模式細節
以下設定在以「相容模式」運行 Helm 4 時,會保留 Helm 3 的行為:
- 更嚴格的結構驗證
- Helm 4 引入了更嚴格的驗證,在驗證 JSON 陣列時拒絕 Go-type 切片,例如 []map[string]interface{}。 當 NFO 注入 imagePullSecrets 值時,這種行為可能導致失敗。
- NFO 會更新值注入邏輯以改用 []介面{} ,並審核類似的程式碼路徑以確保相容性。
- Server-Side 申請(SSA)預設已啟用
- Helm 4 會在套用資源前,先驗證渲染的清單與叢集 OpenAPI 架構的對照。 包含 Helm 3 先前容忍的無效欄位定義的圖表可能會無法驗證。
- 相容模式會在安裝與升級操作中停用 SSA,以保留 Helm 3 的行為。
- 新的等待模式
- Helm 4 預設採用事件驅動等待模式,需要 Kubernetes 監控權限。 這種行為在沒有必要 RBAC 權限的 Nexus 叢集上可能會失敗。
- 相容模式會將等待行為釘選為 LegacyStrategy,並保留 Helm 3 的輪詢語義。
- 重新建立已移除的項目
- Helm 4 移除了對 Upgrade.Recreate 的支援。 雖然執行期影響預期很低,但否則客戶在 CRD 中設定的值將不再有任何效果。
- 相容模式保留CRD欄位以維持向下相容,但在執行Helm 4操作時會忽略該欄位。
- 結構描述後設綱要確認
- Helm 4 會依據 JSON Schema 後設綱要驗證 values.schema.json。 包含不合規結構定義的圖表會在值驗證前被拒絕。 這種行為已知會影響部分出版商排行榜。
- 相容模式會在安裝和升級作業期間將 SkipSchemaValidation=true 設為 true。