You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Terraform动态创建CodePipeline阶段遇两类错误求助

更新内容

我已修复stages变量问题,terraform plan执行成功,但执行terraform apply时出现新错误:

creating CodePipeline (dev-mgt-mytest-cp): ValidationException: 2
validation errors detected: Value at
'pipeline.stages.1.member.actions.1.member.configuration' failed to
satisfy constraint: Map value must satisfy constraint: [Member must
have length less than or equal to 50000, Member must have length
greater than or equal to 1]; Value at
'pipeline.stages.2.member.actions.1.member.configuration' failed to
satisfy constraint: Map value must satisfy constraint: [Member must
have length less than or equal to 50000, Member must have a length
greater than or equal to 1]

我手动创建无动态阶段的同类型Pipeline可正常运行,不确定是否为Terraform限制,寻求帮助。同时已更新可用变量代码供参考。

原问题

================================================================
我首次尝试用Terraform创建动态CodePipeline阶段,参考网络资料编写代码后,传递stages变量时出现错误:

The given value is not suitable for the module.test_code.var.stages
declared at │ ../dynamic_pipeline/variables.tf:60,1-18: all list
elements must have the same │ type.

第一部分

核心需求是向Pipeline传递动态阶段,解决该问题后将添加新的动态变量。以下是动态模块、模块的variables.tf、测试代码及变量配置:

dynamic_pipeline.tf

resource "aws_codepipeline" "cp_plan_pipeline" {
  name        = "${local.cp_name}-cp"
  role_arn    = var.cp_run_role

  artifact_store {
    type      = var.cp_artifact_type
    location  = var.cp_artifact_bucketname

  }

  dynamic "stage" {
    for_each = [for s in var.stages : {
      name   = s.name
      action = s.action
    } if(lookup(s, "enabled", true))]

    content {
      name = stage.value.name
      dynamic "action" {
        for_each = stage.value.action
        content {
          name             = action.value["name"]
          owner            = action.value["owner"]
          version          = action.value["version"]
          category         = action.value["category"]
          provider         = action.value["provider"]
          run_order        = lookup(action.value, "run_order", null)
          namespace        = lookup(action.value, "namespace", null)
          region           = lookup(action.value, "region", data.aws_region.current.name)
          input_artifacts  = lookup(action.value, "input_artifacts", [])
          output_artifacts = lookup(action.value, "output_artifacts", [])
          configuration    = {
            RepositoryName        = lookup(action.value, "repository_name", null)
            ProjectName           = lookup(action.value, "ProjectName", null)
            BranchName            = lookup(action.value, "branch_name", null)
            PollForSourceChanges  = lookup(action.value, "poll_for_sourcechanges", null)
            OutputArtifactFormat  = lookup(action.value, "ouput_format", null)
          }
          
        }
      }
    }
  }
}

variables.tf

#---------------------------------------------------------------------------------------------------
# General
#---------------------------------------------------------------------------------------------------

variable "region" {
  type        = string
  description = "The AWS Region to be used when deploying region-specific resources (Default: us-east-1)"
  default     = "us-east-1"
}

#---------------------------------------------------------------------------------------------------
# CODEPIPELINE VARIABLES
#---------------------------------------------------------------------------------------------------
variable "cp_name" {
  type        = string
  description = "The name of the codepipline"
}

variable "cp_repo_name" {
  type        = string
  description = "Then name of the repo that will be used as a source repo to trigger builds"
}

variable "cp_branch_name" {
  type        = string
  description = "The branch of the repo that will be watched and used to trigger deployment"
  default     = "development"
}

variable "cp_artifact_bucketname" {
  type        = string
  description = "name of the artifact bucket where articacts are stored."
  default     = "Codepipeline-artifacts-s3"
}

variable "cp_run_role" {
  type        = string
  description = "S3 artifact bucket name."
  
}

variable "cp_artifact_type" {
  type        = string
  description = ""
  default     = "S3"
}

variable "cp_poll_sources" {
  description = "Trigger that lets codepipeline know that it needs to trigger build on change"
  type        = bool
  default     = false
}

