前言
在 Serverless 應用開發中,多環境配置是一個繞不開的話題。從開發、測試到生產,每個環境都有其特定的配置需求。阿里云 Serverless Devs 雖然提供了官方的 env
命令來管理多環境,但在實際使用中,我發現官方方案存在一些局限性。
本文將通過四個實際案例,展示 Serverless FC 多環境配置的演進過程,從基礎驗證到最終的最佳實踐方案。通過對比分析,幫助開發者選擇最適合的多環境配置策略。
技術背景
多環境配置的核心挑戰
在 Serverless 架構中,多環境配置面臨以下挑戰:
- 配置復用:避免在不同環境中重復相同的配置
- 環境隔離:確保不同環境的配置相互獨立
- 靈活配置:支持動態配置和敏感信息管理
- 維護成本:降低配置管理的復雜度
Serverless Devs 多環境支持現狀
Serverless Devs 提供了兩種多環境配置方式:
- 官方 env 命令:通過
env.yaml
集中管理所有環境配置 - 自定義方案:通過模板繼承、環境變量等方式實現
項目架構設計
代碼地址:practice_serverlsess/p07
項目整體結構
我們的測試項目包含四個不同的多環境配置方案:
p07/
├── a/ # 方案一:模板元數據
│ ├── s.yaml
│ └── code/
├── b/ # 方案二:環境變量配置
│ ├── s.yaml
│ └── code/
├── c/ # 方案三:模板繼承
│ ├── s.yaml
│ ├── s-dev.yaml
│ ├── s-prod.yaml
│ └── code/
├── d/ # 方案四:綜合方案(推薦)
│ ├── s.yaml
│ ├── s-dev.yaml
│ ├── s-prod.yaml
│ └── code/
└── readme.md
方案驗證:從基礎到高級
方案一:模板元數據驗證
驗證目的:理解 template
字段的配置復用能力
# a/s.yaml
edition: 3.0.**0**
name: fc3-example
access: default
vars:projectName: practice-07
template:# 模板信息t1:# 模板名稱region: cn-shenzhentimeout: 60diskSize: 512internetAccess: trueruntime: python3.10cpu: 0.35memorySize: 512
resources:index:component: fc3extend:name: t1props:handler: index.handlerfunctionName: ${vars.projectName}-${this.name}code: ./code
運行結果:
$ s preview
edition: 3.0.0
name: fc3-example
access: default
vars: projectName: practice-07
template: t1: region: cn-shenzhentimeout: 60diskSize: 512internetAccess: trueruntime: python3.10cpu: 0.35memorySize: 512
resources: index: component: fc3extend: name: t1props: region: cn-shenzhentimeout: 60diskSize: 512internetAccess: trueruntime: python3.10cpu: 0.35memorySize: 512handler: index.handlerfunctionName: practice-07-indexcode: ./code
驗證結論:
- ? 解決了配置重復問題
- ? 缺乏環境差異化能力
- ? 所有環境使用相同配置
方案二:環境變量驗證
驗證目的:理解環境變量的動態配置能力
# b/s.yaml
edition: 3.0.0
name: fc3-example
access: default
vars:projectName: practice-07
resources:index:component: fc3props:handler: index.handlerfunctionName: ${vars.projectName}-${this.name}-${env('DEV_ENV')}code: ./coderegion: cn-shenzhenruntime: python3.10environmentVariables:env: ${env('DEV_ENV')}tags:env: ${env('DEV_ENV')}
運行結果:
$ DEV_ENV='abc' s preview
edition: 3.0.0
name: fc3-example
access: default
vars: projectName: practice-07
resources: index: component: fc3props: handler: index.handlerfunctionName: practice-07-index-abccode: ./coderegion: cn-shenzhenruntime: python3.10environmentVariables: env: abctags: env: abc
驗證結論:
- ? 提供了靈活性
- ? 支持動態配置
- ? 配置管理復雜
- ? 需要手動管理環境變量
💡 對于非常簡單的項目,配置是有規律,也是可以使用這種方式進行配置。
方案三:模板繼承驗證
驗證目的:理解 extend
字段的環境隔離能力
# c/s.yaml - 基礎配置
edition: 3.0.0
name: fc3-example
access: default
vars:projectName: practice-07
resources:index:component: fc3props:handler: index.handlerfunctionName: ${vars.projectName}-${this.name}code: ./coderegion: cn-shenzheninternetAccess: trueruntime: python3.10
# c/s-prod.yaml - 生產環境配置
extend: s.yaml
resources:index:props:handler: ${this.name}.handlerfunctionName: ${vars.projectName}-${this.name}-prodcode: ./codeenvironmentVariables:DEV_ENV: env-prodtags:TAG1: tag-prod
運行結果:
$ s preview -t s-prod.yaml
edition: 3.0.0
name: fc3-example
access: default
vars: projectName: practice-07
resources: index: component: fc3props: handler: index.handlerfunctionName: practice-07-index-prodcode: ./coderegion: cn-shenzheninternetAccess: trueruntime: python3.10environmentVariables: DEV_ENV: env-prodtags: TAG1: tag-prod
驗證結論:
- ? 實現了環境隔離
- ? 配置文件結構清晰
- ? 仍有配置冗余,當 resources 越來越多的時候,
s.yaml
就會越來越繁瑣 - ? 有一定的動態配置能力
💡 對于簡單的項目,多環境的配置方法,已經是足夠了。
最佳實踐:方案四深度解析
設計理念
方案四完美結合了前三個方案的優點:
- 模板元數據:解決配置復用問題
- 模板繼承:實現環境隔離
- 環境變量:提供靈活配置
代碼架構分析
基礎配置:d/s.yaml
edition: 3.0.0
name: fc3-example
access: default
vars:projectName: practice-07
template:# 模板信息t1:# 模板名稱region: cn-shenzheninternetAccess: trueruntime: python3.10tags:project: ${vars.projectName}
resources:index:component: fc3extend:name: t1props:handler: index.handlerfunctionName: ${vars.projectName}-${this.name}code: ./code
開發環境配置:d/s-dev.yaml
extend: s.yaml
resources:index:props:environmentVariables:DEV_ENV: env-devtags:TAG1: tag-dev
生產環境配置:d/s-prod.yaml
extend: s.yaml
resources:index:props:environmentVariables:DEV_ENV: ${env('DEV_ENV')}tags:TAG1: ${env('TAG1')}
運行結果分析
$ TAG1='tag-prod' DEV_ENV='prod' s preview -t s-prod.yaml
edition: 3.0.0
name: fc3-example
access: default
vars: projectName: practice-07
template: t1: region: cn-shenzheninternetAccess: trueruntime: python3.10tags: project: practice-07
resources: index: component: fc3extend: name: t1props: region: cn-shenzheninternetAccess: trueruntime: python3.10tags: project: practice-07TAG1: tag-prodhandler: index.handlerfunctionName: practice-07-indexcode: ./codeenvironmentVariables: DEV_ENV: prod
核心優勢
- ? 配置復用:通過模板元數據避免重復
- ? 環境隔離:通過文件分離實現清晰隔離
- ? 靈活配置:通過環境變量處理敏感信息
- ? 易于維護:配置文件結構清晰
官方 env 命令的局限性分析
為什么不使用官方的 env
命令呢?
官方方案介紹
Serverless Devs 提供了 env
命令來管理多環境:
# 初始化環境
s env init --name dev# 設置默認環境
s env default --name dev# 使用環境部署
s deploy --env dev
核心缺陷
1. 配置集中化問題
所有環境配置都集中在 env.yaml
中,隨著環境增多,配置文件變得臃腫難維護。
2. 插入環境變量不夠靈活
有些環境的變量是在文件中保存中保存的,有些是從環境變量中來的。
🤬🤬🤬 吐槽一波官方的 yaml
格式,繼承和覆蓋 過于強綁定,不夠靈活,無法沿用之前的 yaml
理解。
方案四的實際應用
開發環境部署
# 開發環境部署,配置都是寫死的
s deploy -t s-dev.yaml
生產環境部署
# 生產環境部署,部分的敏感信息可以在環境變量從傳入的
TAG1='prod' DEV_ENV='production' s deploy -t s-prod.yaml
環境切換策略
# 快速切換環境
alias deploy-dev="TAG1='dev' DEV_ENV='development' s deploy -t s-dev.yaml"
alias deploy-prod="TAG1='prod' DEV_ENV='production' s deploy -t s-prod.yaml"
高級配置技巧
敏感信息處理
通過環境變量管理密鑰、數據庫連接等敏感信息:
# s-prod.yaml
extend: s.yaml
resources:index:props:environmentVariables:DATABASE_URL: ${env('DATABASE_URL')}API_KEY: ${env('API_KEY')}SECRET_TOKEN: ${env('SECRET_TOKEN')}
配置驗證
使用 s preview
驗證配置正確性:
# 驗證開發環境配置
s preview -t s-dev.yaml# 驗證生產環境配置
TAG1='prod' DEV_ENV='production' s preview -t s-prod.yaml
最佳實踐總結
推薦方案
方案四作為生產環境標準配置,完美解決了多環境配置的核心問題。
配置原則
- 基礎配置模板化:通過
template
字段實現配置復用 - 環境差異文件化:增加多個環境的 yaml 文件,通過
extend
字段實現環境隔離,同時每個文件都是獨立的 - 敏感信息環境變量化:通過
env()
函數處理敏感配置
文件組織
project/
├── s.yaml # 基礎配置 + 模板元數據
├── s-dev.yaml # 開發環境差異配置
├── s-prod.yaml # 生產環境差異配置
└── code/ # 業務代碼
部署命令標準化
# 開發環境
DEV_ENV='dev' s deploy -t s-dev.yaml# 生產環境
DEV_ENV='prod' s deploy -t s-prod.yaml
總結
方案回顧
通過四個方案的演進,我們看到了 Serverless 多環境配置的完整路徑:
- 方案一:驗證了模板元數據的配置復用能力
- 方案二:驗證了環境變量的動態配置能力
- 方案三:驗證了模板繼承的環境隔離能力
- 方案四:綜合前三者優點,形成最佳實踐
核心價值
方案四解決了多環境配置的關鍵問題:
- 配置復用:避免重復配置
- 環境隔離:確保環境獨立
- 靈活配置:支持動態配置
- 易于維護:結構清晰,便于管理
寄語
沒有方案是完美的,大家可以根據自己情況,挑選一個合適自己的方案。
參考資料
- Serverless Devs 官方文檔 - 描述文件格式/規范
- Serverless Devs 官方文檔 - Env 多環境配置
- Serverless Devs 官方文檔 - 如何解決yaml配置重復冗余的問題
- 項目代碼倉庫 - practice_serverlsess/p07
- 阿里云函數計算官方文檔