Skip to content

Commit

Permalink
add depends_on; fix execution_order_group 0. (#320)
Browse files Browse the repository at this point in the history
* add depends_on; fix execution_order_group 0.
  • Loading branch information
pseudomorph authored Apr 25, 2024
1 parent dc05a21 commit bec44ce
Show file tree
Hide file tree
Showing 9 changed files with 205 additions and 16 deletions.
3 changes: 2 additions & 1 deletion README.md
Original file line number Diff line number Diff line change
Expand Up @@ -48,7 +48,7 @@ Then, make sure `terragrunt-atlantis-config` is present on your Atlantis server.

```hcl
variable "terragrunt_atlantis_config_version" {
default = "1.17.9"
default = "1.18.0"
}
build {
Expand Down Expand Up @@ -132,6 +132,7 @@ One way to customize the behavior of this module is through CLI flag values pass
| `--filter` | Path or glob expression to the directory you want scope down the config for. Default is all files in root | "" |
| `--num-executors` | Number of executors used for parallel generation of projects. Default is 15 | 15 |
| `--execution-order-groups` | Computes execution_order_group for projects | false |
| `--depends-on` | Computes depends_on for projects. Project names are required. | false |

## Project generation

Expand Down
5 changes: 4 additions & 1 deletion cmd/config.go
Original file line number Diff line number Diff line change
Expand Up @@ -54,7 +54,10 @@ type AtlantisProject struct {
ApplyRequirements *[]string `json:"apply_requirements,omitempty"`

// Atlantis use ExecutionOrderGroup for sort projects before applying/planning
ExecutionOrderGroup int `json:"execution_order_group,omitempty"`
ExecutionOrderGroup *int `json:"execution_order_group,omitempty"`

// Atlantis uses DependsOn to define dependencies between projects
DependsOn []string `json:"depends_on,omitempty"`
}

// Autoplan settings for which plans affect other plans
Expand Down
46 changes: 33 additions & 13 deletions cmd/generate.go
Original file line number Diff line number Diff line change
Expand Up @@ -817,7 +817,7 @@ func main(cmd *cobra.Command, args []string) error {
// Sort the projects in config by Dir
sort.Slice(config.Projects, func(i, j int) bool { return config.Projects[i].Dir < config.Projects[j].Dir })

if executionOrderGroups {
if executionOrderGroups || dependsOn {
projectsMap := make(map[string]*AtlantisProject, len(config.Projects))
for i := range config.Projects {
projectsMap[config.Projects[i].Dir] = &config.Projects[i]
Expand All @@ -829,9 +829,10 @@ func main(cmd *cobra.Command, args []string) error {
hasChanges = false
for _, project := range config.Projects {
executionOrderGroup := 0
dependsOnList := []string{}
// choose order group based on dependencies
for _, dep := range project.Autoplan.WhenModified {
depPath := filepath.Dir(filepath.Join(project.Dir, dep))
depPath := filepath.ToSlash(filepath.Dir(filepath.Join(project.Dir, dep)))
if depPath == project.Dir {
// skip dependency on oneself
continue
Expand All @@ -842,12 +843,20 @@ func main(cmd *cobra.Command, args []string) error {
// skip not project dependencies
continue
}
if depProject.ExecutionOrderGroup+1 > executionOrderGroup {
executionOrderGroup = depProject.ExecutionOrderGroup + 1
if depProject.ExecutionOrderGroup != nil {
if *depProject.ExecutionOrderGroup+1 > executionOrderGroup {
executionOrderGroup = *depProject.ExecutionOrderGroup + 1
}
}
dependsOnList = append(dependsOnList, depProject.Name)
}
if projectsMap[project.Dir].ExecutionOrderGroup != executionOrderGroup {
projectsMap[project.Dir].ExecutionOrderGroup = executionOrderGroup
if projectsMap[project.Dir].ExecutionOrderGroup == nil || *projectsMap[project.Dir].ExecutionOrderGroup != executionOrderGroup {
if executionOrderGroups {
projectsMap[project.Dir].ExecutionOrderGroup = &executionOrderGroup
}
if dependsOn {
projectsMap[project.Dir].DependsOn = dependsOnList
}
// repeat the main cycle when changed some project
hasChanges = true
}
Expand All @@ -860,12 +869,14 @@ func main(cmd *cobra.Command, args []string) error {
}

// Sort by execution_order_group
sort.Slice(config.Projects, func(i, j int) bool {
if config.Projects[i].ExecutionOrderGroup == config.Projects[j].ExecutionOrderGroup {
return config.Projects[i].Dir < config.Projects[j].Dir
}
return config.Projects[i].ExecutionOrderGroup < config.Projects[j].ExecutionOrderGroup
})
if executionOrderGroups {
sort.Slice(config.Projects, func(i, j int) bool {
if *config.Projects[i].ExecutionOrderGroup == *config.Projects[j].ExecutionOrderGroup {
return config.Projects[i].Dir < config.Projects[j].Dir
}
return *config.Projects[i].ExecutionOrderGroup < *config.Projects[j].ExecutionOrderGroup
})
}
}

// Convert config to YAML string
Expand Down Expand Up @@ -914,13 +925,21 @@ var createHclProjectChilds bool
var createHclProjectExternalChilds bool
var useProjectMarkers bool
var executionOrderGroups bool
var dependsOn bool

// generateCmd represents the generate command
var generateCmd = &cobra.Command{
Use: "generate",
Short: "Makes atlantis config",
Long: `Logs Yaml representing Atlantis config to stderr`,
RunE: main,
// Test is needed to confirm that if --depends on is set, --create-project-name is also set.
PreRun: func(cmd *cobra.Command, args []string) {
dependsOn, _ := cmd.Flags().GetBool("depends-on")
if dependsOn {
cmd.MarkFlagRequired("create-project-name")
}
},
RunE: main,
}

func init() {
Expand Down Expand Up @@ -954,6 +973,7 @@ func init() {
generateCmd.PersistentFlags().BoolVar(&createHclProjectExternalChilds, "create-hcl-project-external-childs", true, "Creates Atlantis projects for terragrunt child modules outside the directories containing the HCL files defined in --project-hcl-files")
generateCmd.PersistentFlags().BoolVar(&useProjectMarkers, "use-project-markers", false, "Creates Atlantis projects only for project hcl files with locals: atlantis_project = true")
generateCmd.PersistentFlags().BoolVar(&executionOrderGroups, "execution-order-groups", false, "Computes execution_order_groups for projects")
generateCmd.PersistentFlags().BoolVar(&dependsOn, "depends-on", false, "Computes depends_on for projects. Requires --create-project-name.")
}

// Runs a set of arguments, returning the output
Expand Down
21 changes: 21 additions & 0 deletions cmd/generate_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -44,6 +44,8 @@ func resetForRun() error {
createHclProjectChilds = false
createHclProjectExternalChilds = true
useProjectMarkers = false
executionOrderGroups = false
dependsOn = false

return nil
}
Expand Down Expand Up @@ -639,3 +641,22 @@ func TestWithExecutionOrderGroups(t *testing.T) {
"--execution-order-groups",
})
}

func TestWithExecutionOrderGroupsAndDependsOn(t *testing.T) {
runTest(t, filepath.Join("golden", "withExecutionOrderGroupsAndDependsOn.yaml"), []string{
"--root",
filepath.Join("..", "test_examples", "chained_dependencies"),
"--execution-order-groups",
"--depends-on",
"--create-project-name",
})
}

func TestWithDependsOn(t *testing.T) {
runTest(t, filepath.Join("golden", "withDependsOn.yaml"), []string{
"--root",
filepath.Join("..", "test_examples", "chained_dependencies"),
"--depends-on",
"--create-project-name",
})
}
45 changes: 45 additions & 0 deletions cmd/golden/withDependsOn.yaml
Original file line number Diff line number Diff line change
@@ -0,0 +1,45 @@
parallel_apply: true
parallel_plan: true
projects:
- autoplan:
enabled: false
when_modified:
- '*.hcl'
- '*.tf*'
dir: dependency
name: dependency
- autoplan:
enabled: false
when_modified:
- '*.hcl'
- '*.tf*'
- ../dependency/terragrunt.hcl
depends_on:
- dependency
dir: depender
name: depender
- autoplan:
enabled: false
when_modified:
- '*.hcl'
- '*.tf*'
- ../depender/terragrunt.hcl
- ../dependency/terragrunt.hcl
- nested/terragrunt.hcl
depends_on:
- depender
- dependency
- depender_on_depender_nested
dir: depender_on_depender
name: depender_on_depender
- autoplan:
enabled: false
when_modified:
- '*.hcl'
- '*.tf*'
- ../../dependency/terragrunt.hcl
depends_on:
- dependency
dir: depender_on_depender/nested
name: depender_on_depender_nested
version: 3
1 change: 1 addition & 0 deletions cmd/golden/withExecutionOrderGroups.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -8,6 +8,7 @@ projects:
- '*.hcl'
- '*.tf*'
dir: dependency
execution_order_group: 0
- autoplan:
enabled: false
when_modified:
Expand Down
49 changes: 49 additions & 0 deletions cmd/golden/withExecutionOrderGroupsAndDependsOn.yaml
Original file line number Diff line number Diff line change
@@ -0,0 +1,49 @@
parallel_apply: true
parallel_plan: true
projects:
- autoplan:
enabled: false
when_modified:
- '*.hcl'
- '*.tf*'
dir: dependency
execution_order_group: 0
name: dependency
- autoplan:
enabled: false
when_modified:
- '*.hcl'
- '*.tf*'
- ../dependency/terragrunt.hcl
depends_on:
- dependency
dir: depender
execution_order_group: 1
name: depender
- autoplan:
enabled: false
when_modified:
- '*.hcl'
- '*.tf*'
- ../../dependency/terragrunt.hcl
depends_on:
- dependency
dir: depender_on_depender/nested
execution_order_group: 1
name: depender_on_depender_nested
- autoplan:
enabled: false
when_modified:
- '*.hcl'
- '*.tf*'
- ../depender/terragrunt.hcl
- ../dependency/terragrunt.hcl
- nested/terragrunt.hcl
depends_on:
- depender
- dependency
- depender_on_depender_nested
dir: depender_on_depender
execution_order_group: 2
name: depender_on_depender
version: 3
2 changes: 1 addition & 1 deletion main.go
Original file line number Diff line number Diff line change
Expand Up @@ -5,7 +5,7 @@ import "github.com/transcend-io/terragrunt-atlantis-config/cmd"
// This variable is set at build time using -ldflags parameters.
// But we still set a default here for those using plain `go get` downloads
// For more info, see: http://stackoverflow.com/a/11355611/483528
var VERSION string = "1.17.9"
var VERSION string = "1.18.0"

func main() {
cmd.Execute(VERSION)
Expand Down
49 changes: 49 additions & 0 deletions out
Original file line number Diff line number Diff line change
@@ -0,0 +1,49 @@
automerge: false
parallel_apply: true
parallel_plan: true
projects:
- autoplan:
enabled: false
when_modified:
- '*.hcl'
- '*.tf*'
dir: dependency
execution_order_group: 0
name: dependency
- autoplan:
enabled: false
when_modified:
- '*.hcl'
- '*.tf*'
- ../dependency/terragrunt.hcl
depends_on:
- dependency
dir: depender
execution_order_group: 1
name: depender
- autoplan:
enabled: false
when_modified:
- '*.hcl'
- '*.tf*'
- ../../dependency/terragrunt.hcl
depends_on:
- dependency
dir: depender_on_depender/nested
execution_order_group: 1
name: depender_on_depender_nested
- autoplan:
enabled: false
when_modified:
- '*.hcl'
- '*.tf*'
- ../depender/terragrunt.hcl
- ../dependency/terragrunt.hcl
- nested/terragrunt.hcl
depends_on:
- depender
- dependency
dir: depender_on_depender
execution_order_group: 2
name: depender_on_depender
version: 3

0 comments on commit bec44ce

Please sign in to comment.