Azure Pipeline中无法将跨步骤变量设置为环境变量
在Azure DevOps的CI/CD流程中,我通过AzurePowerShell任务生成了Databricks访问令牌,并用task.setVariable标记为输出变量。后续的script任务可以正常echo出该令牌,但在AzureCLI@2任务的env:块中设置DATABRICKS_ACCESS_TOKEN时,无法成功传入该令牌。
相关流水线代码如下:
- task: AzurePowerShell@5 displayName: 'Generate Databricks credentials' inputs: azureSubscription: ${{ parameters.azureServiceConnection }} azurePowerShellVersion: 'LatestVersion' ScriptType: 'InlineScript' Inline: | $token = (Get-AzAccessToken -Resource "2ff814a6-3304-4ab8-85cb-cd0e6f879c1d").Token Write-Host "##vso[task.setVariable variable=DATABRICKS_TOKEN;isOutput=true;isSecret=false]$token" name: GenerateTokenStep - script: echo $(GenerateTokenStep.DATABRICKS_TOKEN) <--- 此步骤有效 displayName: 'Echo Databricks token' - task: AzureCLI@2 displayName: "dbt debug" inputs: azureSubscription: ${{ parameters.azureServiceConnection }} ScriptType: bash scriptLocation: inlineScript inlineScript: | echo "dbx token: $(GenerateTokenStep.DATABRICKS_TOKEN)" dbt debug --profiles-dir $(location) env: AZURE_SUBSCRIPTION: $(AZURE_SUBSCRIPTION) DATABRICKS_HOSTNAME: $(DATABRICKS_HOSTNAME) DATABRICKS_HTTP_PATH: $(DATABRICKS_HTTP_PATH) DATABRICKS_SCHEMA: $(DATABRICKS_SCHEMA) DATABRICKS_ACCESS_TOKEN: $(GenerateTokenStep.DATABRICKS_TOKEN) <--- 此设置无效
我尝试过将设置变量的语句改为bash格式的echo "##vso[task.setVariable variable=DATABRICKS_TOKEN;isOutput=true;isSecret=false]$token",但结果依旧无效。
原因分析
Azure DevOps中,env块的变量解析时机早于任务运行时的输出变量生成时机。直接在env块中用$(GenerateTokenStep.DATABRICKS_TOKEN)引用运行时生成的输出变量,会导致解析失败——此时该变量还未被创建。而任务内的inlineScript是在任务运行时执行的,此时输出变量已经生成,所以$(GenerateTokenStep.DATABRICKS_TOKEN)可以正常解析。
解决方法
将环境变量的设置移到AzureCLI@2任务的inlineScript中,通过bash的export命令设置,这样就能正确获取到运行时生成的令牌:
修改后的AzureCLI@2任务代码:
- task: AzureCLI@2 displayName: "dbt debug" inputs: azureSubscription: ${{ parameters.azureServiceConnection }} ScriptType: bash scriptLocation: inlineScript inlineScript: | export DATABRICKS_ACCESS_TOKEN=$(GenerateTokenStep.DATABRICKS_TOKEN) echo "dbx token: $DATABRICKS_ACCESS_TOKEN" dbt debug --profiles-dir $(location) env: AZURE_SUBSCRIPTION: $(AZURE_SUBSCRIPTION) DATABRICKS_HOSTNAME: $(DATABRICKS_HOSTNAME) DATABRICKS_HTTP_PATH: $(DATABRICKS_HTTP_PATH) DATABRICKS_SCHEMA: $(DATABRICKS_SCHEMA)
原理说明
通过export命令在bash脚本内设置的环境变量,会被当前shell会话中的后续命令(比如dbt debug)继承,dbt就能正常读取到DATABRICKS_ACCESS_TOKEN变量的值。
内容的提问来源于stack exchange,提问作者David Backx

