Azure devops 在Azure管道构建中使用Azure Repos git模块源进行身份验证
我目前正在为Azure DevOps创建一个管道,以验证Terraform配置并将其应用于不同的订阅 我的terraform配置使用模块,这些模块“托管”在与terraform配置相同的Azure DevOps项目中的其他存储库中 不幸的是,当我试图执行Azure devops 在Azure管道构建中使用Azure Repos git模块源进行身份验证,azure-devops,terraform,azure-pipelines,azure-repos,Azure Devops,Terraform,Azure Pipelines,Azure Repos,我目前正在为Azure DevOps创建一个管道,以验证Terraform配置并将其应用于不同的订阅 我的terraform配置使用模块,这些模块“托管”在与terraform配置相同的Azure DevOps项目中的其他存储库中 不幸的是,当我试图执行terraforminit获取这些模块时,管道任务“挂起”在那里等待凭证输入 按照中的建议,我尝试使用persistCredentials:true属性添加checkout步骤 从我在任务日志(见下文)中看到的情况来看,凭证信息专门添加到当前回购
terraforminit
获取这些模块时,管道任务“挂起”在那里等待凭证输入
按照中的建议,我尝试使用persistCredentials:true
属性添加checkout
步骤
从我在任务日志(见下文)中看到的情况来看,凭证信息专门添加到当前回购协议中,不可用于其他回购协议
添加持久凭据时执行的命令:true
2018-10-22T14:06:54.4347764Z ##[command]git config http.https://my-org@dev.azure.com/my-org/my-project/_git/my-repo.extraheader "AUTHORIZATION: bearer ***"
terraform初始化任务的输出
2018-10-22T14:09:24.1711473Z terraform init -input=false
2018-10-22T14:09:24.2761016Z Initializing modules...
2018-10-22T14:09:24.2783199Z - module.my-module
2018-10-22T14:09:24.2786455Z Getting source "git::https://my-org@dev.azure.com/my-org/my-project/_git/my-module-repo?ref=1.0.2"
如何设置git凭据以用于其他存储库?我认为您不能。通常,您创建另一个构建并链接到该构建中的工件,以便在当前定义中使用它。这样,您就不需要连接到不同的Git存储库我也遇到了同样的问题,我最终做的是在terraform配置中标记化
SYSTEM\u ACCESSTOKEN
。我在Azure DevOps中使用了Tokenzization任务,其中使用前缀和后缀来识别并用实际变量替换标记(它是可自定义的,但我发现双下划线最适合于不干扰我拥有的任何代码)
类似于find$(Build.SourcesDirectory)/-typef-name'main.tf'-exec sed-i's~\uuuuu系统\uu访问令牌\uuuuu~$(SYSTEM.ACCESSTOKEN)~g'{}\如果您无法将自定义扩展安装到DevOps组织,则代码>也可以工作
我的terraform main.tf如下所示:
module "app" {
source = "git::https://token:__SYSTEM_ACCESSTOKEN__@dev.azure.com/actualOrgName/actualProjectName/_git/TerraformModules//azure/app-service?ref=__app-service-module-ver__"
....
}
它并不漂亮,但它完成了任务。模块源(在编写本文时)不支持terraform的变量输入。所以我们能做的就是使用Terrafile它是一个开源项目,通过在代码旁边保留一个简单的YAML文件,帮助您跟上模块和同一模块的不同版本。它似乎不再被积极维护,但它只是工作:
我的Terrafile示例:
app:
source: "https://token:__SYSTEM_ACCESSTOKEN__@dev.azure.com/actualOrgName/actualProjectName/_git/TerraformModules"
version: "feature/handle-twitter"
app-stable:
source: "https://token:__SYSTEM_ACCESSTOKEN__@dev.azure.com/actualOrgName/actualProjectName/_git/TerraformModules"
version: "1.0.5"
默认情况下,Terrafile将您的模块下载到./vendor目录,这样您就可以将模块源指向以下位置:
module "app" {
source = "./vendor/modules/app-stable/azure/app_service"
....
}
现在,您只需了解如何在terrafile所在的目录中执行terrafile
命令。
My azure.pipelines.yml示例:
- script: curl -L https://github.com/coretech/terrafile/releases/download/v0.6/terrafile_0.6_Linux_x86_64.tar.gz | tar xz -C $(Agent.ToolsDirectory)
displayName: Install Terrafile
- script: |
cd $(Build.Repository.LocalPath)
$(Agent.ToolsDirectory)/terrafile
displayName: Download required modules
是我干的
_ado_token.ps1
# used in Azure DevOps to allow terrform to auth with Azure DevOps GIT repos
$tfmodules = Get-ChildItem $PSScriptRoot -Recurse -Filter "*.tf"
foreach ($tfmodule in $tfmodules) {
$content = [System.IO.File]::ReadAllText($tfmodule.FullName).Replace("git::https://myorg@","git::https://" + $env:SYSTEM_ACCESSTOKEN +"@")
[System.IO.File]::WriteAllText($tfmodule.FullName, $content)
}
azure-pipelines.yml
- task: PowerShell@2
env:
SYSTEM_ACCESSTOKEN: $(System.AccessToken)
inputs:
filePath: '_ado_token.ps1'
pwsh: true
displayName: '_ado_token.ps1'
基本上有两种方法
先决条件
确保阅读并根据需要应用“在脚本中运行Git命令”文档中的部分
解决方案1:在管道运行时动态插入System.AccessToken
(或PAT,但我不推荐)
您可以通过以下方式来解决此问题:
- 在代码中插入替换令牌,如
\uu系统\u访问令牌
(如建议),并使用一些令牌替换代码或qetza.replaceTokes.replaceTokes任务。replaceTokes
任务插入值。此解决方案的缺点是,在本地运行terraform
时,还必须替换令牌
- 使用一些代码替换所有
git::https://dev.azure.com
带有git:的文本:https://YOUR_ACCESS_TOKEN@dev.azure.com
我使用了第二种方法,使用了下面的bash任务脚本(它搜索terragrunt
文件,但您可以适应terraform
文件,而无需做太多更改):
提供一个PowerShell脚本来执行类似的操作
但是,如果您的terraform
modulesgit
repo中的模块在另一个git
repo中调用自己的模块,则这种类型的解决方案不起作用,这就是我们的情况
解决方案2:在您的terraform
modulesgit
repos的url的extraheader
中全局添加访问令牌
这样,所有模块的repo(由您的代码直接调用或由被调用模块的代码间接调用)都将能够使用您的访问令牌。为此,我在您的terraform
/terragrunt
调用之前添加了以下步骤:
- bash: |
git config --global http.https://dev.azure.com/<your-org>/<your-first-repo-project>/_git/<your-first-repo>.extraheader "AUTHORIZATION: bearer $(System.AccessToken)"
git config --global http.https://dev.azure.com/<your-org>/<your-second-repo-project>/_git/<your-second-repo>.extraheader "AUTHORIZATION: bearer $(System.AccessToken)"
- bash: |
find $(Build.SourcesDirectory)/ -type f -name 'terragrunt.hcl' -exec sed -i 's~git::https://dev.azure.com~git::https://$(System.AccessToken)@dev.azure.com~g' {} \;
- bash: |
git config --global http.https://dev.azure.com/<your-org>/<your-first-repo-project>/_git/<your-first-repo>.extraheader "AUTHORIZATION: bearer $(System.AccessToken)"
git config --global http.https://dev.azure.com/<your-org>/<your-second-repo-project>/_git/<your-second-repo>.extraheader "AUTHORIZATION: bearer $(System.AccessToken)"
- bash: |
git config --global --unset-all http.https://dev.azure.com/<your-org>/<your-first-repo-project>/_git/<your-first-repo>.extraheader
git config --global --unset-all http.https://dev.azure.com/<your-org>/<your-second-repo-project>/_git/<your-second-repo>.extraheader