variable "cp_ouput_format" {
  type        = string
  description = "Output artifacts format that is used to save the outputs"
  default = "CODE_ZIP"
}

variable "stages" {
  type        = list(object({
    name      = string
    action    = list(object({
      name              = string
      owner             = string
      version           = string
      category          = string
      provider          = string
      run_order         = number
      namespace         = string
      region            = string
      input_artifacts   = list(string)
      output_artifacts  = list(string)
      repository_name   = string
      ProjectName       = string
      branch_name             = string
      poll_for_sourcechanges  = bool
      output_format           = string

    }))
  }))
  
  description = "This list describes each stage of the build"

}

#---------------------------------------------------------------------------------------------------
# ENVIORNMENT VARIABLES
#---------------------------------------------------------------------------------------------------

variable "env" {
  type        = string
  description = "The environment to deploy resources (dev | test | prod | sbx)"
  default     = "dev"
}

variable "tenant" {
  type        = string
  description = "The Service Tenant in which the IaC is being deployed to"
  default     = "dummytenant"
}

variable "project" {
  type        = string
  description = "The Project Name or Acronym. (Note: You should consider setting this in your Enviornment  Variables.)"
}

#---------------------------------------------------------------------------------------------------
# Parameter Store Variables
#---------------------------------------------------------------------------------------------------

variable "bucketlocation" {
  type        = string
  description = "location within the S3 bucket where the State file resides"
}

第二部分

以上为Pipeline核心代码,以下是测试用模块代码,也是触发初始错误的地方:

main.tf

module test_code {

    source          = "../dynamic_pipeline"
    cp_name         = "dynamic-actions" 
    project         = "my_project"
    bucketlocation  = var.backend_bucket_target_name
    cp_run_role     = "arn:aws:iam::xxxxxxxxx:role/cp-deploy-service-role"
    cp_repo_name    = var.repo
    
    stages          = [{  
        name = "part 1"
        action  = [{
            name                    = "Source"
            owner                   = "AWS"
            version                 = "1"
            category                = "Source"
            provider                = "CodeCommit"
            run_order               = 1
            repository_name         = "my_target_repo"
            branch_name             = "main"
            poll_for_sourcechanges  = true
            output_artifacts        = ["CodeWorkspace"]
            ouput_format            = var.cp_ouput_format

        }]
    },
    {
        name = "part 2"
        action  = [{
            run_order               = 1    
            name                    = "Combine_Binaries"
            owner                   = "AWS"
            version                 = "1"
            category                = "Build"
            provider                = "CodeBuild"
            namespace               = "BIN"
            input_artifacts         = ["CodeWorkspace"]
            output_artifacts        = ["CodeSource"]
            ProjectName             = "test_runner"

        }]
    }]
}

测试代码对应的变量文件:

variables.tf

#---------------------------------------------------------------------------------------------------
# CODEPIPELINE VARIABLES
#---------------------------------------------------------------------------------------------------

variable "cp_branch_name" {
  type        = string
  description = "The branch of the repo that will be watched and used to trigger deployment"
  default     = "development"
}

variable "cp_poll_sources" {
  description = "Trigger that lets codepipeline know that it needs to trigger build on change"
  type        = bool
  default     = false
}

variable "cp_ouput_format" {
  type        = string
  description = "Output artifacts format that is used to save the outputs. Values can be CODEBUILD_CLONE_REF or CODE_ZIP"
  default = "CODE_ZIP"
}

variable "backend_bucket_target_name" {

  type        = string
  description = "The folder name where the state file is stored for the pipeline"
  default     = "dynamic-test-pl"

}

variable "repo" {
  type        = string
  description = "name of the repo the pipeine is managing"
  default = "my_target_repo"
  
}

我首次接触Terraform的列表和映射用法,确定初始错误与变量传递方式有关,希望得到排查指导与解决方案。


内容的提问来源于stack exchange,提问作者Maxamis4

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.08.13 08:40:25