├── .appveyor.yml ├── .config └── dotnet-tools.json ├── .editorconfig ├── .gitattributes ├── .github ├── CODE_OF_CONDUCT.md ├── CONTRIBUTING.md ├── ISSUE_TEMPLATE.md ├── PULL_REQUEST_TEMPLATE.md ├── renovate.json └── workflows │ ├── build.yml │ └── codeql-analysis.yml ├── .gitignore ├── GitReleaseManager.yaml ├── LICENSE ├── README.md ├── build.ps1 ├── build.sh ├── config.wyam ├── docs ├── index.md ├── input │ ├── assets │ │ ├── css │ │ │ └── override.css │ │ ├── images │ │ │ └── clippy.svg │ │ └── js │ │ │ ├── anchor.min.js │ │ │ └── clipboard.min.js │ ├── blog │ │ ├── initial-release.md │ │ ├── release-0-3-0.md │ │ └── release-0.1.1.md │ ├── docs │ │ ├── index.cshtml │ │ └── usage │ │ │ ├── examples.md │ │ │ └── index.cshtml │ └── index.cshtml └── packages.xml ├── recipe.cake └── src ├── Cake.Terraform.Tests ├── Cake.Terraform.Tests.csproj ├── TerraformApplyTests.cs ├── TerraformDestroyTests.cs ├── TerraformEnvListTests.cs ├── TerraformFixture.cs ├── TerraformInitTests.cs ├── TerraformOutputTests.cs ├── TerraformPlanTests.cs ├── TerraformRefreshTests.cs ├── TerraformShowTests.cs └── TerraformValidateTests.cs ├── Cake.Terraform.sln ├── Cake.Terraform ├── Apply │ ├── TerraformApplyRunner.cs │ └── TerraformApplySettings.cs ├── Cake.Terraform.csproj ├── Destroy │ ├── TerraformDestroyRunner.cs │ └── TerraformDestroySettings.cs ├── EnvDelete │ ├── TerraformEnvDeleteRunner.cs │ └── TerraformEnvDeleteSettings.cs ├── EnvList │ ├── TerraformEnvListRunner.cs │ └── TerraformEnvListSettings.cs ├── EnvNew │ ├── TerraformEnvNewRunner.cs │ └── TerraformEnvNewSettings.cs ├── EnvSelect │ ├── TerraformEnvSelectRunner.cs │ └── TerraformEnvSelectSettings.cs ├── Init │ ├── TerraformInitRunner.cs │ └── TerraformInitSettings.cs ├── Output │ ├── TerraformOutputRunner.cs │ └── TerraformOutputSettings.cs ├── Plan │ ├── TerraformPlanRunner.cs │ └── TerraformPlanSettings.cs ├── Refresh │ ├── TerraformRefreshRunner.cs │ └── TerraformRefreshSettings.cs ├── Show │ ├── HtmlFormatter.cs │ ├── OutputFormat.cs │ ├── OutputFormatter.cs │ ├── PlainTextFormatter.cs │ ├── TerraformShowRunner.cs │ └── TerraformShowSettings.cs ├── TerraformAliases.cs ├── TerraformEnvSettings.cs ├── TerraformRunner.cs ├── TerraformSettings.cs └── Validate │ └── TerraformValidateRunner.cs ├── Directory.Build.props └── Directory.Build.targets /.appveyor.yml: -------------------------------------------------------------------------------- 1 | #---------------------------------# 2 | # Build Image # 3 | #---------------------------------# 4 | image: Visual Studio 2022 5 | 6 | #---------------------------------# 7 | # Install .NET # 8 | #---------------------------------# 9 | install: 10 | - ps: $env:DOTNET_INSTALL_DIR = "$pwd\.dotnetsdk" 11 | - ps: mkdir $env:DOTNET_INSTALL_DIR -Force | Out-Null 12 | - ps: Invoke-WebRequest -Uri "https://dotnet.microsoft.com/download/dotnet/scripts/v1/dotnet-install.ps1" -OutFile "$($env:DOTNET_INSTALL_DIR)/dotnet-install.ps1" 13 | - ps: '& "$($env:DOTNET_INSTALL_DIR)/dotnet-install.ps1" -Channel 2.1 -InstallDir $env:DOTNET_INSTALL_DIR' 14 | - ps: '& "$($env:DOTNET_INSTALL_DIR)/dotnet-install.ps1" -Channel 3.1 -InstallDir $env:DOTNET_INSTALL_DIR' 15 | - ps: '& "$($env:DOTNET_INSTALL_DIR)/dotnet-install.ps1" -Channel 5.0 -InstallDir $env:DOTNET_INSTALL_DIR' 16 | - ps: '& "$($env:DOTNET_INSTALL_DIR)/dotnet-install.ps1" -Channel 6.0 -InstallDir $env:DOTNET_INSTALL_DIR' 17 | - ps: '& "$($env:DOTNET_INSTALL_DIR)/dotnet-install.ps1" -Channel 7.0 -InstallDir $env:DOTNET_INSTALL_DIR' 18 | - ps: '& "$($env:DOTNET_INSTALL_DIR)/dotnet-install.ps1" -Channel 8.0 -InstallDir $env:DOTNET_INSTALL_DIR' 19 | - ps: $env:Path = "$env:DOTNET_INSTALL_DIR;$env:Path" 20 | - ps: dotnet --info 21 | 22 | #---------------------------------# 23 | # Build Script # 24 | #---------------------------------# 25 | build_script: 26 | - ps: .\build.ps1 --target=CI 27 | 28 | #---------------------------------# 29 | # Tests 30 | #---------------------------------# 31 | test: off 32 | 33 | #---------------------------------# 34 | # Pull Requests # 35 | #---------------------------------# 36 | pull_requests: 37 | do_not_increment_build_number: true 38 | 39 | #---------------------------------# 40 | # General # 41 | #---------------------------------# 42 | skip_branch_with_pr: true 43 | 44 | #---------------------------------# 45 | # Branches to build # 46 | #---------------------------------# 47 | branches: 48 | # Whitelist 49 | only: 50 | - develop 51 | - master 52 | - /release\/.*/ 53 | - /hotfix\/.*/ 54 | 55 | #---------------------------------# 56 | # Build Cache # 57 | #---------------------------------# 58 | cache: 59 | - tools -> recipe.cake 60 | 61 | #---------------------------------# 62 | # Skip builds for doc changes # 63 | #---------------------------------# 64 | skip_commits: 65 | # Regex for matching commit message 66 | message: /\(doc\).*/ 67 | -------------------------------------------------------------------------------- /.config/dotnet-tools.json: -------------------------------------------------------------------------------- 1 | { 2 | "version": 1, 3 | "isRoot": true, 4 | "tools": { 5 | "cake.tool": { 6 | "version": "1.3.0", 7 | "commands": [ 8 | "dotnet-cake" 9 | ] 10 | } 11 | } 12 | } -------------------------------------------------------------------------------- /.editorconfig: -------------------------------------------------------------------------------- 1 | ; This file is for unifying the coding style for different editors and IDEs. 2 | ; More information at http://EditorConfig.org 3 | 4 | root = true 5 | 6 | [*] 7 | end_of_line = CRLF 8 | 9 | [*.ps1] 10 | indent_style = space 11 | indent_size = 4 12 | 13 | [*.cs] 14 | indent_style = space 15 | indent_size = 4 16 | 17 | [*.cake] 18 | indent_style = space 19 | indent_size = 4 20 | 21 | [*.js] 22 | indent_style = tab 23 | indent_size = 2 24 | -------------------------------------------------------------------------------- /.gitattributes: -------------------------------------------------------------------------------- 1 | # Set the default behavior, in case people don't have core.autocrlf set. 2 | * text=auto 3 | 4 | # Declare files that will always have CRLF line endings on checkout. 5 | *.sln text eol=crlf 6 | 7 | # Denote all files that are truly binary and should not be modified. 8 | *.png binary 9 | *.jpg binary 10 | -------------------------------------------------------------------------------- /.github/CODE_OF_CONDUCT.md: -------------------------------------------------------------------------------- 1 | # Contributor Code of Conduct 2 | 3 | As contributors and maintainers of this project, and in the interest of fostering an open and welcoming community, we pledge to respect all people who contribute through reporting issues, posting feature requests, updating documentation, submitting pull requests or patches, and other activities. 4 | 5 | We are committed to making participation in this project a harassment-free experience for everyone, regardless of level of experience, gender, gender identity and expression, sexual orientation, disability, personal appearance, body size, race, ethnicity, age, religion, or nationality. 6 | 7 | Examples of unacceptable behavior by participants include: 8 | 9 | - The use of sexualized language or imagery 10 | - Personal attacks 11 | - Trolling or insulting/derogatory comments 12 | - Public or private harassment 13 | - Publishing other's private information, such as physical or electronic addresses, without explicit permission 14 | - Other unethical or unprofessional conduct 15 | 16 | Project maintainers have the right and responsibility to remove, edit, or reject comments, commits, code, wiki edits, issues, and other contributions that are not aligned to this Code of Conduct, or to ban temporarily or permanently any contributor for other behaviors that they deem inappropriate, threatening, offensive, or harmful. 17 | 18 | By adopting this Code of Conduct, project maintainers commit themselves to fairly and consistently applying these principles to every aspect of managing this project. Project maintainers who do not follow or enforce the Code of Conduct may be permanently removed from the project team. 19 | 20 | This Code of Conduct applies both within project spaces and in public spaces when an individual is representing the project or its community. 21 | 22 | Instances of abusive, harassing, or otherwise unacceptable behavior may be reported by contacting a project maintainer at [abuse@gep13.co.uk](mailto:abuse@gep13.co.uk). All complaints will be reviewed and investigated and will result in a response that is deemed necessary and appropriate to the circumstances. Maintainers are obligated to maintain confidentiality with regard to the reporter of an incident. 23 | 24 | This Code of Conduct is adapted from the Contributor Covenant, version 1.3.0, available from 25 | -------------------------------------------------------------------------------- /.github/CONTRIBUTING.md: -------------------------------------------------------------------------------- 1 | # How to contribute 2 | 3 | Contributions to Cake.Terraform are highly encouraged and desired. Below are some guidelines that will help make the process as smooth as possible. 4 | 5 | ## Getting Started 6 | 7 | * Make sure you have a [GitHub account](https://github.com/signup/free) 8 | * Submit a new issue, assuming one does not already exist. 9 | * Clearly describe the issue including steps to reproduce when it is a bug. 10 | * Make sure you fill in the earliest version that you know has the issue. 11 | * Fork the repository on GitHub 12 | 13 | ## Suggesting Enhancements 14 | 15 | We want to know what you think is missing from Cake.Terraform and how it can be made better. 16 | 17 | * When submitting an issue for an enhancement, please be as clear as possible about why you think the enhancement is needed and what the benefit of 18 | it would be. 19 | 20 | ## Making Changes 21 | 22 | * From your fork of the repository, create a topic branch where work on your change will take place. 23 | * To quickly create a topic branch based on develop; `git checkout -b my_contribution develop`. Please avoid working directly on the `develop` or `master` branch. 24 | * Make commits of logical units. 25 | * Check for unnecessary whitespace with `git diff --check` before committing. 26 | * Please follow the prevailing code conventions in the repository. Differences in style make the code harder to understand for everyone. 27 | * Make sure your commit messages are in the proper format. 28 | ````text 29 | Add more cowbell to Get-Something 30 | 31 | The functionaly of Get-Something would be greatly improved if there was a little 32 | more 'pizzazz' added to it. I propose a cowbell. Adding more cowbell has been 33 | shown in studies to both increase one's mojo, and cement one's status 34 | as a rock legend. 35 | ```` 36 | 37 | * Make sure you have added all the necessary unit tests for your changes. 38 | * Run _all_ unit tests to assure nothing else was accidentally broken. 39 | 40 | ## Documentation 41 | 42 | We are infallible and as such the documenation needs no corectoin. In the highly 43 | unlikely event that that is _not_ the case, commits to update or add documentation 44 | are highly apprecaited. 45 | 46 | ## Submitting Changes 47 | 48 | * Push your changes to a topic branch in your fork of the repository. 49 | * Submit a pull request to the main repository. 50 | * Once the pull request has been reviewed and accepted, it will be merged with the develop branch. 51 | * Celebrate 52 | 53 | ## Additional Resources 54 | 55 | * [General GitHub documentation](https://help.github.com/) 56 | * [GitHub forking documentation](https://guides.github.com/activities/forking/) 57 | * [GitHub pull request documentation](https://help.github.com/send-pull-requests/) 58 | * [GitHub Flow guide](https://guides.github.com/introduction/flow/) 59 | * [GitHub's guide to contributing to open source projects](https://guides.github.com/activities/contributing-to-open-source/) 60 | -------------------------------------------------------------------------------- /.github/ISSUE_TEMPLATE.md: -------------------------------------------------------------------------------- 1 | 2 | 3 | ## Expected Behavior 4 | 5 | 6 | 7 | ## Current Behavior 8 | 9 | 10 | 11 | ## Possible Solution 12 | 13 | 14 | 15 | ## Steps to Reproduce (for bugs) 16 | 17 | 18 | 1. 19 | 2. 20 | 3. 21 | 4. 22 | 23 | ## Context 24 | 25 | 26 | 27 | ## Your Environment 28 | 29 | * Addin version used: 30 | * Cake Version used: 31 | * Operating System: 32 | -------------------------------------------------------------------------------- /.github/PULL_REQUEST_TEMPLATE.md: -------------------------------------------------------------------------------- 1 | 2 | 3 | ## Description 4 | 5 | 6 | ## Related Issue 7 | 8 | 9 | 10 | 11 | 12 | ## Motivation and Context 13 | 14 | 15 | ## How Has This Been Tested? 16 | 17 | 18 | 19 | 20 | ## Screenshots (if appropriate): 21 | 22 | ## Types of changes 23 | 24 | - [ ] Bug fix (non-breaking change which fixes an issue) 25 | - [ ] New feature (non-breaking change which adds functionality) 26 | - [ ] Breaking change (fix or feature that would cause existing functionality to change) 27 | 28 | ## Checklist: 29 | 30 | 31 | - [ ] My code follows the code style of this project. 32 | - [ ] My change requires a change to the documentation. 33 | - [ ] I have updated the documentation accordingly. 34 | - [ ] I have read the **CONTRIBUTING** document. 35 | - [ ] I have added tests to cover my changes. 36 | - [ ] All new and existing tests passed. 37 | -------------------------------------------------------------------------------- /.github/renovate.json: -------------------------------------------------------------------------------- 1 | { 2 | "$schema": "https://docs.renovatebot.com/renovate-schema.json", 3 | "extends": [ 4 | "github>cake-contrib/renovate-presets:cake-recipe", 5 | "github>cake-contrib/renovate-presets:github-actions" ], 6 | "packageRules": [ 7 | { 8 | "description": "Updates to Cake.Core references are breaking.", 9 | "matchPackageNames": ["Cake.Core"], 10 | "matchUpdateTypes": ["major"], 11 | "labels": ["Breaking Change"] 12 | } 13 | ] 14 | } 15 | -------------------------------------------------------------------------------- /.github/workflows/build.yml: -------------------------------------------------------------------------------- 1 | name: Build 2 | 3 | on: 4 | push: 5 | branches: 6 | - master 7 | - develop 8 | - "feature/**" 9 | - "release/**" 10 | - "hotfix/**" 11 | tags: 12 | - "*" 13 | paths-ignore: 14 | - "README.md" 15 | pull_request: 16 | 17 | jobs: 18 | build: 19 | runs-on: ${{ matrix.os }} 20 | strategy: 21 | matrix: 22 | os: [ windows-2022, ubuntu-22.04, macos-12 ] 23 | 24 | env: 25 | AZURE_PASSWORD: ${{ secrets.AZURE_PASSWORD }} 26 | AZURE_SOURCE: ${{ secrets.AZURE_SOURCE }} 27 | AZURE_USER: ${{ secrets.AZURE_USER }} 28 | COVERALLS_REPO_TOKEN: ${{ secrets.COVERALLS_REPO_TOKEN }} 29 | GITHUB_PAT: ${{ secrets.GH_TOKEN }} 30 | GPR_PASSWORD: ${{ secrets.GPR_PASSWORD }} 31 | GPR_SOURCE: ${{ secrets.GPR_SOURCE }} 32 | GPR_USER: ${{ secrets.GPR_USER }} 33 | NUGET_API_KEY: ${{ secrets.NUGET_API_KEY }} 34 | NUGET_SOURCE: "https://api.nuget.org/v3/index.json" 35 | TWITTER_ACCESS_TOKEN: ${{ secrets.TWITTER_ACCESS_TOKEN }} 36 | TWITTER_ACCESS_TOKEN_SECRET: ${{ secrets.TWITTER_ACCESS_TOKEN_SECRET }} 37 | TWITTER_CONSUMER_KEY: ${{ secrets.TWITTER_CONSUMER_KEY }} 38 | TWITTER_CONSUMER_SECRET: ${{ secrets.TWITTER_CONSUMER_SECRET }} 39 | WYAM_ACCESS_TOKEN: ${{ secrets.WYAM_ACCESS_TOKEN }} 40 | WYAM_DEPLOY_BRANCH: "gh-pages" 41 | WYAM_DEPLOY_REMOTE: ${{ github.event.repository.html_url }} 42 | 43 | steps: 44 | - name: Checkout the repository 45 | uses: actions/checkout@692973e3d937129bcbf40652eb9f2f61becf3332 # v4 46 | - name: Fetch all tags and branches 47 | run: git fetch --prune --unshallow 48 | - uses: actions/setup-dotnet@6bd8b7f7774af54e05809fcc5431931b3eb1ddee # v4.0.1 49 | with: 50 | dotnet-version: | 51 | 2.1.818 52 | 3.1.x 53 | 5.0.x 54 | 6.0.x 55 | 7.0.x 56 | 8.0.x 57 | - name: Cache Tools 58 | uses: actions/cache@0c45773b623bea8c8e75f6c82b208c3cf94ea4f9 # v4 59 | with: 60 | path: tools 61 | key: ${{ runner.os }}-tools-${{ hashFiles('recipe.cake') }} 62 | - name: Build project 63 | uses: cake-build/cake-action@a6eb054329257c9e70a6c6bf01747ad6e1d9d52b # v1 64 | with: 65 | script-path: recipe.cake 66 | target: CI 67 | cake-version: tool-manifest 68 | - name: Upload Issues 69 | uses: actions/upload-artifact@834a144ee995460fba8ed112a2fc961b36a5ec5a # v4 70 | with: 71 | if-no-files-found: warn 72 | name: ${{ matrix.os }} Issues 73 | path: | 74 | BuildArtifacts/report.html 75 | BuildArtifacts/**/coverlet/*.xml 76 | - name: Upload Packages 77 | uses: actions/upload-artifact@834a144ee995460fba8ed112a2fc961b36a5ec5a # v4 78 | if: runner.os == 'Windows' 79 | with: 80 | if-no-files-found: warn 81 | name: package 82 | path: BuildArtifacts/Packages/**/* 83 | -------------------------------------------------------------------------------- /.github/workflows/codeql-analysis.yml: -------------------------------------------------------------------------------- 1 | # For most projects, this workflow file will not need changing; you simply need 2 | # to commit it to your repository. 3 | # 4 | # You may wish to alter this file to override the set of languages analyzed, 5 | # or to provide custom queries or build logic. 6 | name: "CodeQL" 7 | 8 | on: 9 | push: 10 | branches: [develop] 11 | pull_request: 12 | # The branches below must be a subset of the branches above 13 | branches: [develop] 14 | schedule: 15 | - cron: '0 15 * * 6' 16 | workflow_dispatch: 17 | 18 | jobs: 19 | analyze: 20 | name: Analyze 21 | runs-on: ubuntu-22.04 22 | 23 | strategy: 24 | fail-fast: false 25 | matrix: 26 | # Override automatic language detection by changing the below list 27 | # Supported options are ['csharp', 'cpp', 'go', 'java', 'javascript', 'python'] 28 | language: ['csharp'] 29 | # Learn more... 30 | # https://docs.github.com/en/github/finding-security-vulnerabilities-and-errors-in-your-code/configuring-code-scanning#overriding-automatic-language-detection 31 | 32 | steps: 33 | - name: Checkout repository 34 | uses: actions/checkout@692973e3d937129bcbf40652eb9f2f61becf3332 # v4 35 | with: 36 | fetch-depth: 0 37 | - uses: actions/setup-dotnet@6bd8b7f7774af54e05809fcc5431931b3eb1ddee # v4.0.1 38 | with: 39 | dotnet-version: | 40 | 5.0.x 41 | 8.0.x 42 | 43 | - name: Cache Tools 44 | uses: actions/cache@0c45773b623bea8c8e75f6c82b208c3cf94ea4f9 # v4 45 | with: 46 | path: tools 47 | key: ${{ runner.os }}-tools-${{ hashFiles('recipe.cake') }} 48 | 49 | # Initializes the CodeQL tools for scanning. 50 | - name: Initialize CodeQL 51 | uses: github/codeql-action/init@eb055d739abdc2e8de2e5f4ba1a8b246daa779aa # v3 52 | with: 53 | languages: ${{ matrix.language }} 54 | # If you wish to specify custom queries, you can do so here or in a config file. 55 | # By default, queries listed here will override any specified in a config file. 56 | # Prefix the list here with "+" to use these queries and those in the config file. 57 | # queries: ./path/to/local/query, your-org/your-repo/queries@main 58 | 59 | - name: Build project 60 | uses: cake-build/cake-action@a6eb054329257c9e70a6c6bf01747ad6e1d9d52b # v1 61 | with: 62 | script-path: recipe.cake 63 | target: DotNetCore-Build 64 | cake-version: tool-manifest 65 | 66 | - name: Perform CodeQL Analysis 67 | uses: github/codeql-action/analyze@eb055d739abdc2e8de2e5f4ba1a8b246daa779aa # v3 68 | -------------------------------------------------------------------------------- /.gitignore: -------------------------------------------------------------------------------- 1 | ## Ignore Visual Studio temporary files, build results, and 2 | ## files generated by popular Visual Studio add-ons. 3 | ## 4 | ## Get latest from https://github.com/github/gitignore/blob/master/VisualStudio.gitignore 5 | 6 | # User-specific files 7 | *.suo 8 | *.user 9 | *.userosscache 10 | *.sln.docstates 11 | 12 | # User-specific files (MonoDevelop/Xamarin Studio) 13 | *.userprefs 14 | 15 | # Build results 16 | [Dd]ebug/ 17 | [Dd]ebugPublic/ 18 | [Rr]elease/ 19 | [Rr]eleases/ 20 | x64/ 21 | x86/ 22 | bld/ 23 | [Bb]in/ 24 | [Oo]bj/ 25 | [Ll]og/ 26 | 27 | # Visual Studio 2015 cache/options directory 28 | .vs/ 29 | # Uncomment if you have tasks that create the project's static files in wwwroot 30 | #wwwroot/ 31 | 32 | # MSTest test Results 33 | [Tt]est[Rr]esult*/ 34 | [Bb]uild[Ll]og.* 35 | 36 | # NUNIT 37 | *.VisualState.xml 38 | TestResult.xml 39 | 40 | # Build Results of an ATL Project 41 | [Dd]ebugPS/ 42 | [Rr]eleasePS/ 43 | dlldata.c 44 | 45 | # .NET Core 46 | project.lock.json 47 | project.fragment.lock.json 48 | artifacts/ 49 | **/Properties/launchSettings.json 50 | 51 | *_i.c 52 | *_p.c 53 | *_i.h 54 | *.ilk 55 | *.meta 56 | *.obj 57 | *.pch 58 | *.pdb 59 | *.pgc 60 | *.pgd 61 | *.rsp 62 | *.sbr 63 | *.tlb 64 | *.tli 65 | *.tlh 66 | *.tmp 67 | *.tmp_proj 68 | *.log 69 | *.vspscc 70 | *.vssscc 71 | .builds 72 | *.pidb 73 | *.svclog 74 | *.scc 75 | 76 | # Chutzpah Test files 77 | _Chutzpah* 78 | 79 | # Visual C++ cache files 80 | ipch/ 81 | *.aps 82 | *.ncb 83 | *.opendb 84 | *.opensdf 85 | *.sdf 86 | *.cachefile 87 | *.VC.db 88 | *.VC.VC.opendb 89 | 90 | # Visual Studio profiler 91 | *.psess 92 | *.vsp 93 | *.vspx 94 | *.sap 95 | 96 | # TFS 2012 Local Workspace 97 | $tf/ 98 | 99 | # Guidance Automation Toolkit 100 | *.gpState 101 | 102 | # ReSharper is a .NET coding add-in 103 | _ReSharper*/ 104 | *.[Rr]e[Ss]harper 105 | *.DotSettings.user 106 | 107 | # JustCode is a .NET coding add-in 108 | .JustCode 109 | 110 | # TeamCity is a build add-in 111 | _TeamCity* 112 | 113 | # DotCover is a Code Coverage Tool 114 | *.dotCover 115 | 116 | # Visual Studio code coverage results 117 | *.coverage 118 | *.coveragexml 119 | 120 | # NCrunch 121 | _NCrunch_* 122 | .*crunch*.local.xml 123 | nCrunchTemp_* 124 | 125 | # MightyMoose 126 | *.mm.* 127 | AutoTest.Net/ 128 | 129 | # Web workbench (sass) 130 | .sass-cache/ 131 | 132 | # Installshield output folder 133 | [Ee]xpress/ 134 | 135 | # DocProject is a documentation generator add-in 136 | DocProject/buildhelp/ 137 | DocProject/Help/*.HxT 138 | DocProject/Help/*.HxC 139 | DocProject/Help/*.hhc 140 | DocProject/Help/*.hhk 141 | DocProject/Help/*.hhp 142 | DocProject/Help/Html2 143 | DocProject/Help/html 144 | 145 | # Click-Once directory 146 | publish/ 147 | 148 | # Publish Web Output 149 | *.[Pp]ublish.xml 150 | *.azurePubxml 151 | # TODO: Comment the next line if you want to checkin your web deploy settings 152 | # but database connection strings (with potential passwords) will be unencrypted 153 | *.pubxml 154 | *.publishproj 155 | 156 | # Microsoft Azure Web App publish settings. Comment the next line if you want to 157 | # checkin your Azure Web App publish settings, but sensitive information contained 158 | # in these scripts will be unencrypted 159 | PublishScripts/ 160 | 161 | # NuGet Packages 162 | *.nupkg 163 | # The packages folder can be ignored because of Package Restore 164 | **/packages/* 165 | # except build/, which is used as an MSBuild target. 166 | !**/packages/build/ 167 | # Uncomment if necessary however generally it will be regenerated when needed 168 | #!**/packages/repositories.config 169 | # NuGet v3's project.json files produces more ignoreable files 170 | *.nuget.props 171 | *.nuget.targets 172 | 173 | # Microsoft Azure Build Output 174 | csx/ 175 | *.build.csdef 176 | 177 | # Microsoft Azure Emulator 178 | ecf/ 179 | rcf/ 180 | 181 | # Windows Store app package directories and files 182 | AppPackages/ 183 | BundleArtifacts/ 184 | Package.StoreAssociation.xml 185 | _pkginfo.txt 186 | 187 | # Visual Studio cache files 188 | # files ending in .cache can be ignored 189 | *.[Cc]ache 190 | # but keep track of directories ending in .cache 191 | !*.[Cc]ache/ 192 | 193 | # Others 194 | ClientBin/ 195 | ~$* 196 | *~ 197 | *.dbmdl 198 | *.dbproj.schemaview 199 | *.jfm 200 | *.pfx 201 | *.publishsettings 202 | node_modules/ 203 | orleans.codegen.cs 204 | 205 | # Since there are multiple workflows, uncomment next line to ignore bower_components 206 | # (https://github.com/github/gitignore/pull/1529#issuecomment-104372622) 207 | #bower_components/ 208 | 209 | # RIA/Silverlight projects 210 | Generated_Code/ 211 | 212 | # Backup & report files from converting an old project file 213 | # to a newer Visual Studio version. Backup files are not needed, 214 | # because we have git ;-) 215 | _UpgradeReport_Files/ 216 | Backup*/ 217 | UpgradeLog*.XML 218 | UpgradeLog*.htm 219 | 220 | # SQL Server files 221 | *.mdf 222 | *.ldf 223 | 224 | # Business Intelligence projects 225 | *.rdl.data 226 | *.bim.layout 227 | *.bim_*.settings 228 | 229 | # Microsoft Fakes 230 | FakesAssemblies/ 231 | 232 | # GhostDoc plugin setting file 233 | *.GhostDoc.xml 234 | 235 | # Node.js Tools for Visual Studio 236 | .ntvs_analysis.dat 237 | 238 | # Visual Studio 6 build log 239 | *.plg 240 | 241 | # Visual Studio 6 workspace options file 242 | *.opt 243 | 244 | # Visual Studio 6 auto-generated workspace file (contains which files were open etc.) 245 | *.vbw 246 | 247 | # Visual Studio LightSwitch build output 248 | **/*.HTMLClient/GeneratedArtifacts 249 | **/*.DesktopClient/GeneratedArtifacts 250 | **/*.DesktopClient/ModelManifest.xml 251 | **/*.Server/GeneratedArtifacts 252 | **/*.Server/ModelManifest.xml 253 | _Pvt_Extensions 254 | 255 | # Paket dependency manager 256 | .paket/paket.exe 257 | paket-files/ 258 | 259 | # FAKE - F# Make 260 | .fake/ 261 | 262 | # JetBrains Rider 263 | **/.idea/* 264 | *.sln.iml 265 | 266 | # CodeRush 267 | .cr/ 268 | 269 | # Python Tools for Visual Studio (PTVS) 270 | __pycache__/ 271 | *.pyc 272 | 273 | # Cake - Uncomment if you are using it 274 | tools/** 275 | !tools/packages.config 276 | BuildArtifacts/ 277 | .DS_Store 278 | -------------------------------------------------------------------------------- /GitReleaseManager.yaml: -------------------------------------------------------------------------------- 1 | create: 2 | include-footer: true 3 | footer-heading: Where to get it 4 | footer-content: > 5 | You can download this release from 6 | [nuget](https://nuget.org/packages/Cake.Terraform/{milestone}), 7 | or you can just reference it in a cake build script 8 | with `#addin nuget:?package=Cake.Terraform&version={milestone}`. 9 | footer-includes-milestone: true 10 | milestone-replace-text: "{milestone}" 11 | include-sha-section: true 12 | sha-section-heading: "SHA256 Hashes of the release artifacts" 13 | sha-section-line-format: "- `{1}\t{0}`" 14 | export: 15 | include-created-date-in-title: true 16 | created-date-string-format: yyyy-MM-dd 17 | perform-regex-removal: true 18 | regex-text: '[\r\n]*### Where to get it[\r\n]*You can .*`\.[\r\n]*' 19 | multiline-regex: true 20 | issue-labels-include: 21 | - Breaking change 22 | - Bug 23 | - Feature 24 | - Enhancement 25 | - Improvement 26 | - Documentation 27 | - security 28 | issue-labels-exclude: 29 | - Build 30 | - Internal / Refactoring 31 | issue-labels-alias: 32 | - name: Documentation 33 | header: Documentation 34 | plural: Documentation 35 | - name: security 36 | header: Security 37 | plural: Security 38 | close: 39 | use-issue-comments: true 40 | issue-comment: |- 41 | :tada: This issue has been resolved in version {milestone} :tada: 42 | The release is available on: 43 | - [GitHub Release](https://github.com/{owner}/{repository}/releases/tag/{milestone}) 44 | - [NuGet Package](https://www.nuget.org/packages/Cake.Terraform/{milestone}) 45 | Your **[GitReleaseManager](https://github.com/GitTools/GitReleaseManager)** bot :package::rocket: -------------------------------------------------------------------------------- /LICENSE: -------------------------------------------------------------------------------- 1 | MIT License 2 | 3 | Copyright (c) 2017 Erik van Brakel 4 | 5 | Permission is hereby granted, free of charge, to any person obtaining a copy 6 | of this software and associated documentation files (the "Software"), to deal 7 | in the Software without restriction, including without limitation the rights 8 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 9 | copies of the Software, and to permit persons to whom the Software is 10 | furnished to do so, subject to the following conditions: 11 | 12 | The above copyright notice and this permission notice shall be included in all 13 | copies or substantial portions of the Software. 14 | 15 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 16 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 17 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 18 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 19 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 20 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE 21 | SOFTWARE. 22 | -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 | # Cake.Terraform 2 | 3 | Cake.Terraform is set of aliases for [Cake][0] that help simplify using [Terraform][1]. 4 | 5 | [![License](http://img.shields.io/:license-mit-blue.svg)][2] 6 | 7 | ## Information 8 | 9 | | |Stable|Pre-release| 10 | |:--:|:--:|:--:| 11 | |GitHub Release|-|[![GitHub release](https://img.shields.io/github/release/cake-contrib/Cake.Terraform.svg)][3]| 12 | |NuGet|[![MyGet](https://img.shields.io/myget/cake-contrib/vpre/Cake.Terraform.svg)][4]|[![NuGet](https://img.shields.io/nuget/vpre/Cake.Terraform.svg)][5]| 13 | 14 | ## Build Status 15 | 16 | |Develop|Master| 17 | |:--:|:--:| 18 | |[![Build status](https://ci.appveyor.com/api/projects/status/7abq919ioxqwhqmn/branch/master?svg=true)][6]|[![Build status](https://ci.appveyor.com/api/projects/status/7abq919ioxqwhqmn/branch/master?svg=true)][7]| 19 | 20 | ## Quick Links 21 | 22 | - [Documentation][8] 23 | 24 | 25 | [0]: http://cakebuild.net/ 26 | [1]: https://www.terraform.io/ 27 | [2]: https://mit-license.org/ 28 | [3]: https://github.com/cake-contrib/Cake.Terraform/releases/latest 29 | [4]: https://www.myget.org/feed/cake-contrib/package/nuget/Cake.Terraform 30 | [5]: https://www.nuget.org/packages/Cake.Terraform 31 | [6]: https://ci.appveyor.com/project/cakecontrib/cake-terraform/branch/develop 32 | [7]: https://ci.appveyor.com/project/cakecontrib/cake-terraform/branch/master 33 | [8]: https://cakebuild.net/dsl/terraform/ 34 | -------------------------------------------------------------------------------- /build.ps1: -------------------------------------------------------------------------------- 1 | Set-Location -LiteralPath $PSScriptRoot 2 | 3 | $env:DOTNET_SKIP_FIRST_TIME_EXPERIENCE = '1' 4 | $env:DOTNET_CLI_TELEMETRY_OPTOUT = '1' 5 | $env:DOTNET_NOLOGO = '1' 6 | 7 | dotnet tool restore 8 | if ($LASTEXITCODE -ne 0) { exit $LASTEXITCODE } 9 | 10 | dotnet cake recipe.cake @args 11 | if ($LASTEXITCODE -ne 0) { exit $LASTEXITCODE } 12 | -------------------------------------------------------------------------------- /build.sh: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env bash 2 | set -euox pipefail 3 | 4 | cd "$(dirname "${BASH_SOURCE[0]}")" 5 | 6 | export DOTNET_SKIP_FIRST_TIME_EXPERIENCE=1 7 | export DOTNET_CLI_TELEMETRY_OPTOUT=1 8 | export DOTNET_NOLOGO=1 9 | 10 | dotnet tool restore 11 | 12 | dotnet cake recipe.cake "$@" 13 | -------------------------------------------------------------------------------- /config.wyam: -------------------------------------------------------------------------------- 1 | System.Globalization.CultureInfo.DefaultThreadCurrentCulture = System.Globalization.CultureInfo.CreateSpecificCulture("en-GB"); 2 | -------------------------------------------------------------------------------- /docs/index.md: -------------------------------------------------------------------------------- 1 | #Cake.Terraform Documentation 2 | 3 | Cake.Terraform is an Addin for [Cake][0] which allows the execution of the [Terraform][1] command line tool. 4 | 5 | To use this addin, you are required to have [Terraform][1] installed. 6 | 7 | ```csharp 8 | #addin Cake.Terraform 9 | ``` 10 | 11 | [0]: http://cakebuild.net/ 12 | [1]: https://www.terraform.io/ 13 | -------------------------------------------------------------------------------- /docs/input/assets/css/override.css: -------------------------------------------------------------------------------- 1 | /* Control the margin for bootstrap alert boxes */ 2 | .alert > p { 3 | margin-top: 0px; 4 | } 5 | 6 | /* Control the look and feel of the copy box applied to code sections */ 7 | .btn-copy[disabled] .clippy { 8 | opacity: .3; 9 | } 10 | pre .btn-copy { 11 | -webkit-transition: opacity 0.3s ease-in-out; 12 | -o-transition: opacity 0.3s ease-in-out; 13 | transition: opacity 0.3s ease-in-out; 14 | opacity: 0; 15 | padding: 2px 6px; 16 | float: right; 17 | } 18 | pre:hover .btn-copy { 19 | opacity: 1; 20 | } 21 | -------------------------------------------------------------------------------- /docs/input/assets/images/clippy.svg: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | -------------------------------------------------------------------------------- /docs/input/assets/js/anchor.min.js: -------------------------------------------------------------------------------- 1 | /** 2 | * AnchorJS - v3.2.2 - 2016-10-05 3 | * https://github.com/bryanbraun/anchorjs 4 | * Copyright (c) 2016 Bryan Braun; Licensed MIT 5 | */ 6 | !function(A,e){"use strict";"function"==typeof define&&define.amd?define([],e):"object"==typeof module&&module.exports?module.exports=e():(A.AnchorJS=e(),A.anchors=new A.AnchorJS)}(this,function(){"use strict";function A(A){function e(A){A.icon=A.hasOwnProperty("icon")?A.icon:"",A.visible=A.hasOwnProperty("visible")?A.visible:"hover",A.placement=A.hasOwnProperty("placement")?A.placement:"right",A.class=A.hasOwnProperty("class")?A.class:"",A.truncate=A.hasOwnProperty("truncate")?Math.floor(A.truncate):64}function t(A){var e;if("string"==typeof A||A instanceof String)e=[].slice.call(document.querySelectorAll(A));else{if(!(Array.isArray(A)||A instanceof NodeList))throw new Error("The selector provided to AnchorJS was invalid.");e=[].slice.call(A)}return e}function n(){if(null===document.head.querySelector("style.anchorjs")){var A,e=document.createElement("style"),t=" .anchorjs-link { opacity: 0; text-decoration: none; -webkit-font-smoothing: antialiased; -moz-osx-font-smoothing: grayscale; }",n=" *:hover > .anchorjs-link, .anchorjs-link:focus { opacity: 1; }",i=' @font-face { font-family: "anchorjs-icons"; src: url(data:n/a;base64,AAEAAAALAIAAAwAwT1MvMg8yG2cAAAE4AAAAYGNtYXDp3gC3AAABpAAAAExnYXNwAAAAEAAAA9wAAAAIZ2x5ZlQCcfwAAAH4AAABCGhlYWQHFvHyAAAAvAAAADZoaGVhBnACFwAAAPQAAAAkaG10eASAADEAAAGYAAAADGxvY2EACACEAAAB8AAAAAhtYXhwAAYAVwAAARgAAAAgbmFtZQGOH9cAAAMAAAAAunBvc3QAAwAAAAADvAAAACAAAQAAAAEAAHzE2p9fDzz1AAkEAAAAAADRecUWAAAAANQA6R8AAAAAAoACwAAAAAgAAgAAAAAAAAABAAADwP/AAAACgAAA/9MCrQABAAAAAAAAAAAAAAAAAAAAAwABAAAAAwBVAAIAAAAAAAIAAAAAAAAAAAAAAAAAAAAAAAMCQAGQAAUAAAKZAswAAACPApkCzAAAAesAMwEJAAAAAAAAAAAAAAAAAAAAARAAAAAAAAAAAAAAAAAAAAAAQAAg//0DwP/AAEADwABAAAAAAQAAAAAAAAAAAAAAIAAAAAAAAAIAAAACgAAxAAAAAwAAAAMAAAAcAAEAAwAAABwAAwABAAAAHAAEADAAAAAIAAgAAgAAACDpy//9//8AAAAg6cv//f///+EWNwADAAEAAAAAAAAAAAAAAAAACACEAAEAAAAAAAAAAAAAAAAxAAACAAQARAKAAsAAKwBUAAABIiYnJjQ3NzY2MzIWFxYUBwcGIicmNDc3NjQnJiYjIgYHBwYUFxYUBwYGIwciJicmNDc3NjIXFhQHBwYUFxYWMzI2Nzc2NCcmNDc2MhcWFAcHBgYjARQGDAUtLXoWOR8fORYtLTgKGwoKCjgaGg0gEhIgDXoaGgkJBQwHdR85Fi0tOAobCgoKOBoaDSASEiANehoaCQkKGwotLXoWOR8BMwUFLYEuehYXFxYugC44CQkKGwo4GkoaDQ0NDXoaShoKGwoFBe8XFi6ALjgJCQobCjgaShoNDQ0NehpKGgobCgoKLYEuehYXAAAADACWAAEAAAAAAAEACAAAAAEAAAAAAAIAAwAIAAEAAAAAAAMACAAAAAEAAAAAAAQACAAAAAEAAAAAAAUAAQALAAEAAAAAAAYACAAAAAMAAQQJAAEAEAAMAAMAAQQJAAIABgAcAAMAAQQJAAMAEAAMAAMAAQQJAAQAEAAMAAMAAQQJAAUAAgAiAAMAAQQJAAYAEAAMYW5jaG9yanM0MDBAAGEAbgBjAGgAbwByAGoAcwA0ADAAMABAAAAAAwAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAABAAH//wAP) format("truetype"); }',o=" [data-anchorjs-icon]::after { content: attr(data-anchorjs-icon); }";e.className="anchorjs",e.appendChild(document.createTextNode("")),A=document.head.querySelector('[rel="stylesheet"], style'),void 0===A?document.head.appendChild(e):document.head.insertBefore(e,A),e.sheet.insertRule(t,e.sheet.cssRules.length),e.sheet.insertRule(n,e.sheet.cssRules.length),e.sheet.insertRule(o,e.sheet.cssRules.length),e.sheet.insertRule(i,e.sheet.cssRules.length)}}this.options=A||{},this.elements=[],e(this.options),this.isTouchDevice=function(){return!!("ontouchstart"in window||window.DocumentTouch&&document instanceof DocumentTouch)},this.add=function(A){var i,o,s,c,r,a,h,l,u,d,f,p,w=[];if(e(this.options),p=this.options.visible,"touch"===p&&(p=this.isTouchDevice()?"always":"hover"),A||(A="h1, h2, h3, h4, h5, h6"),i=t(A),0===i.length)return!1;for(n(),o=document.querySelectorAll("[id]"),s=[].map.call(o,function(A){return A.id}),r=0;r-1,t=A.lastChild&&(" "+A.lastChild.className+" ").indexOf(" anchorjs-link ")>-1;return e||t||!1}}return A}); 7 | -------------------------------------------------------------------------------- /docs/input/assets/js/clipboard.min.js: -------------------------------------------------------------------------------- 1 | /*! 2 | * clipboard.js v1.5.16 3 | * https://zenorocha.github.io/clipboard.js 4 | * 5 | * Licensed MIT © Zeno Rocha 6 | */ 7 | !function(e){if("object"==typeof exports&&"undefined"!=typeof module)module.exports=e();else if("function"==typeof define&&define.amd)define([],e);else{var t;t="undefined"!=typeof window?window:"undefined"!=typeof global?global:"undefined"!=typeof self?self:this,t.Clipboard=e()}}(function(){var e,t,n;return function e(t,n,i){function o(a,c){if(!n[a]){if(!t[a]){var l="function"==typeof require&&require;if(!c&&l)return l(a,!0);if(r)return r(a,!0);var s=new Error("Cannot find module '"+a+"'");throw s.code="MODULE_NOT_FOUND",s}var u=n[a]={exports:{}};t[a][0].call(u.exports,function(e){var n=t[a][1][e];return o(n?n:e)},u,u.exports,e,t,n,i)}return n[a].exports}for(var r="function"==typeof require&&require,a=0;a0&&void 0!==arguments[0]?arguments[0]:{};this.action=t.action,this.emitter=t.emitter,this.target=t.target,this.text=t.text,this.trigger=t.trigger,this.selectedText=""}},{key:"initSelection",value:function e(){this.text?this.selectFake():this.target&&this.selectTarget()}},{key:"selectFake",value:function e(){var t=this,n="rtl"==document.documentElement.getAttribute("dir");this.removeFake(),this.fakeHandlerCallback=function(){return t.removeFake()},this.fakeHandler=document.body.addEventListener("click",this.fakeHandlerCallback)||!0,this.fakeElem=document.createElement("textarea"),this.fakeElem.style.fontSize="12pt",this.fakeElem.style.border="0",this.fakeElem.style.padding="0",this.fakeElem.style.margin="0",this.fakeElem.style.position="absolute",this.fakeElem.style[n?"right":"left"]="-9999px";var i=window.pageYOffset||document.documentElement.scrollTop;this.fakeElem.addEventListener("focus",window.scrollTo(0,i)),this.fakeElem.style.top=i+"px",this.fakeElem.setAttribute("readonly",""),this.fakeElem.value=this.text,document.body.appendChild(this.fakeElem),this.selectedText=(0,o.default)(this.fakeElem),this.copyText()}},{key:"removeFake",value:function e(){this.fakeHandler&&(document.body.removeEventListener("click",this.fakeHandlerCallback),this.fakeHandler=null,this.fakeHandlerCallback=null),this.fakeElem&&(document.body.removeChild(this.fakeElem),this.fakeElem=null)}},{key:"selectTarget",value:function e(){this.selectedText=(0,o.default)(this.target),this.copyText()}},{key:"copyText",value:function e(){var t=void 0;try{t=document.execCommand(this.action)}catch(e){t=!1}this.handleResult(t)}},{key:"handleResult",value:function e(t){this.emitter.emit(t?"success":"error",{action:this.action,text:this.selectedText,trigger:this.trigger,clearSelection:this.clearSelection.bind(this)})}},{key:"clearSelection",value:function e(){this.target&&this.target.blur(),window.getSelection().removeAllRanges()}},{key:"destroy",value:function e(){this.removeFake()}},{key:"action",set:function e(){var t=arguments.length>0&&void 0!==arguments[0]?arguments[0]:"copy";if(this._action=t,"copy"!==this._action&&"cut"!==this._action)throw new Error('Invalid "action" value, use either "copy" or "cut"')},get:function e(){return this._action}},{key:"target",set:function e(t){if(void 0!==t){if(!t||"object"!==("undefined"==typeof t?"undefined":r(t))||1!==t.nodeType)throw new Error('Invalid "target" value, use a valid Element');if("copy"===this.action&&t.hasAttribute("disabled"))throw new Error('Invalid "target" attribute. Please use "readonly" instead of "disabled" attribute');if("cut"===this.action&&(t.hasAttribute("readonly")||t.hasAttribute("disabled")))throw new Error('Invalid "target" attribute. You can\'t cut text from elements with "readonly" or "disabled" attributes');this._target=t}},get:function e(){return this._target}}]),e}();e.exports=c})},{select:5}],8:[function(t,n,i){!function(o,r){if("function"==typeof e&&e.amd)e(["module","./clipboard-action","tiny-emitter","good-listener"],r);else if("undefined"!=typeof i)r(n,t("./clipboard-action"),t("tiny-emitter"),t("good-listener"));else{var a={exports:{}};r(a,o.clipboardAction,o.tinyEmitter,o.goodListener),o.clipboard=a.exports}}(this,function(e,t,n,i){"use strict";function o(e){return e&&e.__esModule?e:{default:e}}function r(e,t){if(!(e instanceof t))throw new TypeError("Cannot call a class as a function")}function a(e,t){if(!e)throw new ReferenceError("this hasn't been initialised - super() hasn't been called");return!t||"object"!=typeof t&&"function"!=typeof t?e:t}function c(e,t){if("function"!=typeof t&&null!==t)throw new TypeError("Super expression must either be null or a function, not "+typeof t);e.prototype=Object.create(t&&t.prototype,{constructor:{value:e,enumerable:!1,writable:!0,configurable:!0}}),t&&(Object.setPrototypeOf?Object.setPrototypeOf(e,t):e.__proto__=t)}function l(e,t){var n="data-clipboard-"+e;if(t.hasAttribute(n))return t.getAttribute(n)}var s=o(t),u=o(n),f=o(i),d=function(){function e(e,t){for(var n=0;n0&&void 0!==arguments[0]?arguments[0]:{};this.action="function"==typeof t.action?t.action:this.defaultAction,this.target="function"==typeof t.target?t.target:this.defaultTarget,this.text="function"==typeof t.text?t.text:this.defaultText}},{key:"listenClick",value:function e(t){var n=this;this.listener=(0,f.default)(t,"click",function(e){return n.onClick(e)})}},{key:"onClick",value:function e(t){var n=t.delegateTarget||t.currentTarget;this.clipboardAction&&(this.clipboardAction=null),this.clipboardAction=new s.default({action:this.action(n),target:this.target(n),text:this.text(n),trigger:n,emitter:this})}},{key:"defaultAction",value:function e(t){return l("action",t)}},{key:"defaultTarget",value:function e(t){var n=l("target",t);if(n)return document.querySelector(n)}},{key:"defaultText",value:function e(t){return l("text",t)}},{key:"destroy",value:function e(){this.listener.destroy(),this.clipboardAction&&(this.clipboardAction.destroy(),this.clipboardAction=null)}}]),t}(u.default);e.exports=h})},{"./clipboard-action":7,"good-listener":4,"tiny-emitter":6}]},{},[8])(8)}); 8 | -------------------------------------------------------------------------------- /docs/input/blog/initial-release.md: -------------------------------------------------------------------------------- 1 | --- 2 | Title: Initial Release - 0.1.0 3 | Published: 21/03/2017 4 | Category: Release 5 | Author: erikvanbrakel 6 | --- 7 | 8 | # 0.1.0 is here 9 | 10 | The first prerelease version of Cake.Terraform is available! 11 | -------------------------------------------------------------------------------- /docs/input/blog/release-0-3-0.md: -------------------------------------------------------------------------------- 1 | --- 2 | Title: New release - 0.2.0 3 | Published: 22/03/2017 4 | Category: Release 5 | Author: erikvanbrakel 6 | --- 7 | 8 | # 0.2.0 is here 9 | 10 | This version adds functionality to format the output of the TerraformShow method as HTML. This is particularly useful in CI/CD scenarios, as a report to use within a build server such as TeamCity. 11 | -------------------------------------------------------------------------------- /docs/input/blog/release-0.1.1.md: -------------------------------------------------------------------------------- 1 | --- 2 | Title: New release - 0.2.0 3 | Published: 22/03/2017 4 | Category: Release 5 | Author: erikvanbrakel 6 | --- 7 | 8 | # 0.2.0 is here 9 | 10 | This version adds functionality to format the output of the TerraformShow method as HTML. This is particularly useful in CI/CD scenarios, as a report to use within a build server such as TeamCity. 11 | -------------------------------------------------------------------------------- /docs/input/docs/index.cshtml: -------------------------------------------------------------------------------- 1 | --- 2 | Title: Documentation 3 | --- 4 |

This user guide, like Cake.Terraform itself, is under active development. Some parts of it aren't 5 | documented as completely as they need to be, but we glady accept your contributions.

6 | 7 |

We need your help to improve the documentation for Cake.Terraform, so if there is something that you 8 | would like to add then you can edit the content directly on GitHub.

9 | 10 | @foreach(IDocument child in Model.DocumentList(Keys.Children).OrderBy(x => x.Get(DocsKeys.Order, 1000))) 11 | { 12 |

@(child.String(Keys.Title))

13 | if(child.ContainsKey(DocsKeys.Description)) 14 | { 15 |

@Html.Raw(child.String(DocsKeys.Description))

16 | } 17 | 18 | @Html.Partial("_ChildPages", child) 19 | } 20 | -------------------------------------------------------------------------------- /docs/input/docs/usage/examples.md: -------------------------------------------------------------------------------- 1 | # Build Script 2 | 3 | In order to make use of the Cake.Terraform Addin, you will need to first use the `#addin` preprocessor to install Cake.Terraform, but once that is done, you can directly use the available aliases. 4 | 5 | In addition, the `terraform` tool will need to be installed and available on the machine on which the script is running. Alternatively, you can provide a `ToolPath` to where it can be located. 6 | 7 | ## TerraformInit 8 | ```csharp 9 | #addin Cake.Terraform 10 | 11 | Task("Init") 12 | .Does(() => 13 | { 14 | TerraformInit(); 15 | }); 16 | ``` 17 | 18 | or, with specific settings: 19 | 20 | ```csharp 21 | #addin Cake.Terraform 22 | 23 | Task("Plan") 24 | .Does(() => 25 | { 26 | var settings = new TerraformInitSettings { 27 | WorkingDirectory = "./terraform" 28 | }; 29 | TerraformInit(settings); 30 | }); 31 | ``` 32 | 33 | ## TerraformPlan 34 | 35 | ```csharp 36 | #addin Cake.Terraform 37 | 38 | Task("Plan") 39 | .Does(() => 40 | { 41 | TerraformPlan(); 42 | }); 43 | ``` 44 | 45 | or, with specific settings: 46 | 47 | ```csharp 48 | #addin Cake.Terraform 49 | 50 | Task("Plan") 51 | .Does(() => 52 | { 53 | var settings = new TerraformPlanSettings { 54 | WorkingDirectory = "./terraform", 55 | OutFile = "./output/terraform.plan" 56 | }; 57 | TerraformPlan(settings); 58 | }); 59 | ``` 60 | 61 | ## TerraformShow 62 | 63 | ```csharp 64 | #addin Cake.Terraform 65 | 66 | Task("Show") 67 | .Does(() => 68 | { 69 | TerraformShow(); 70 | }); 71 | ``` 72 | 73 | or, with specific settings: 74 | 75 | ```csharp 76 | #addin Cake.Terraform 77 | 78 | Task("Plan") 79 | .Does(() => 80 | { 81 | var settings = new TerraformShowSettings { 82 | PlanFile = "./output/terraform.plan", 83 | OutFile = "./output/terraform.html", 84 | OutputFormat = OutputFormat.Html 85 | }; 86 | TerraformShow(settings); 87 | }); 88 | ``` 89 | 90 | ## TerraformApply 91 | 92 | ```csharp 93 | #addin Cake.Terraform 94 | 95 | Task("Apply") 96 | .Does(() => 97 | { 98 | TerraformApply(); 99 | }); 100 | ``` 101 | 102 | or, with specific settings: 103 | 104 | ```csharp 105 | #addin Cake.Terraform 106 | 107 | Task("Apply") 108 | .Does(() => 109 | { 110 | var settings = new TerraformApplySettings { 111 | Plan = "./output/terraform.plan" 112 | }; 113 | TerraformApply(settings); 114 | }); 115 | ``` 116 | 117 | ## TerraformDestroy 118 | 119 | ```csharp 120 | #addin Cake.Terraform 121 | 122 | Task("Destroy") 123 | .Does(() => 124 | { 125 | TerraformDestroy(); 126 | }); 127 | ``` 128 | 129 | or, with specific settings: 130 | 131 | ```csharp 132 | #addin Cake.Terraform 133 | 134 | Task("Destroy") 135 | .Does(() => 136 | { 137 | var settings = new TerraformDestroySettings { 138 | WorkingDirectory = ".", 139 | Force = true, 140 | InputVariables = new Dictionary { 141 | {"some-input-variable", "value"}, 142 | } 143 | }; 144 | TerraformDestroy(settings); 145 | }); 146 | ``` 147 | 148 | 149 | ## TerraformValidate 150 | 151 | ```csharp 152 | #addin Cake.Terraform 153 | 154 | Task("Validate") 155 | .Does(() => 156 | { 157 | TerraformValidate(); 158 | }); 159 | ``` -------------------------------------------------------------------------------- /docs/input/docs/usage/index.cshtml: -------------------------------------------------------------------------------- 1 | --- 2 | Order: 2 3 | Description: How to obtain, configure, and execute Cake.Terraform. 4 | --- 5 |

@Html.Raw(Model.String(DocsKeys.Description))

6 | 7 | @Html.Partial("_ChildPages") 8 | -------------------------------------------------------------------------------- /docs/input/index.cshtml: -------------------------------------------------------------------------------- 1 | --- 2 | Title: Cake.Terraform 3 | NoSidebar: true 4 | NoContainer: false 5 | NoGutter: true 6 | --- 7 | 8 |
9 |

What is it?

10 |

11 | Cake.Terraform is an Addin for Cake which which allows the execution of the Terraform command line tool. 12 |

13 |
14 | -------------------------------------------------------------------------------- /docs/packages.xml: -------------------------------------------------------------------------------- 1 |  2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | 10 | 11 | 12 | 13 | 14 | 15 | 16 | 17 | 18 | 19 | 20 | 21 | 22 | 23 | 24 | 25 | 26 | 27 | 28 | 29 | 30 | 31 | 32 | 33 | 34 | 35 | 36 | 37 | 38 | 39 | 40 | 41 | 42 | 43 | 44 | 45 | 46 | 47 | 48 | 49 | 50 | 51 | 52 | 53 | 54 | 55 | 56 | 57 | 58 | 59 | 60 | 61 | 62 | 63 | 64 | 65 | 66 | 67 | 68 | 69 | 70 | 71 | 72 | 73 | 74 | 75 | 76 | 77 | 78 | 79 | 80 | 81 | 82 | 83 | 84 | 85 | 86 | 87 | 88 | 89 | 90 | 91 | 92 | 93 | 94 | 95 | 96 | 97 | 98 | 99 | 100 | 101 | 102 | 103 | 104 | 105 | 106 | 107 | 108 | 109 | 110 | 111 | 112 | 113 | 114 | 115 | 116 | 117 | 118 | 119 | 120 | 121 | 122 | 123 | 124 | 125 | 126 | 127 | 128 | 129 | 130 | 131 | 132 | 133 | 134 | 135 | 136 | 137 | 138 | 139 | 140 | 141 | 142 | 143 | 144 | 145 | 146 | 147 | -------------------------------------------------------------------------------- /recipe.cake: -------------------------------------------------------------------------------- 1 | #load nuget:?package=Cake.Recipe&version=3.1.1 2 | 3 | Environment.SetVariableNames(); 4 | 5 | BuildParameters.SetParameters(context: Context, 6 | buildSystem: BuildSystem, 7 | sourceDirectoryPath: "./src", 8 | title: "Cake.Terraform", 9 | repositoryOwner: "cake-contrib", 10 | repositoryName: "Cake.Terraform", 11 | webHost: "cake-contrib.github.io", 12 | webLinkRoot: "Cake.Terraform", 13 | webBaseEditUrl: "https://github.com/cake-contrib/Cake.Terraform/tree/develop/docs/input", 14 | shouldRunDotNetCorePack: true, 15 | shouldRunCodecov: false, 16 | shouldPostToGitter: false 17 | //preferredBuildProviderType: BuildProviderType.GitHubActions, 18 | //preferredBuildAgentOperatingSystem: PlatformFamily.Linux 19 | ); 20 | 21 | BuildParameters.PrintParameters(Context); 22 | 23 | ToolSettings.SetToolPreprocessorDirectives( 24 | gitReleaseManagerGlobalTool: "#tool dotnet:?package=GitReleaseManager.Tool&version=0.17.0"); 25 | 26 | ToolSettings.SetToolSettings(context: Context); 27 | 28 | Build.RunDotNetCore(); 29 | 30 | -------------------------------------------------------------------------------- /src/Cake.Terraform.Tests/Cake.Terraform.Tests.csproj: -------------------------------------------------------------------------------- 1 |  2 | 3 | 4 | 9 | netcoreapp3.1 10 | net6.0;net7.0;net8.0 11 | 12 | 13 | 14 | 15 | 16 | 17 | runtime; build; native; contentfiles; analyzers; buildtransitive 18 | all 19 | 20 | 21 | 25 | 26 | 27 | 28 | 29 | 30 | 31 | 32 | 33 | 34 | 35 | -------------------------------------------------------------------------------- /src/Cake.Terraform.Tests/TerraformApplyTests.cs: -------------------------------------------------------------------------------- 1 | using Cake.Core; 2 | using Cake.Terraform.Apply; 3 | using Cake.Testing; 4 | using Xunit; 5 | 6 | namespace Cake.Terraform.Tests 7 | { 8 | using System.Collections.Generic; 9 | 10 | public class TerraformApplyTests 11 | { 12 | class Fixture : TerraformFixture 13 | { 14 | public Fixture(PlatformFamily platformFamily = PlatformFamily.Windows) : base(platformFamily) { } 15 | 16 | protected override void RunTool() 17 | { 18 | var tool = new TerraformApplyRunner(FileSystem, Environment, ProcessRunner, Tools); 19 | tool.Run(Settings); 20 | } 21 | } 22 | 23 | public class TheExecutable 24 | { 25 | [Fact] 26 | public void Should_throw_if_terraform_runner_was_not_found() 27 | { 28 | var fixture = new Fixture(); 29 | fixture.GivenDefaultToolDoNotExist(); 30 | 31 | var result = Record.Exception(() => fixture.Run()); 32 | 33 | Assert.IsType(result); 34 | Assert.Equal("Terraform: Could not locate executable.", result.Message); 35 | } 36 | 37 | [Theory] 38 | [InlineData("/bin/tools/terraform/terraform.exe", "/bin/tools/terraform/terraform.exe")] 39 | [InlineData("/bin/tools/terraform/terraform", "/bin/tools/terraform/terraform")] 40 | public void Should_use_terraform_from_tool_path_if_provided(string toolPath, string expected) 41 | { 42 | var fixture = new Fixture() {Settings = {ToolPath = toolPath}}; 43 | fixture.GivenSettingsToolPathExist(); 44 | 45 | var result = fixture.Run(); 46 | 47 | Assert.Equal(expected, result.Path.FullPath); 48 | } 49 | 50 | [Fact] 51 | public void Should_find_terraform_if_tool_path_not_provided() 52 | { 53 | var fixture = new Fixture(); 54 | 55 | var result = fixture.Run(); 56 | 57 | Assert.Equal("/Working/tools/terraform.exe", result.Path.FullPath); 58 | } 59 | 60 | [Fact] 61 | public void Should_throw_if_process_has_a_non_zero_exit_code() 62 | { 63 | var fixture = new Fixture(); 64 | fixture.GivenProcessExitsWithCode(1); 65 | 66 | var result = Record.Exception(() => fixture.Run()); 67 | 68 | Assert.IsType(result); 69 | Assert.Equal("Terraform: Process returned an error (exit code 1).", result.Message); 70 | } 71 | 72 | [Fact] 73 | public void Should_find_linux_executable() 74 | { 75 | var fixture = new Fixture(PlatformFamily.Linux); 76 | fixture.Environment.Platform.Family = PlatformFamily.Linux; 77 | 78 | 79 | var result = fixture.Run(); 80 | 81 | Assert.Equal("/Working/tools/terraform", result.Path.FullPath); 82 | } 83 | 84 | [Fact] 85 | public void Should_set_apply_parameter() 86 | { 87 | var fixture = new Fixture(); 88 | 89 | var result = fixture.Run(); 90 | 91 | Assert.Contains("apply", result.Args); 92 | } 93 | 94 | [Fact] 95 | public void Should_set_input_variables() 96 | { 97 | var fixture = new Fixture(); 98 | fixture.Settings = new TerraformApplySettings 99 | { 100 | InputVariables = new Dictionary 101 | { 102 | { "access_key", "foo" }, 103 | { "secret_key", "bar" } 104 | } 105 | }; 106 | var result = fixture.Run(); 107 | 108 | Assert.Contains("-var \"access_key=foo\" -var \"secret_key=bar\"", result.Args); 109 | } 110 | 111 | [Fact] 112 | public void Should_set_input_variables_file() 113 | { 114 | var fixture = new Fixture 115 | { 116 | Settings = new TerraformApplySettings 117 | { 118 | InputVariablesFile = "./aws-creds.json", 119 | InputVariables = new Dictionary 120 | { 121 | {"access_key", "foo"}, 122 | {"secret_key", "bar"} 123 | } 124 | } 125 | }; 126 | var result = fixture.Run(); 127 | 128 | Assert.Contains("-var-file \"./aws-creds.json\" -var \"access_key=foo\" -var \"secret_key=bar\"", result.Args); 129 | } 130 | 131 | [Fact] 132 | public void Should_Append_Auto_Approve_When_AutoApprove_Is_True() 133 | { 134 | var fixture = new Fixture { 135 | Settings = new TerraformApplySettings { 136 | AutoApprove = true 137 | } 138 | }; 139 | 140 | var result = fixture.Run(); 141 | 142 | Assert.Contains("-auto-approve", result.Args); 143 | } 144 | 145 | [Fact] 146 | public void Should_Append_Destroy_When_AutoApprove_Is_True() 147 | { 148 | var fixture = new Fixture 149 | { 150 | Settings = new TerraformApplySettings 151 | { 152 | Destroy = true 153 | } 154 | }; 155 | 156 | var result = fixture.Run(); 157 | 158 | Assert.Contains("-destroy", result.Args); 159 | } 160 | 161 | [Fact] 162 | public void Should_set_plan_path() 163 | { 164 | var fixture = new Fixture 165 | { 166 | Settings = new TerraformApplySettings { 167 | Plan = "plan.out" 168 | } 169 | }; 170 | 171 | var result = fixture.Run(); 172 | 173 | Assert.Equal("apply \"plan.out\"", result.Args); 174 | } 175 | 176 | [Fact] 177 | public void Should_set_parallelism() 178 | { 179 | var fixture = new Fixture 180 | { 181 | Settings = new TerraformApplySettings { 182 | Parallelism = 42 183 | } 184 | }; 185 | 186 | var result = fixture.Run(); 187 | 188 | Assert.Contains("-parallelism=42", result.Args); 189 | } 190 | 191 | [Fact] 192 | public void Should_omit_input_flag_by_default() 193 | { 194 | var fixture = new Fixture(); 195 | 196 | var result = fixture.Run(); 197 | 198 | Assert.DoesNotContain("-input", result.Args); 199 | } 200 | 201 | [Fact] 202 | public void Should_include_input_flag_when_setting_is_false() 203 | { 204 | var fixture = new Fixture 205 | { 206 | Settings = new TerraformApplySettings 207 | { 208 | Input = false 209 | } 210 | }; 211 | 212 | var result = fixture.Run(); 213 | 214 | Assert.Contains("-input", result.Args); 215 | } 216 | } 217 | } 218 | } 219 | -------------------------------------------------------------------------------- /src/Cake.Terraform.Tests/TerraformDestroyTests.cs: -------------------------------------------------------------------------------- 1 | using System.Collections.Generic; 2 | using Cake.Core; 3 | using Cake.Terraform.Destroy; 4 | using Cake.Testing; 5 | using Xunit; 6 | 7 | namespace Cake.Terraform.Tests 8 | { 9 | public class TerraformDestroyTests 10 | { 11 | class Fixture : TerraformFixture 12 | { 13 | public Fixture(PlatformFamily platformFamily = PlatformFamily.Windows) : base(platformFamily) { } 14 | 15 | protected override void RunTool() 16 | { 17 | var tool = new TerraformDestroyRunner(FileSystem, Environment, ProcessRunner, Tools); 18 | tool.Run(Settings); 19 | } 20 | } 21 | 22 | public class TheExecutable 23 | { 24 | [Fact] 25 | public void Should_throw_if_terraform_runner_was_not_found() 26 | { 27 | var fixture = new Fixture(); 28 | fixture.GivenDefaultToolDoNotExist(); 29 | 30 | var result = Record.Exception(() => fixture.Run()); 31 | 32 | Assert.IsType(result); 33 | Assert.Equal("Terraform: Could not locate executable.", result.Message); 34 | } 35 | 36 | [Theory] 37 | [InlineData("/bin/tools/terraform/terraform.exe", "/bin/tools/terraform/terraform.exe")] 38 | [InlineData("/bin/tools/terraform/terraform", "/bin/tools/terraform/terraform")] 39 | public void Should_use_terraform_from_tool_path_if_provided(string toolPath, string expected) 40 | { 41 | var fixture = new Fixture {Settings = {ToolPath = toolPath}}; 42 | fixture.GivenSettingsToolPathExist(); 43 | 44 | var result = fixture.Run(); 45 | 46 | Assert.Equal(expected, result.Path.FullPath); 47 | } 48 | 49 | [Fact] 50 | public void Should_find_terraform_if_tool_path_not_provided() 51 | { 52 | var fixture = new Fixture(); 53 | 54 | var result = fixture.Run(); 55 | 56 | Assert.Equal("/Working/tools/terraform.exe", result.Path.FullPath); 57 | } 58 | 59 | [Fact] 60 | public void Should_throw_if_process_has_a_non_zero_exit_code() 61 | { 62 | var fixture = new Fixture(); 63 | fixture.GivenProcessExitsWithCode(1); 64 | 65 | var result = Record.Exception(() => fixture.Run()); 66 | 67 | Assert.IsType(result); 68 | Assert.Equal("Terraform: Process returned an error (exit code 1).", result.Message); 69 | } 70 | 71 | [Fact] 72 | public void Should_find_linux_executable() 73 | { 74 | var fixture = new Fixture(PlatformFamily.Linux); 75 | fixture.Environment.Platform.Family = PlatformFamily.Linux; 76 | 77 | 78 | var result = fixture.Run(); 79 | 80 | Assert.Equal("/Working/tools/terraform", result.Path.FullPath); 81 | } 82 | 83 | [Fact] 84 | public void Should_set_destroy_parameter() 85 | { 86 | var fixture = new Fixture(); 87 | 88 | var result = fixture.Run(); 89 | 90 | Assert.Contains("destroy", result.Args); 91 | } 92 | 93 | [Fact] 94 | public void Should_set_force_flag_when_set_to_true() 95 | { 96 | var fixture = new Fixture 97 | { 98 | Settings = new TerraformDestroySettings 99 | { 100 | Force = true 101 | } 102 | }; 103 | var result = fixture.Run(); 104 | 105 | Assert.Contains("-force", result.Args); 106 | } 107 | 108 | [Fact] 109 | public void Should_set_input_variables() 110 | { 111 | var fixture = new Fixture 112 | { 113 | Settings = new TerraformDestroySettings 114 | { 115 | InputVariables = new Dictionary 116 | { 117 | {"access_key", "foo"}, 118 | {"secret_key", "bar"} 119 | } 120 | } 121 | }; 122 | var result = fixture.Run(); 123 | 124 | Assert.Contains("-var \"access_key=foo\" -var \"secret_key=bar\"", result.Args); 125 | } 126 | 127 | [Fact] 128 | public void Should_set_input_variables_file() 129 | { 130 | var fixture = new Fixture 131 | { 132 | Settings = new TerraformDestroySettings 133 | { 134 | InputVariablesFile = "./aws-creds.json", 135 | InputVariables = new Dictionary 136 | { 137 | {"access_key", "foo"}, 138 | {"secret_key", "bar"} 139 | } 140 | } 141 | }; 142 | var result = fixture.Run(); 143 | 144 | Assert.Contains("-var-file \"./aws-creds.json\" -var \"access_key=foo\" -var \"secret_key=bar\"", result.Args); 145 | } 146 | } 147 | } 148 | } -------------------------------------------------------------------------------- /src/Cake.Terraform.Tests/TerraformEnvListTests.cs: -------------------------------------------------------------------------------- 1 | using Cake.Core; 2 | using Cake.Terraform.EnvList; 3 | using Cake.Testing; 4 | using Xunit; 5 | 6 | namespace Cake.Terraform.Tests 7 | { 8 | using System.Collections.Generic; 9 | 10 | public class TerraformEnvListTests 11 | { 12 | class Fixture : TerraformFixture 13 | { 14 | public Fixture(PlatformFamily platformFamily = PlatformFamily.Windows) : base(platformFamily) { } 15 | 16 | public IEnumerable Environments { get; private set; } = new List(); 17 | 18 | protected override void RunTool() 19 | { 20 | ProcessRunner.Process.SetStandardOutput(new List{ "default" }); 21 | 22 | var tool = new TerraformEnvListRunner(FileSystem, Environment, ProcessRunner, Tools); 23 | 24 | Environments = tool.Run(Settings); 25 | } 26 | } 27 | 28 | public class TheExecutable 29 | { 30 | [Fact] 31 | public void Should_throw_if_terraform_runner_was_not_found() 32 | { 33 | var fixture = new Fixture(); 34 | fixture.GivenDefaultToolDoNotExist(); 35 | 36 | var result = Record.Exception(() => fixture.Run()); 37 | 38 | Assert.IsType(result); 39 | Assert.Equal("Terraform: Could not locate executable.", result.Message); 40 | } 41 | 42 | [Theory] 43 | [InlineData("/bin/tools/terraform/terraform.exe", "/bin/tools/terraform/terraform.exe")] 44 | [InlineData("/bin/tools/terraform/terraform", "/bin/tools/terraform/terraform")] 45 | public void Should_use_terraform_from_tool_path_if_provided(string toolPath, string expected) 46 | { 47 | var fixture = new Fixture() {Settings = {ToolPath = toolPath}}; 48 | fixture.GivenSettingsToolPathExist(); 49 | 50 | var result = fixture.Run(); 51 | 52 | Assert.Equal(expected, result.Path.FullPath); 53 | } 54 | 55 | [Fact] 56 | public void Should_find_terraform_if_tool_path_not_provided() 57 | { 58 | var fixture = new Fixture(); 59 | 60 | var result = fixture.Run(); 61 | 62 | Assert.Equal("/Working/tools/terraform.exe", result.Path.FullPath); 63 | } 64 | 65 | [Fact] 66 | public void Should_throw_if_process_has_a_non_zero_exit_code() 67 | { 68 | var fixture = new Fixture(); 69 | fixture.GivenProcessExitsWithCode(1); 70 | 71 | var result = Record.Exception(() => fixture.Run()); 72 | 73 | Assert.IsType(result); 74 | Assert.Equal("Terraform: Process returned an error (exit code 1).", result.Message); 75 | } 76 | 77 | [Fact] 78 | public void Should_find_linux_executable() 79 | { 80 | var fixture = new Fixture(PlatformFamily.Linux); 81 | fixture.Environment.Platform.Family = PlatformFamily.Linux; 82 | 83 | 84 | var result = fixture.Run(); 85 | 86 | Assert.Equal("/Working/tools/terraform", result.Path.FullPath); 87 | } 88 | 89 | [Fact] 90 | public void Should_set_workspace_and_list_parameter() 91 | { 92 | var fixture = new Fixture(); 93 | 94 | var result = fixture.Run(); 95 | 96 | Assert.Contains("workspace list", result.Args); 97 | } 98 | 99 | [Fact] 100 | public void Should_set_env_and_list_parameter() 101 | { 102 | var fixture = new Fixture {Settings = {EnvCommand = TerraformEnvSettings.EnvCommandType.Env}}; 103 | 104 | var result = fixture.Run(); 105 | 106 | Assert.Contains("env list", result.Args); 107 | } 108 | 109 | [Fact] 110 | public void Should_return_existing_environments() 111 | { 112 | var fixture = new Fixture(); 113 | 114 | var result = fixture.Run(); 115 | 116 | Assert.Contains("default", fixture.Environments); 117 | } 118 | } 119 | } 120 | } -------------------------------------------------------------------------------- /src/Cake.Terraform.Tests/TerraformFixture.cs: -------------------------------------------------------------------------------- 1 | using Cake.Core; 2 | using Cake.Core.Tooling; 3 | 4 | namespace Cake.Terraform.Tests 5 | { 6 | public abstract class TerraformFixture : Testing.Fixtures.ToolFixture 7 | where TSettings : ToolSettings, new() 8 | { 9 | protected TerraformFixture(PlatformFamily platformFamily = PlatformFamily.Windows) 10 | : base(platformFamily == PlatformFamily.Windows ? "terraform.exe" : "terraform") 11 | { 12 | Environment.Platform.Family = platformFamily; 13 | } 14 | } 15 | } -------------------------------------------------------------------------------- /src/Cake.Terraform.Tests/TerraformInitTests.cs: -------------------------------------------------------------------------------- 1 | using System.Collections.Generic; 2 | using Cake.Core; 3 | using Cake.Terraform.Init; 4 | using Cake.Testing; 5 | using Xunit; 6 | 7 | namespace Cake.Terraform.Tests 8 | { 9 | public class TerraformInitTests 10 | { 11 | class Fixture : TerraformFixture 12 | { 13 | public Fixture(PlatformFamily platformFamily = PlatformFamily.Windows) : base(platformFamily) 14 | { 15 | } 16 | 17 | protected override void RunTool() 18 | { 19 | var tool = new TerraformInitRunner(FileSystem, Environment, ProcessRunner, Tools); 20 | tool.Run(Settings); 21 | } 22 | } 23 | 24 | public class TheExecutable 25 | { 26 | [Fact] 27 | public void Should_throw_if_terraform_runner_was_not_found() 28 | { 29 | var fixture = new Fixture(); 30 | fixture.GivenDefaultToolDoNotExist(); 31 | 32 | var result = Record.Exception(() => fixture.Run()); 33 | 34 | Assert.IsType(result); 35 | Assert.Equal("Terraform: Could not locate executable.", result.Message); 36 | } 37 | 38 | [Theory] 39 | [InlineData("/bin/tools/terraform/terraform.exe", "/bin/tools/terraform/terraform.exe")] 40 | [InlineData("/bin/tools/terraform/terraform", "/bin/tools/terraform/terraform")] 41 | public void Should_use_terraform_from_tool_path_if_provided(string toolPath, string expected) 42 | { 43 | var fixture = new Fixture() {Settings = {ToolPath = toolPath}}; 44 | fixture.GivenSettingsToolPathExist(); 45 | 46 | var result = fixture.Run(); 47 | 48 | Assert.Equal(expected, result.Path.FullPath); 49 | } 50 | 51 | [Fact] 52 | public void Should_find_terraform_if_tool_path_not_provided() 53 | { 54 | var fixture = new Fixture(); 55 | 56 | var result = fixture.Run(); 57 | 58 | Assert.Equal("/Working/tools/terraform.exe", result.Path.FullPath); 59 | } 60 | 61 | [Fact] 62 | public void Should_throw_if_process_has_a_non_zero_exit_code() 63 | { 64 | var fixture = new Fixture(); 65 | fixture.GivenProcessExitsWithCode(1); 66 | 67 | var result = Record.Exception(() => fixture.Run()); 68 | 69 | Assert.IsType(result); 70 | Assert.Equal("Terraform: Process returned an error (exit code 1).", result.Message); 71 | } 72 | 73 | [Fact] 74 | public void Should_find_linux_executable() 75 | { 76 | var fixture = new Fixture(PlatformFamily.Linux); 77 | fixture.Environment.Platform.Family = PlatformFamily.Linux; 78 | 79 | 80 | var result = fixture.Run(); 81 | 82 | Assert.Equal("/Working/tools/terraform", result.Path.FullPath); 83 | } 84 | 85 | [Fact] 86 | public void Should_set_init_parameter() 87 | { 88 | var fixture = new Fixture(); 89 | 90 | var result = fixture.Run(); 91 | 92 | Assert.Contains("init", result.Args); 93 | } 94 | 95 | [Fact] 96 | public void Should_pass_backend_config_overrides() 97 | { 98 | var fixture = new Fixture(); 99 | 100 | fixture.Settings = new TerraformInitSettings 101 | { 102 | BackendConfigOverrides = new Dictionary 103 | { 104 | { "key", "value" }, 105 | { "foo", "bar" }, 106 | } 107 | }; 108 | 109 | var result = fixture.Run(); 110 | 111 | Assert.Contains("-backend-config \"key=value\"", result.Args); 112 | Assert.Contains("-backend-config \"foo=bar\"", result.Args); 113 | } 114 | 115 | [Fact] 116 | public void Should_omit_reconfigure_flag_by_default() 117 | { 118 | var fixture = new Fixture(); 119 | 120 | var result = fixture.Run(); 121 | 122 | Assert.DoesNotContain("-reconfigure", result.Args); 123 | } 124 | 125 | [Fact] 126 | public void Should_include_reconfigure_flag_when_setting_is_true() 127 | { 128 | var fixture = new Fixture 129 | { 130 | Settings = new TerraformInitSettings 131 | { 132 | ForceReconfigure = true 133 | } 134 | }; 135 | 136 | var result = fixture.Run(); 137 | 138 | Assert.Contains("-reconfigure", result.Args); 139 | } 140 | 141 | [Fact] 142 | public void Should_omit_force_copy_flag_by_default() 143 | { 144 | var fixture = new Fixture(); 145 | 146 | var result = fixture.Run(); 147 | 148 | Assert.DoesNotContain("-force-copy", result.Args); 149 | } 150 | 151 | [Fact] 152 | public void Should_include_force_copy_flag_when_setting_is_true() 153 | { 154 | var fixture = new Fixture 155 | { 156 | Settings = new TerraformInitSettings 157 | { 158 | ForceCopy = true 159 | } 160 | }; 161 | 162 | var result = fixture.Run(); 163 | 164 | Assert.Contains("-force-copy", result.Args); 165 | } 166 | 167 | [Fact] 168 | public void Should_omit_input_flag_by_default() 169 | { 170 | var fixture = new Fixture(); 171 | 172 | var result = fixture.Run(); 173 | 174 | Assert.DoesNotContain("-input", result.Args); 175 | } 176 | 177 | [Fact] 178 | public void Should_include_input_flag_when_setting_is_false() 179 | { 180 | var fixture = new Fixture 181 | { 182 | Settings = new TerraformInitSettings 183 | { 184 | Input = false 185 | } 186 | }; 187 | 188 | var result = fixture.Run(); 189 | 190 | Assert.Contains("-input", result.Args); 191 | } 192 | 193 | [Fact] 194 | public void Should_omit_backend_flag_by_default() 195 | { 196 | var fixture = new Fixture(); 197 | 198 | var result = fixture.Run(); 199 | 200 | Assert.DoesNotContain("-backend", result.Args); 201 | } 202 | 203 | [Fact] 204 | public void Should_include_backend_flag_when_setting_is_false() 205 | { 206 | var fixture = new Fixture 207 | { 208 | Settings = new TerraformInitSettings 209 | { 210 | Backend = false 211 | } 212 | }; 213 | 214 | var result = fixture.Run(); 215 | 216 | Assert.Contains("-backend", result.Args); 217 | } 218 | } 219 | } 220 | } -------------------------------------------------------------------------------- /src/Cake.Terraform.Tests/TerraformOutputTests.cs: -------------------------------------------------------------------------------- 1 | using System; 2 | using System.Collections.Generic; 3 | using Cake.Core; 4 | using Cake.Terraform.Output; 5 | using Cake.Testing; 6 | using Xunit; 7 | 8 | namespace Cake.Terraform.Tests 9 | { 10 | public class TerraformOutputTests 11 | { 12 | class Fixture : TerraformFixture 13 | { 14 | public Fixture(PlatformFamily platformFamily = PlatformFamily.Windows) : base(platformFamily) { } 15 | 16 | public List ToolOutput { get; set; } = new List { "foo = 123", "bar = abc" }; 17 | public string Outputs { get; private set; } = null; 18 | 19 | protected override void RunTool() 20 | { 21 | ProcessRunner.Process.SetStandardOutput(ToolOutput); 22 | 23 | var tool = new TerraformOutputRunner(FileSystem, Environment, ProcessRunner, Tools); 24 | 25 | Outputs = tool.Run(Settings); 26 | } 27 | } 28 | 29 | public class TheExecutable 30 | { 31 | [Fact] 32 | public void Should_throw_if_terraform_runner_was_not_found() 33 | { 34 | var fixture = new Fixture(); 35 | fixture.GivenDefaultToolDoNotExist(); 36 | 37 | var result = Record.Exception(() => fixture.Run()); 38 | 39 | Assert.IsType(result); 40 | Assert.Equal("Terraform: Could not locate executable.", result.Message); 41 | } 42 | 43 | [Theory] 44 | [InlineData("/bin/tools/terraform/terraform.exe", "/bin/tools/terraform/terraform.exe")] 45 | [InlineData("/bin/tools/terraform/terraform", "/bin/tools/terraform/terraform")] 46 | public void Should_use_terraform_from_tool_path_if_provided(string toolPath, string expected) 47 | { 48 | var fixture = new Fixture() {Settings = {ToolPath = toolPath}}; 49 | fixture.GivenSettingsToolPathExist(); 50 | 51 | var result = fixture.Run(); 52 | 53 | Assert.Equal(expected, result.Path.FullPath); 54 | } 55 | 56 | [Fact] 57 | public void Should_find_terraform_if_tool_path_not_provided() 58 | { 59 | var fixture = new Fixture(); 60 | 61 | var result = fixture.Run(); 62 | 63 | Assert.Equal("/Working/tools/terraform.exe", result.Path.FullPath); 64 | } 65 | 66 | [Fact] 67 | public void Should_throw_if_process_has_a_non_zero_exit_code() 68 | { 69 | var fixture = new Fixture(); 70 | fixture.GivenProcessExitsWithCode(1); 71 | 72 | var result = Record.Exception(() => fixture.Run()); 73 | 74 | Assert.IsType(result); 75 | Assert.Equal("Terraform: Process returned an error (exit code 1).", result.Message); 76 | } 77 | 78 | [Fact] 79 | public void Should_find_linux_executable() 80 | { 81 | var fixture = new Fixture(PlatformFamily.Linux); 82 | fixture.Environment.Platform.Family = PlatformFamily.Linux; 83 | 84 | var result = fixture.Run(); 85 | 86 | Assert.Equal("/Working/tools/terraform", result.Path.FullPath); 87 | } 88 | 89 | [Fact] 90 | public void Should_call_only_command_if_no_settings_specified() 91 | { 92 | var fixture = new Fixture(); 93 | 94 | var result = fixture.Run(); 95 | 96 | Assert.Equal("output -no-color", result.Args); 97 | } 98 | 99 | [Fact] 100 | public void Should_request_json_if_specified() 101 | { 102 | var fixture = new Fixture { Settings = new TerraformOutputSettings { Json = true } }; 103 | 104 | var result = fixture.Run(); 105 | 106 | Assert.Equal("output -no-color -json", result.Args); 107 | } 108 | 109 | [Fact] 110 | public void Should_request_raw_if_specified() 111 | { 112 | var fixture = new Fixture { Settings = new TerraformOutputSettings { Raw = true } }; 113 | 114 | var result = fixture.Run(); 115 | 116 | Assert.Equal("output -no-color -raw", result.Args); 117 | } 118 | 119 | [Fact] 120 | public void Should_request_raw_over_json_if_both_are_specified() 121 | { 122 | var fixture = new Fixture { Settings = new TerraformOutputSettings { Raw = true, Json = true} }; 123 | 124 | var result = fixture.Run(); 125 | 126 | Assert.Equal("output -no-color -raw", result.Args); 127 | } 128 | 129 | [Fact] 130 | public void Should_request_specific_state_path_if_specified() 131 | { 132 | var fixture = new Fixture { Settings = new TerraformOutputSettings { StatePath = "some_path"} }; 133 | 134 | var result = fixture.Run(); 135 | 136 | Assert.Equal("output -no-color -state=some_path", result.Args); 137 | } 138 | 139 | [Fact] 140 | public void Should_request_particular_output_if_specified() 141 | { 142 | var fixture = new Fixture { Settings = new TerraformOutputSettings { OutputName = "some_output"} }; 143 | 144 | var result = fixture.Run(); 145 | 146 | Assert.Equal("output -no-color some_output", result.Args); 147 | } 148 | 149 | [Fact] 150 | public void Should_combine_output_lines_into_string() 151 | { 152 | var fixture = new Fixture(); 153 | 154 | fixture.Run(); 155 | 156 | Assert.Equal("foo = 123\nbar = abc", fixture.Outputs); 157 | } 158 | 159 | [Fact] 160 | public void Should_raise_exception_if_output_not_found() 161 | { 162 | var fixture = new Fixture 163 | { 164 | ToolOutput = new List 165 | { 166 | "The output variable requested could not be found in the state", 167 | "file. If you recently added this to your configuration, be", 168 | "sure to run `terraform apply`, since the state won't be updated", 169 | "with new output variables until that command is run." 170 | } 171 | }; 172 | 173 | var exception = Assert.Throws(() => fixture.Run()); 174 | Assert.Equal( 175 | "The output variable requested could not be found in the state\nfile. If you recently added this to your configuration, be\nsure to run `terraform apply`, since the state won't be updated\nwith new output variables until that command is run.", 176 | exception.Message); 177 | } 178 | 179 | [Fact] 180 | public void Should_not_raise_exception_if_output_not_found_and_validation_disabled() 181 | { 182 | var fixture = new Fixture 183 | { 184 | ToolOutput = new List 185 | { 186 | "The output variable requested could not be found in the state", 187 | "file. If you recently added this to your configuration, be", 188 | "sure to run `terraform apply`, since the state won't be updated", 189 | "with new output variables until that command is run." 190 | }, 191 | Settings = new TerraformOutputSettings 192 | { 193 | ValidateToolOutput = false 194 | } 195 | }; 196 | 197 | fixture.Run(); 198 | 199 | Assert.Equal( 200 | "The output variable requested could not be found in the state\nfile. If you recently added this to your configuration, be\nsure to run `terraform apply`, since the state won't be updated\nwith new output variables until that command is run.", 201 | fixture.Outputs); 202 | } 203 | } 204 | } 205 | } -------------------------------------------------------------------------------- /src/Cake.Terraform.Tests/TerraformPlanTests.cs: -------------------------------------------------------------------------------- 1 | using System.Collections.Generic; 2 | using Cake.Core; 3 | using Cake.Terraform.Plan; 4 | using Cake.Testing; 5 | using Xunit; 6 | 7 | namespace Cake.Terraform.Tests 8 | { 9 | public class TerraformPlanTests 10 | { 11 | class Fixture : TerraformFixture 12 | { 13 | public Fixture(PlatformFamily platformFamily = PlatformFamily.Windows) : base(platformFamily) {} 14 | 15 | public bool HasChanges { get; set; } 16 | 17 | protected override void RunTool() 18 | { 19 | var tool = new TerraformPlanRunner(FileSystem, Environment, ProcessRunner, Tools); 20 | tool.Run(Settings); 21 | HasChanges = tool.HasChanges; 22 | } 23 | } 24 | 25 | public class TheExecutable 26 | { 27 | [Fact] 28 | public void Should_throw_if_terraform_runner_was_not_found() 29 | { 30 | var fixture = new Fixture(); 31 | fixture.GivenDefaultToolDoNotExist(); 32 | 33 | var result = Record.Exception(() => fixture.Run()); 34 | 35 | Assert.IsType(result); 36 | Assert.Equal("Terraform: Could not locate executable.", result.Message); 37 | } 38 | 39 | [Theory] 40 | [InlineData("/bin/tools/terraform/terraform.exe", "/bin/tools/terraform/terraform.exe")] 41 | [InlineData("/bin/tools/terraform/terraform", "/bin/tools/terraform/terraform")] 42 | public void Should_use_terraform_from_tool_path_if_provided(string toolPath, string expected) 43 | { 44 | var fixture = new Fixture {Settings = {ToolPath = toolPath}}; 45 | fixture.GivenSettingsToolPathExist(); 46 | 47 | var result = fixture.Run(); 48 | 49 | Assert.Equal(expected, result.Path.FullPath); 50 | } 51 | 52 | [Fact] 53 | public void Should_find_terraform_if_tool_path_not_provided() 54 | { 55 | var fixture = new Fixture(); 56 | 57 | var result = fixture.Run(); 58 | 59 | Assert.Equal("/Working/tools/terraform.exe", result.Path.FullPath); 60 | } 61 | 62 | [Fact] 63 | public void Should_find_linux_executable() 64 | { 65 | var fixture = new Fixture(PlatformFamily.Linux); 66 | fixture.Environment.Platform.Family = PlatformFamily.Linux; 67 | 68 | 69 | var result = fixture.Run(); 70 | 71 | Assert.Equal("/Working/tools/terraform", result.Path.FullPath); 72 | } 73 | 74 | [Fact] 75 | public void Should_not_have_changes_if_process_has_exit_code_zero() 76 | { 77 | var fixture = new Fixture(); 78 | fixture.GivenProcessExitsWithCode(0); 79 | 80 | var result = fixture.Run(); 81 | 82 | Assert.False(fixture.HasChanges); 83 | } 84 | 85 | [Fact] 86 | public void Should_throw_if_process_has_exit_code_one() 87 | { 88 | var fixture = new Fixture(); 89 | fixture.GivenProcessExitsWithCode(1); 90 | 91 | var result = Record.Exception(() => fixture.Run()); 92 | 93 | Assert.IsType(result); 94 | Assert.Equal("Terraform: Process returned an error (exit code 1).", result.Message); 95 | } 96 | 97 | [Fact] 98 | public void Should_have_changes_if_process_has_exit_code_two() 99 | { 100 | var fixture = new Fixture(); 101 | fixture.GivenProcessExitsWithCode(2); 102 | 103 | var result = fixture.Run(); 104 | 105 | Assert.True(fixture.HasChanges); 106 | } 107 | 108 | [Fact] 109 | public void Should_set_plan_parameter() 110 | { 111 | var fixture = new Fixture(); 112 | 113 | var result = fixture.Run(); 114 | 115 | Assert.Contains("plan", result.Args); 116 | } 117 | 118 | [Fact] 119 | public void Should_set_detailed_exit_code() 120 | { 121 | var fixture = new Fixture(); 122 | var result = fixture.Run(); 123 | 124 | Assert.Contains("-detailed-exitcode", result.Args); 125 | } 126 | 127 | [Fact] 128 | public void Should_set_parallelism() 129 | { 130 | var fixture = new Fixture(); 131 | fixture.Settings = new TerraformPlanSettings {Parallelism = 10}; 132 | var result = fixture.Run(); 133 | 134 | Assert.Contains("-parallelism=10", result.Args); 135 | } 136 | 137 | [Fact] 138 | public void Should_not_set_parallelism_if_zero() 139 | { 140 | var fixture = new Fixture(); 141 | var result = fixture.Run(); 142 | 143 | Assert.DoesNotContain("-parallelism", result.Args); 144 | } 145 | 146 | [Fact] 147 | public void Should_set_input_variables() 148 | { 149 | var fixture = new Fixture(); 150 | fixture.Settings = new TerraformPlanSettings 151 | { 152 | InputVariables = new Dictionary 153 | { 154 | { "access_key", "foo" }, 155 | { "secret_key", "bar" } 156 | } 157 | }; 158 | var result = fixture.Run(); 159 | 160 | Assert.Contains("-var \"access_key=foo\" -var \"secret_key=bar\"", result.Args); 161 | } 162 | 163 | [Fact] 164 | public void Should_set_input_variables_file() 165 | { 166 | var fixture = new Fixture 167 | { 168 | Settings = new TerraformPlanSettings 169 | { 170 | InputVariablesFile = "./aws-creds.json", 171 | InputVariables = new Dictionary 172 | { 173 | {"access_key", "foo"}, 174 | {"secret_key", "bar"} 175 | } 176 | } 177 | }; 178 | var result = fixture.Run(); 179 | 180 | Assert.Contains("-var-file \"./aws-creds.json\" -var \"access_key=foo\" -var \"secret_key=bar\"", result.Args); 181 | } 182 | 183 | [Fact] 184 | public void Should_set_destroy_flag_when_set_to_true() 185 | { 186 | var fixture = new Fixture(); 187 | fixture.Settings = new TerraformPlanSettings 188 | { 189 | Destroy = true 190 | }; 191 | var result = fixture.Run(); 192 | 193 | Assert.Contains("-destroy", result.Args); 194 | } 195 | 196 | [Fact] 197 | public void Should_not_set_destroy_flag_if_set_to_false() 198 | { 199 | var fixture = new Fixture(); 200 | fixture.Settings = new TerraformPlanSettings 201 | { 202 | Destroy = false 203 | }; 204 | var result = fixture.Run(); 205 | 206 | Assert.DoesNotContain("-destroy", result.Args); 207 | } 208 | 209 | [Fact] 210 | public void Should_omit_input_flag_by_default() 211 | { 212 | var fixture = new Fixture(); 213 | 214 | var result = fixture.Run(); 215 | 216 | Assert.DoesNotContain("-input", result.Args); 217 | } 218 | 219 | [Fact] 220 | public void Should_include_input_flag_when_setting_is_false() 221 | { 222 | var fixture = new Fixture 223 | { 224 | Settings = new TerraformPlanSettings 225 | { 226 | Input = false 227 | } 228 | }; 229 | 230 | var result = fixture.Run(); 231 | 232 | Assert.Contains("-input", result.Args); 233 | } 234 | } 235 | } 236 | } -------------------------------------------------------------------------------- /src/Cake.Terraform.Tests/TerraformRefreshTests.cs: -------------------------------------------------------------------------------- 1 | using System; 2 | using Cake.Core; 3 | using Cake.Terraform.Refresh; 4 | using Cake.Testing; 5 | using Xunit; 6 | 7 | namespace Cake.Terraform.Tests 8 | { 9 | using System.Collections.Generic; 10 | 11 | public class TerraformRefreshTests 12 | { 13 | class Fixture : TerraformFixture 14 | { 15 | public Fixture(PlatformFamily platformFamily = PlatformFamily.Windows) : base(platformFamily) { } 16 | 17 | protected override void RunTool() 18 | { 19 | var tool = new TerraformRefreshRunner(FileSystem, Environment, ProcessRunner, Tools); 20 | tool.Run(Settings); 21 | } 22 | } 23 | 24 | public class TheExecutable 25 | { 26 | [Fact] 27 | public void Should_throw_if_terraform_runner_was_not_found() 28 | { 29 | var fixture = new Fixture(); 30 | fixture.GivenDefaultToolDoNotExist(); 31 | 32 | var result = Record.Exception(() => fixture.Run()); 33 | 34 | Assert.IsType(result); 35 | Assert.Equal("Terraform: Could not locate executable.", result.Message); 36 | } 37 | 38 | [Theory] 39 | [InlineData("/bin/tools/terraform/terraform.exe", "/bin/tools/terraform/terraform.exe")] 40 | [InlineData("/bin/tools/terraform/terraform", "/bin/tools/terraform/terraform")] 41 | public void Should_use_terraform_from_tool_path_if_provided(string toolPath, string expected) 42 | { 43 | var fixture = new Fixture {Settings = {ToolPath = toolPath}}; 44 | fixture.GivenSettingsToolPathExist(); 45 | 46 | var result = fixture.Run(); 47 | 48 | Assert.Equal(expected, result.Path.FullPath); 49 | } 50 | 51 | [Fact] 52 | public void Should_find_terraform_if_tool_path_not_provided() 53 | { 54 | var fixture = new Fixture(); 55 | 56 | var result = fixture.Run(); 57 | 58 | Assert.Equal("/Working/tools/terraform.exe", result.Path.FullPath); 59 | } 60 | 61 | [Fact] 62 | public void Should_throw_if_process_has_a_non_zero_exit_code() 63 | { 64 | var fixture = new Fixture(); 65 | fixture.GivenProcessExitsWithCode(1); 66 | 67 | var result = Record.Exception(() => fixture.Run()); 68 | 69 | Assert.IsType(result); 70 | Assert.Equal("Terraform: Process returned an error (exit code 1).", result.Message); 71 | } 72 | 73 | [Fact] 74 | public void Should_find_linux_executable() 75 | { 76 | var fixture = new Fixture(PlatformFamily.Linux); 77 | fixture.Environment.Platform.Family = PlatformFamily.Linux; 78 | 79 | 80 | var result = fixture.Run(); 81 | 82 | Assert.Equal("/Working/tools/terraform", result.Path.FullPath); 83 | } 84 | 85 | [Fact] 86 | public void Should_set_refresh_parameter() 87 | { 88 | var fixture = new Fixture(); 89 | 90 | var result = fixture.Run(); 91 | 92 | Assert.Contains("refresh", result.Args); 93 | } 94 | 95 | [Fact] 96 | public void Should_set_input_variables() 97 | { 98 | var fixture = new Fixture 99 | { 100 | Settings = new TerraformRefreshSettings 101 | { 102 | InputVariables = new Dictionary 103 | { 104 | {"access_key", "foo"}, {"secret_key", "bar"} 105 | } 106 | } 107 | }; 108 | var result = fixture.Run(); 109 | 110 | Assert.Contains("-var \"access_key=foo\" -var \"secret_key=bar\"", result.Args); 111 | } 112 | 113 | [Obsolete("Remove, together with InputVariablesFile")] 114 | [Fact] 115 | public void Should_set_input_variables_file() 116 | { 117 | var fixture = new Fixture 118 | { 119 | Settings = new TerraformRefreshSettings 120 | { 121 | InputVariablesFile = "./aws-creds.json", 122 | InputVariables = new Dictionary 123 | { 124 | {"access_key", "foo"}, 125 | {"secret_key", "bar"} 126 | } 127 | } 128 | }; 129 | var result = fixture.Run(); 130 | 131 | Assert.Contains("-var-file \"./aws-creds.json\" -var \"access_key=foo\" -var \"secret_key=bar\"", 132 | result.Args); 133 | } 134 | 135 | [Fact] 136 | public void Should_set_input_variables_files() 137 | { 138 | var fixture = new Fixture 139 | { 140 | Settings = new TerraformRefreshSettings 141 | { 142 | InputVariablesFiles = { "./aws-creds.json", "./more-vars.json" }, 143 | InputVariables = new Dictionary 144 | { 145 | {"access_key", "foo"}, 146 | {"secret_key", "bar"} 147 | } 148 | } 149 | }; 150 | var result = fixture.Run(); 151 | 152 | Assert.Contains("-var-file \"./aws-creds.json\" -var-file \"./more-vars.json\" -var \"access_key=foo\" -var \"secret_key=bar\"", 153 | result.Args); 154 | } 155 | } 156 | } 157 | } -------------------------------------------------------------------------------- /src/Cake.Terraform.Tests/TerraformShowTests.cs: -------------------------------------------------------------------------------- 1 | using System.IO; 2 | using Cake.Core; 3 | using Cake.Terraform.Show; 4 | using Cake.Testing; 5 | using Xunit; 6 | 7 | namespace Cake.Terraform.Tests 8 | { 9 | public class TerraformShowTests 10 | { 11 | class Fixture : TerraformFixture 12 | { 13 | public Fixture(PlatformFamily platformFamily = PlatformFamily.Windows) : base(platformFamily) { } 14 | 15 | protected override void RunTool() 16 | { 17 | var tool = new TerraformShowRunner(FileSystem, Environment, ProcessRunner, Tools); 18 | Settings.PlanFile = "my.plan"; 19 | ProcessRunner.Process.SetStandardOutput(new[] { "output" }); 20 | tool.Run(Settings); 21 | } 22 | } 23 | 24 | 25 | public class TheExecutable 26 | { 27 | [Fact] 28 | public void Should_throw_if_terraform_runner_was_not_found() 29 | { 30 | var fixture = new Fixture(); 31 | fixture.GivenDefaultToolDoNotExist(); 32 | 33 | var result = Record.Exception(() => fixture.Run()); 34 | 35 | Assert.IsType(result); 36 | Assert.Equal("Terraform: Could not locate executable.", result.Message); 37 | } 38 | 39 | [Theory] 40 | [InlineData("/bin/tools/terraform/terraform.exe", "/bin/tools/terraform/terraform.exe")] 41 | [InlineData("/bin/tools/terraform/terraform", "/bin/tools/terraform/terraform")] 42 | public void Should_use_terraform_from_tool_path_if_provided(string toolPath, string expected) 43 | { 44 | var fixture = new Fixture {Settings = {ToolPath = toolPath}}; 45 | fixture.GivenSettingsToolPathExist(); 46 | 47 | var result = fixture.Run(); 48 | 49 | Assert.Equal(expected, result.Path.FullPath); 50 | } 51 | 52 | [Fact] 53 | public void Should_find_terraform_if_tool_path_not_provided() 54 | { 55 | var fixture = new Fixture(); 56 | 57 | var result = fixture.Run(); 58 | 59 | Assert.Equal("/Working/tools/terraform.exe", result.Path.FullPath); 60 | } 61 | 62 | [Fact] 63 | public void Should_find_linux_executable() 64 | { 65 | var fixture = new Fixture(PlatformFamily.Linux); 66 | 67 | var result = fixture.Run(); 68 | 69 | Assert.Equal("/Working/tools/terraform", result.Path.FullPath); 70 | } 71 | 72 | [Fact] 73 | public void Should_set_show_parameter() 74 | { 75 | var fixture = new Fixture(); 76 | 77 | var result = fixture.Run(); 78 | 79 | Assert.Contains("show", result.Args); 80 | } 81 | 82 | [Fact] 83 | public void Should_set_plan_file_parameter() 84 | { 85 | var fixture = new Fixture { Settings = { PlanFile = "./input/myplan.plan" }}; 86 | 87 | var result = fixture.Run(); 88 | 89 | Assert.Contains(fixture.Settings.PlanFile.FullPath, result.Args); 90 | } 91 | 92 | [Fact] 93 | public void Should_redirect_stdout_to_file_if_set() 94 | { 95 | var fixture = new Fixture {Settings = { OutFile = "./output.txt" }}; 96 | 97 | var result = fixture.Run(); 98 | 99 | Assert.True(result.Process.RedirectStandardOutput); 100 | Assert.Equal(fixture.ProcessRunner.Process.GetStandardOutput(), File.ReadAllLines(fixture.Settings.OutFile.FullPath)); 101 | } 102 | } 103 | } 104 | } -------------------------------------------------------------------------------- /src/Cake.Terraform.Tests/TerraformValidateTests.cs: -------------------------------------------------------------------------------- 1 | using System.Collections.Generic; 2 | using Cake.Core; 3 | using Cake.Terraform.Validate; 4 | using Cake.Testing; 5 | using Xunit; 6 | 7 | namespace Cake.Terraform.Tests 8 | { 9 | public class TerraformValidateTests 10 | { 11 | class Fixture : TerraformFixture 12 | { 13 | public Fixture(PlatformFamily platformFamily = PlatformFamily.Windows) : base(platformFamily) { } 14 | 15 | protected override void RunTool() 16 | { 17 | ProcessRunner.Process.SetStandardOutput(new List { "default" }); 18 | 19 | var tool = new TerraformValidateRunner(FileSystem, Environment, ProcessRunner, Tools); 20 | 21 | tool.Run(Settings); 22 | } 23 | } 24 | 25 | public class TheExecutable 26 | { 27 | [Fact] 28 | public void Should_throw_if_terraform_runner_was_not_found() 29 | { 30 | var fixture = new Fixture(); 31 | fixture.GivenDefaultToolDoNotExist(); 32 | 33 | var result = Record.Exception(() => fixture.Run()); 34 | 35 | Assert.IsType(result); 36 | Assert.Equal("Terraform: Could not locate executable.", result.Message); 37 | } 38 | 39 | [Theory] 40 | [InlineData("/bin/tools/terraform/terraform.exe", "/bin/tools/terraform/terraform.exe")] 41 | [InlineData("/bin/tools/terraform/terraform", "/bin/tools/terraform/terraform")] 42 | public void Should_use_terraform_from_tool_path_if_provided(string toolPath, string expected) 43 | { 44 | var fixture = new Fixture() { Settings = { ToolPath = toolPath } }; 45 | fixture.GivenSettingsToolPathExist(); 46 | 47 | var result = fixture.Run(); 48 | 49 | Assert.Equal(expected, result.Path.FullPath); 50 | } 51 | 52 | [Fact] 53 | public void Should_find_terraform_if_tool_path_not_provided() 54 | { 55 | var fixture = new Fixture(); 56 | 57 | var result = fixture.Run(); 58 | 59 | Assert.Equal("/Working/tools/terraform.exe", result.Path.FullPath); 60 | } 61 | 62 | [Fact] 63 | public void Should_throw_if_process_has_a_non_zero_exit_code() 64 | { 65 | var fixture = new Fixture(); 66 | fixture.GivenProcessExitsWithCode(1); 67 | 68 | var result = Record.Exception(() => fixture.Run()); 69 | 70 | Assert.IsType(result); 71 | Assert.Equal("Terraform: Process returned an error (exit code 1).", result.Message); 72 | } 73 | 74 | [Fact] 75 | public void Should_find_linux_executable() 76 | { 77 | var fixture = new Fixture(PlatformFamily.Linux); 78 | fixture.Environment.Platform.Family = PlatformFamily.Linux; 79 | 80 | 81 | var result = fixture.Run(); 82 | 83 | Assert.Equal("/Working/tools/terraform", result.Path.FullPath); 84 | } 85 | 86 | [Fact] 87 | public void Should_set_workspace_and_list_parameter() 88 | { 89 | var fixture = new Fixture(); 90 | 91 | var result = fixture.Run(); 92 | 93 | Assert.Contains("validate", result.Args); 94 | } 95 | } 96 | } 97 | } 98 | -------------------------------------------------------------------------------- /src/Cake.Terraform.sln: -------------------------------------------------------------------------------- 1 |  2 | Microsoft Visual Studio Solution File, Format Version 12.00 3 | # Visual Studio 15 4 | VisualStudioVersion = 15.0.26228.12 5 | MinimumVisualStudioVersion = 10.0.40219.1 6 | Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "Cake.Terraform", "Cake.Terraform\Cake.Terraform.csproj", "{C6E9A60F-9055-4E54-9E29-7F277875ABC1}" 7 | EndProject 8 | Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "Cake.Terraform.Tests", "Cake.Terraform.Tests\Cake.Terraform.Tests.csproj", "{AB9EDCDE-48B6-4B6E-B0B6-28CF549A6591}" 9 | EndProject 10 | Project("{2150E333-8FDC-42A3-9474-1A3956D46DE8}") = "SolutionItems", "SolutionItems", "{78C1E10D-45E1-4D1A-8063-B063BE554D6E}" 11 | ProjectSection(SolutionItems) = preProject 12 | Directory.Build.targets = Directory.Build.targets 13 | Directory.Build.props = Directory.Build.props 14 | EndProjectSection 15 | EndProject 16 | Global 17 | GlobalSection(SolutionConfigurationPlatforms) = preSolution 18 | Debug|Any CPU = Debug|Any CPU 19 | Release|Any CPU = Release|Any CPU 20 | EndGlobalSection 21 | GlobalSection(ProjectConfigurationPlatforms) = postSolution 22 | {C6E9A60F-9055-4E54-9E29-7F277875ABC1}.Debug|Any CPU.ActiveCfg = Debug|Any CPU 23 | {C6E9A60F-9055-4E54-9E29-7F277875ABC1}.Debug|Any CPU.Build.0 = Debug|Any CPU 24 | {C6E9A60F-9055-4E54-9E29-7F277875ABC1}.Release|Any CPU.ActiveCfg = Release|Any CPU 25 | {C6E9A60F-9055-4E54-9E29-7F277875ABC1}.Release|Any CPU.Build.0 = Release|Any CPU 26 | {AB9EDCDE-48B6-4B6E-B0B6-28CF549A6591}.Debug|Any CPU.ActiveCfg = Debug|Any CPU 27 | {AB9EDCDE-48B6-4B6E-B0B6-28CF549A6591}.Debug|Any CPU.Build.0 = Debug|Any CPU 28 | {AB9EDCDE-48B6-4B6E-B0B6-28CF549A6591}.Release|Any CPU.ActiveCfg = Release|Any CPU 29 | {AB9EDCDE-48B6-4B6E-B0B6-28CF549A6591}.Release|Any CPU.Build.0 = Release|Any CPU 30 | EndGlobalSection 31 | GlobalSection(SolutionProperties) = preSolution 32 | HideSolutionNode = FALSE 33 | EndGlobalSection 34 | EndGlobal 35 | -------------------------------------------------------------------------------- /src/Cake.Terraform/Apply/TerraformApplyRunner.cs: -------------------------------------------------------------------------------- 1 | using System.Collections.Generic; 2 | using Cake.Core; 3 | using Cake.Core.IO; 4 | using Cake.Core.Tooling; 5 | 6 | namespace Cake.Terraform.Apply 7 | { 8 | public class TerraformApplyRunner : TerraformRunner 9 | { 10 | public TerraformApplyRunner(IFileSystem fileSystem, ICakeEnvironment environment, IProcessRunner processRunner, IToolLocator tools) 11 | : base(fileSystem, environment, processRunner, tools) 12 | { 13 | } 14 | 15 | public void Run(TerraformApplySettings settings) 16 | { 17 | var builder = new ProcessArgumentBuilder() 18 | .Append("apply"); 19 | 20 | if (settings.Destroy) 21 | { 22 | builder.Append("-destroy"); 23 | } 24 | 25 | // Order of AutoApprove and Plan are important. 26 | if (settings.AutoApprove) 27 | { 28 | builder.Append("-auto-approve"); 29 | } 30 | 31 | // Use Plan if it exists. 32 | if (settings.Plan != null) 33 | { 34 | builder.AppendQuoted(settings.Plan.FullPath); 35 | } 36 | 37 | if (settings.Parallelism != default(int)) 38 | { 39 | builder.AppendSwitch("-parallelism", "=", settings.Parallelism.ToString()); 40 | } 41 | 42 | if (!string.IsNullOrWhiteSpace(settings.InputVariablesFile)) 43 | { 44 | builder.AppendSwitchQuoted("-var-file", $"{settings.InputVariablesFile}"); 45 | } 46 | 47 | foreach (var inputVariable in settings.InputVariables ?? new Dictionary()) 48 | { 49 | builder.AppendSwitchQuoted("-var", $"{inputVariable.Key}={inputVariable.Value}"); 50 | } 51 | 52 | if (!settings.Input) 53 | { 54 | builder.AppendSwitch("-input", "=", settings.Input.ToString()); 55 | } 56 | 57 | Run(settings, builder); 58 | } 59 | } 60 | } 61 | -------------------------------------------------------------------------------- /src/Cake.Terraform/Apply/TerraformApplySettings.cs: -------------------------------------------------------------------------------- 1 | using System.Collections.Generic; 2 | using Cake.Core.IO; 3 | 4 | namespace Cake.Terraform.Apply 5 | { 6 | public class TerraformApplySettings : TerraformSettings 7 | { 8 | public TerraformApplySettings() 9 | { 10 | this.Input = true; 11 | } 12 | 13 | public int Parallelism { get; set; } 14 | 15 | public FilePath Plan { get; set; } 16 | 17 | /// 18 | /// Gets or sets the input variables. https://www.terraform.io/intro/getting-started/variables.html 19 | /// 20 | public Dictionary InputVariables { get; set; } 21 | 22 | /// 23 | /// Variables file 24 | /// https://www.terraform.io/docs/configuration/variables.html#variable-files 25 | /// 26 | public string InputVariablesFile { get; set; } 27 | 28 | /// 29 | /// Skip interactive approval of plan before applying. 30 | /// https://www.terraform.io/docs/commands/apply.html#auto-approve 31 | /// 32 | public bool AutoApprove { get; set; } 33 | 34 | /// 35 | /// Ask for input for variables if not directly set. 36 | /// https://www.terraform.io/docs/commands/apply.html#input-true 37 | /// 38 | public bool Input { get; set; } 39 | 40 | /// 41 | /// Does destory 42 | /// https://www.terraform.io/docs/commands/destroy.html 43 | /// 44 | public bool Destroy { get; set; } 45 | } 46 | } -------------------------------------------------------------------------------- /src/Cake.Terraform/Cake.Terraform.csproj: -------------------------------------------------------------------------------- 1 |  2 | 3 | 4 | net6.0;net7.0;net8.0 5 | 6 | 7 | 8 | 9 | 10 | 11 | 12 | 13 | Erik van Brakel 14 | opyright (c) 2017 - Present — Erik van Brakel 15 | Cake AddIn that extends Cake with ability to execute terraform commands. 16 | This version was build for Cake v$(CakeVersion) 17 | MIT 18 | https://github.com/cake-contrib/Cake.Terraform 19 | cake;build;cake-build;script;addin;cake-addin;terraform;hashicorp 20 | $(PackageProjectUrl).git 21 | This version was build for Cake v$(CakeVersion). 22 | For details see $(PackageProjectUrl)/releases 23 | 0.0.0 24 | README.md 25 | 26 | 27 | 28 | 29 | 0.1.3 30 | all 31 | runtime; build; native; contentfiles; analyzers; buildtransitive 32 | 33 | 34 | $(CakeVersion) 35 | 36 | 37 | 1.5.1 38 | all 39 | runtime; build; native; contentfiles; analyzers; buildtransitive 40 | 41 | 42 | runtime; build; native; contentfiles; analyzers; buildtransitive 43 | all 44 | 45 | 46 | 47 | 48 | -------------------------------------------------------------------------------- /src/Cake.Terraform/Destroy/TerraformDestroyRunner.cs: -------------------------------------------------------------------------------- 1 | using System.Collections.Generic; 2 | using Cake.Core; 3 | using Cake.Core.IO; 4 | using Cake.Core.Tooling; 5 | 6 | namespace Cake.Terraform.Destroy 7 | { 8 | public class TerraformDestroyRunner : TerraformRunner 9 | { 10 | public TerraformDestroyRunner(IFileSystem fileSystem, ICakeEnvironment environment, IProcessRunner processRunner, IToolLocator tools) 11 | : base(fileSystem, environment, processRunner, tools) 12 | { 13 | } 14 | 15 | public void Run(TerraformDestroySettings settings) 16 | { 17 | var builder = new ProcessArgumentBuilder().Append("destroy"); 18 | 19 | if (settings.Force) 20 | { 21 | builder = builder.Append("-force"); 22 | } 23 | 24 | if (!string.IsNullOrWhiteSpace(settings.InputVariablesFile)) 25 | { 26 | builder.AppendSwitchQuoted("-var-file", $"{settings.InputVariablesFile}"); 27 | } 28 | 29 | foreach (var inputVariable in settings.InputVariables ?? new Dictionary()) 30 | { 31 | builder.AppendSwitchQuoted("-var", $"{inputVariable.Key}={inputVariable.Value}"); 32 | } 33 | 34 | Run(settings, builder); 35 | } 36 | } 37 | } -------------------------------------------------------------------------------- /src/Cake.Terraform/Destroy/TerraformDestroySettings.cs: -------------------------------------------------------------------------------- 1 | using System.Collections.Generic; 2 | 3 | namespace Cake.Terraform.Destroy 4 | { 5 | /// 6 | /// The terraform destroy command is used to destroy the Terraform-managed infrastructure. 7 | /// 8 | public class TerraformDestroySettings : TerraformSettings 9 | { 10 | /// 11 | /// Gets or sets the input variables. https://www.terraform.io/intro/getting-started/variables.html 12 | /// 13 | public Dictionary InputVariables { get; set; } 14 | 15 | /// 16 | /// Variables file 17 | /// https://www.terraform.io/docs/configuration/variables.html#variable-files 18 | /// 19 | public string InputVariablesFile { get; set; } 20 | 21 | /// 22 | /// If set to true, then the destroy confirmation will not be shown. 23 | /// 24 | public bool Force { get; set; } 25 | } 26 | } -------------------------------------------------------------------------------- /src/Cake.Terraform/EnvDelete/TerraformEnvDeleteRunner.cs: -------------------------------------------------------------------------------- 1 | using Cake.Core; 2 | using Cake.Core.IO; 3 | using Cake.Core.Tooling; 4 | 5 | namespace Cake.Terraform.EnvDelete 6 | { 7 | public class TerraformEnvDeleteRunner : TerraformRunner 8 | { 9 | public TerraformEnvDeleteRunner(IFileSystem fileSystem, ICakeEnvironment environment, IProcessRunner processRunner, IToolLocator tools) 10 | : base(fileSystem, environment, processRunner, tools) 11 | { 12 | } 13 | public void Run(TerraformEnvDeleteSettings settings) 14 | { 15 | var builder = new ProcessArgumentBuilder() 16 | .Append(settings.EnvCommand.ToString().ToLower()) 17 | .Append("delete"); 18 | 19 | if (settings.Force) 20 | { 21 | builder = builder.Append("-force"); 22 | } 23 | 24 | Run(settings, builder); 25 | } 26 | } 27 | } -------------------------------------------------------------------------------- /src/Cake.Terraform/EnvDelete/TerraformEnvDeleteSettings.cs: -------------------------------------------------------------------------------- 1 | namespace Cake.Terraform.EnvDelete 2 | { 3 | public class TerraformEnvDeleteSettings : TerraformEnvSettings 4 | { 5 | public string Environment { get; set; } 6 | 7 | /// 8 | /// If set to true, then on Subcommand delete the state even if non-empty. Defaults to false. 9 | /// 10 | public bool Force { get; set; } 11 | } 12 | } -------------------------------------------------------------------------------- /src/Cake.Terraform/EnvList/TerraformEnvListRunner.cs: -------------------------------------------------------------------------------- 1 | using System.Collections.Generic; 2 | using System.Linq; 3 | using Cake.Core; 4 | using Cake.Core.IO; 5 | using Cake.Core.Tooling; 6 | 7 | namespace Cake.Terraform.EnvList 8 | { 9 | public class TerraformEnvListRunner : TerraformRunner 10 | { 11 | public TerraformEnvListRunner(IFileSystem fileSystem, ICakeEnvironment environment, IProcessRunner processRunner, IToolLocator tools) 12 | : base(fileSystem, environment, processRunner, tools) 13 | { 14 | } 15 | 16 | public List Run(TerraformEnvListSettings settings) 17 | { 18 | var builder = 19 | new ProcessArgumentBuilder() 20 | .Append(settings.EnvCommand.ToString().ToLower()) 21 | .Append("list"); 22 | 23 | var processSettings = new ProcessSettings 24 | { 25 | RedirectStandardOutput = true 26 | }; 27 | 28 | var result = new List(); 29 | this.Run(settings, builder, processSettings, x => 30 | { 31 | result = x.GetStandardOutput() 32 | .Select(env => env.Replace("*", "").Trim()) 33 | .Where(env => !string.IsNullOrWhiteSpace(env)) 34 | .ToList(); 35 | }); 36 | 37 | return result; 38 | } 39 | } 40 | } -------------------------------------------------------------------------------- /src/Cake.Terraform/EnvList/TerraformEnvListSettings.cs: -------------------------------------------------------------------------------- 1 | namespace Cake.Terraform.EnvList 2 | { 3 | public class TerraformEnvListSettings : TerraformEnvSettings 4 | { 5 | } 6 | } -------------------------------------------------------------------------------- /src/Cake.Terraform/EnvNew/TerraformEnvNewRunner.cs: -------------------------------------------------------------------------------- 1 | using System; 2 | using Cake.Core; 3 | using Cake.Core.IO; 4 | using Cake.Core.Tooling; 5 | 6 | namespace Cake.Terraform.EnvNew 7 | { 8 | public class TerraformEnvNewRunner : TerraformRunner 9 | { 10 | public TerraformEnvNewRunner(IFileSystem fileSystem, ICakeEnvironment environment, IProcessRunner processRunner, IToolLocator tools) 11 | : base(fileSystem, environment, processRunner, tools) 12 | { 13 | } 14 | 15 | public void Run(TerraformEnvNewSettings settings) 16 | { 17 | if (string.IsNullOrEmpty(settings.Environment)) 18 | { 19 | throw new ArgumentException(nameof(settings.Environment)); 20 | } 21 | 22 | var builder = new ProcessArgumentBuilder() 23 | .Append(settings.EnvCommand.ToString().ToLower()) 24 | .Append("new") 25 | .Append(settings.Environment); 26 | 27 | Run(settings, builder); 28 | } 29 | } 30 | } -------------------------------------------------------------------------------- /src/Cake.Terraform/EnvNew/TerraformEnvNewSettings.cs: -------------------------------------------------------------------------------- 1 | namespace Cake.Terraform.EnvNew 2 | { 3 | public class TerraformEnvNewSettings : TerraformEnvSettings 4 | { 5 | public string Environment { get; set; } 6 | } 7 | } -------------------------------------------------------------------------------- /src/Cake.Terraform/EnvSelect/TerraformEnvSelectRunner.cs: -------------------------------------------------------------------------------- 1 | using System; 2 | using Cake.Core; 3 | using Cake.Core.IO; 4 | using Cake.Core.Tooling; 5 | 6 | namespace Cake.Terraform.EnvSelect 7 | { 8 | public class TerraformEnvSelectRunner : TerraformRunner 9 | { 10 | public TerraformEnvSelectRunner(IFileSystem fileSystem, ICakeEnvironment environment, IProcessRunner processRunner, IToolLocator tools) 11 | : base(fileSystem, environment, processRunner, tools) 12 | { 13 | } 14 | 15 | public void Run(TerraformEnvSelectSettings settings) 16 | { 17 | if (string.IsNullOrEmpty(settings.Environment)) 18 | { 19 | throw new ArgumentException(nameof(settings.Environment)); 20 | } 21 | 22 | var builder = new ProcessArgumentBuilder() 23 | .Append(settings.EnvCommand.ToString().ToLower()) 24 | .Append("select") 25 | .Append(settings.Environment); 26 | 27 | Run(settings, builder); 28 | } 29 | } 30 | } -------------------------------------------------------------------------------- /src/Cake.Terraform/EnvSelect/TerraformEnvSelectSettings.cs: -------------------------------------------------------------------------------- 1 | namespace Cake.Terraform.EnvSelect 2 | { 3 | public class TerraformEnvSelectSettings : TerraformEnvSettings 4 | { 5 | public string Environment { get; set; } 6 | } 7 | } -------------------------------------------------------------------------------- /src/Cake.Terraform/Init/TerraformInitRunner.cs: -------------------------------------------------------------------------------- 1 | using System.Collections.Generic; 2 | using Cake.Core; 3 | using Cake.Core.IO; 4 | using Cake.Core.Tooling; 5 | 6 | namespace Cake.Terraform.Init 7 | { 8 | public class TerraformInitRunner : TerraformRunner 9 | { 10 | public TerraformInitRunner(IFileSystem fileSystem, ICakeEnvironment environment, IProcessRunner processRunner, IToolLocator tools) 11 | : base(fileSystem, environment, processRunner, tools) 12 | { 13 | } 14 | 15 | public void Run(TerraformInitSettings settings) 16 | { 17 | var builder = new ProcessArgumentBuilder().Append("init"); 18 | 19 | foreach (var pair in settings.BackendConfigOverrides ?? new Dictionary()) 20 | { 21 | // https://www.terraform.io/docs/commands/init.html#backend-config-value 22 | builder.AppendSwitchQuoted("-backend-config", $"{pair.Key}={pair.Value}"); 23 | } 24 | 25 | if (settings.ForceCopy) 26 | { 27 | builder.Append("-force-copy"); 28 | } 29 | 30 | if (settings.ForceReconfigure) 31 | { 32 | builder.Append("-reconfigure"); 33 | } 34 | 35 | if (!settings.Input) 36 | { 37 | builder.AppendSwitch("-input", "=", settings.Input.ToString()); 38 | } 39 | 40 | if (!settings.Backend) 41 | { 42 | builder.AppendSwitch("-backend", "=", settings.Backend.ToString()); 43 | } 44 | 45 | Run(settings, builder); 46 | } 47 | } 48 | } -------------------------------------------------------------------------------- /src/Cake.Terraform/Init/TerraformInitSettings.cs: -------------------------------------------------------------------------------- 1 | using System.Collections.Generic; 2 | 3 | namespace Cake.Terraform.Init 4 | { 5 | public class TerraformInitSettings : TerraformSettings 6 | { 7 | public TerraformInitSettings() 8 | { 9 | this.Input = true; 10 | this.Backend = true; 11 | } 12 | 13 | /// 14 | /// A set of backend config key-value overrides to be passed to `terraform init` 15 | /// https://www.terraform.io/docs/commands/init.html#backend-config-value 16 | /// 17 | public Dictionary BackendConfigOverrides { get; set; } 18 | 19 | /// 20 | /// Reconfigure the backend, ignoring any saved configuration. 21 | /// https://www.terraform.io/docs/commands/init.html#reconfigure 22 | /// 23 | public bool ForceReconfigure { get; set; } 24 | 25 | /// 26 | /// Suppress prompts about copying state data. This is equivalent to providing 27 | /// a "yes" to all confirmation prompts. 28 | /// https://www.terraform.io/docs/commands/init.html#force-copy 29 | /// 30 | public bool ForceCopy { get; set; } 31 | 32 | /// 33 | /// Ask for input if necessary. If false, will error if input was required. 34 | /// https://www.terraform.io/docs/commands/init.html#input-true 35 | /// 36 | public bool Input { get; set; } 37 | 38 | /// 39 | /// Configure the backend for this configuration. 40 | /// https://www.terraform.io/docs/commands/init.html#backend-initialization 41 | /// 42 | public bool Backend { get; set; } 43 | } 44 | } 45 | -------------------------------------------------------------------------------- /src/Cake.Terraform/Output/TerraformOutputRunner.cs: -------------------------------------------------------------------------------- 1 | using System; 2 | using System.Linq; 3 | using System.Text; 4 | using Cake.Core; 5 | using Cake.Core.IO; 6 | using Cake.Core.Tooling; 7 | 8 | namespace Cake.Terraform.Output 9 | { 10 | public class TerraformOutputRunner : TerraformRunner 11 | { 12 | public TerraformOutputRunner(IFileSystem fileSystem, ICakeEnvironment environment, IProcessRunner processRunner, IToolLocator tools) 13 | : base(fileSystem, environment, processRunner, tools) 14 | { 15 | } 16 | 17 | private static string RemoveWhitespace(string x) 18 | { 19 | return x 20 | .Replace("\n", "") 21 | .Replace("\r", "") 22 | .Replace(" ", ""); 23 | } 24 | 25 | private void ConfirmSuccess(string output) 26 | { 27 | string outputNotFoundErrorString = RemoveWhitespace("The output variable requested could not be found in the state file. If you recently added this to your configuration, be sure to run `terraform apply`, since the state won't be updated with new output variables until that command is run."); 28 | 29 | if (RemoveWhitespace(output) == outputNotFoundErrorString) 30 | { 31 | throw new ArgumentException(output); 32 | } 33 | } 34 | 35 | public string Run(TerraformOutputSettings settings) 36 | { 37 | var arguments = new ProcessArgumentBuilder() 38 | .Append("output") 39 | .Append("-no-color"); 40 | 41 | if (settings.StatePath != null) 42 | { 43 | arguments.Append($"-state={settings.StatePath}"); 44 | } 45 | 46 | if (settings.Raw) 47 | { 48 | arguments.Append("-raw"); 49 | } 50 | else if (settings.Json) 51 | { 52 | arguments.Append("-json"); 53 | } 54 | 55 | if (settings.OutputName != null) 56 | { 57 | arguments.Append(settings.OutputName); 58 | } 59 | 60 | var processSettings = new ProcessSettings 61 | { 62 | RedirectStandardOutput = true 63 | }; 64 | 65 | string output = null; 66 | Run(settings, arguments, processSettings, x => 67 | { 68 | var outputLines = x.GetStandardOutput().ToList(); 69 | int lineCount = outputLines.Count(); 70 | 71 | var builder = new StringBuilder(); 72 | for (int i = 0; i < lineCount; i++) 73 | { 74 | builder.Append(outputLines[i]); 75 | 76 | if (i < lineCount - 1) 77 | { 78 | builder.Append("\n"); // OS consistent 79 | } 80 | } 81 | 82 | output = builder.ToString(); 83 | }); 84 | 85 | if (settings.ValidateToolOutput) 86 | { 87 | ConfirmSuccess(output); 88 | } 89 | 90 | return output; 91 | } 92 | } 93 | } -------------------------------------------------------------------------------- /src/Cake.Terraform/Output/TerraformOutputSettings.cs: -------------------------------------------------------------------------------- 1 | namespace Cake.Terraform.Output 2 | { 3 | public class TerraformOutputSettings : TerraformSettings 4 | { 5 | public string OutputName { get; set; } 6 | public bool Json { get; set; } 7 | public bool Raw { get; set; } 8 | public string StatePath { get; set; } 9 | public bool ValidateToolOutput { get; set; } = true; 10 | } 11 | } -------------------------------------------------------------------------------- /src/Cake.Terraform/Plan/TerraformPlanRunner.cs: -------------------------------------------------------------------------------- 1 | using Cake.Core; 2 | using Cake.Core.IO; 3 | using Cake.Core.Tooling; 4 | 5 | namespace Cake.Terraform.Plan 6 | { 7 | public class TerraformPlanRunner : TerraformRunner 8 | { 9 | public TerraformPlanRunner(IFileSystem fileSystem, ICakeEnvironment environment, IProcessRunner processRunner, IToolLocator tools) 10 | : base(fileSystem, environment, processRunner, tools) 11 | { 12 | } 13 | 14 | public bool HasChanges { get; private set; } 15 | 16 | public void Run(TerraformPlanSettings settings) 17 | { 18 | var builder = new ProcessArgumentBuilder() 19 | .Append("plan") 20 | .Append($"-out={settings.OutFile}") 21 | .Append("-detailed-exitcode"); 22 | 23 | if (settings.Parallelism > 0) 24 | { 25 | builder = builder.Append($"-parallelism={settings.Parallelism}"); 26 | } 27 | 28 | if (settings.Destroy) 29 | { 30 | builder = builder.Append("-destroy"); 31 | } 32 | 33 | if (!string.IsNullOrEmpty(settings.InputVariablesFile)) 34 | { 35 | builder.AppendSwitchQuoted("-var-file", $"{settings.InputVariablesFile}"); 36 | } 37 | 38 | if (settings.InputVariables != null) 39 | { 40 | foreach (var inputVariable in settings.InputVariables) 41 | { 42 | builder.AppendSwitchQuoted("-var", $"{inputVariable.Key}={inputVariable.Value}"); 43 | } 44 | } 45 | 46 | if (!settings.Input) 47 | { 48 | builder.AppendSwitch("-input", "=", settings.Input.ToString()); 49 | } 50 | 51 | Run(settings, builder); 52 | } 53 | 54 | protected override void ProcessExitCode(int exitCode) 55 | { 56 | if (exitCode == 2) 57 | { 58 | HasChanges = true; 59 | } 60 | else 61 | { 62 | base.ProcessExitCode(exitCode); 63 | } 64 | } 65 | } 66 | } -------------------------------------------------------------------------------- /src/Cake.Terraform/Plan/TerraformPlanSettings.cs: -------------------------------------------------------------------------------- 1 | using System.Collections.Generic; 2 | using Cake.Core.IO; 3 | 4 | namespace Cake.Terraform.Plan 5 | { 6 | public class TerraformPlanSettings : TerraformSettings 7 | { 8 | public TerraformPlanSettings() 9 | { 10 | this.Input = true; 11 | } 12 | 13 | public FilePath OutFile { get; set; } 14 | 15 | public int Parallelism { get; set; } 16 | 17 | /// 18 | /// Gets or sets the input variables. https://www.terraform.io/intro/getting-started/variables.html 19 | /// 20 | public Dictionary InputVariables { get; set; } 21 | 22 | /// 23 | /// Variables file 24 | /// https://www.terraform.io/docs/configuration/variables.html#variable-files 25 | /// 26 | public string InputVariablesFile { get; set; } 27 | 28 | /// 29 | /// If set to true, generates a plan to destroy all the known resources 30 | /// 31 | public bool Destroy { get; set; } 32 | 33 | /// 34 | /// Ask for input for variables if not directly set. 35 | /// https://www.terraform.io/docs/commands/plan.html#input-true 36 | /// 37 | public bool Input { get; set; } 38 | } 39 | } -------------------------------------------------------------------------------- /src/Cake.Terraform/Refresh/TerraformRefreshRunner.cs: -------------------------------------------------------------------------------- 1 | using System.Linq; 2 | using Cake.Core; 3 | using Cake.Core.IO; 4 | using Cake.Core.Tooling; 5 | 6 | namespace Cake.Terraform.Refresh 7 | { 8 | public class TerraformRefreshRunner : TerraformRunner 9 | { 10 | public TerraformRefreshRunner(IFileSystem fileSystem, ICakeEnvironment environment, 11 | IProcessRunner processRunner, IToolLocator tools) 12 | : base(fileSystem, environment, processRunner, tools) 13 | { 14 | } 15 | 16 | public void Run(TerraformRefreshSettings settings) 17 | { 18 | var builder = new ProcessArgumentBuilder().Append("refresh"); 19 | 20 | // Use Plan if it exists. 21 | if (settings.Plan != null) 22 | { 23 | builder.Append(settings.Plan.FullPath); 24 | } 25 | 26 | foreach (var varFile in settings.InputVariablesFiles) 27 | { 28 | builder.AppendSwitchQuoted("-var-file", $"{varFile}"); 29 | } 30 | 31 | if (!string.IsNullOrEmpty(settings.InputVariablesFile)) 32 | { 33 | builder.AppendSwitchQuoted("-var-file", $"{settings.InputVariablesFile}"); 34 | } 35 | 36 | builder = settings.InputVariables?.Aggregate(builder, 37 | (b, input) => b.AppendSwitchQuoted("-var", $"{input.Key}={input.Value}")) 38 | ?? builder; 39 | 40 | Run(settings, builder); 41 | } 42 | } 43 | } -------------------------------------------------------------------------------- /src/Cake.Terraform/Refresh/TerraformRefreshSettings.cs: -------------------------------------------------------------------------------- 1 | using System; 2 | using System.Collections.Generic; 3 | using Cake.Core.IO; 4 | 5 | namespace Cake.Terraform.Refresh 6 | { 7 | public class TerraformRefreshSettings : TerraformSettings 8 | { 9 | public FilePath Plan { get; set; } 10 | 11 | /// 12 | /// Gets or sets the input variables. https://www.terraform.io/intro/getting-started/variables.html 13 | /// 14 | public Dictionary InputVariables { get; set; } 15 | 16 | [Obsolete("use InputVariablesFiles instead.")] 17 | public string InputVariablesFile { get; set; } 18 | 19 | /// 20 | /// Variables file 21 | /// https://www.terraform.io/docs/configuration/variables.html#variable-files 22 | /// 23 | public ICollection InputVariablesFiles { get; } = new List(); 24 | } 25 | } -------------------------------------------------------------------------------- /src/Cake.Terraform/Show/HtmlFormatter.cs: -------------------------------------------------------------------------------- 1 | using System.Collections.Generic; 2 | using System.Linq; 3 | using System.Net; 4 | using System.Text; 5 | using System.Text.RegularExpressions; 6 | 7 | namespace Cake.Terraform.Show 8 | { 9 | internal class HtmlFormatter : OutputFormatter 10 | { 11 | readonly Dictionary _styles = new Dictionary { 12 | { "0", "normal"}, 13 | { "1", "bold"}, 14 | { "30", "black"}, 15 | { "31", "red"}, 16 | { "32", "green"}, 17 | { "33", "yellow"}, 18 | { "34", "blue"}, 19 | { "35", "magenta"}, 20 | { "36", "cyan"}, 21 | { "37", "white"}, 22 | { "90", "grey"} 23 | }; 24 | 25 | private readonly string _header = @" 26 | 27 | 28 | 60 |

61 | ";
62 | 
63 |         private readonly string _footer = @"
64 | 
65 | "; 66 | 67 | public override string FormatLines(IEnumerable lines) 68 | { 69 | var outputBuilder = new StringBuilder(); 70 | outputBuilder.AppendLine(_header); 71 | 72 | var regex = new Regex(@"(.*)\e\[(3[0-7]|90|1)m(.*)"); 73 | foreach(var line in lines.Select(x => new Regex(@"\e\[0m").Replace(x, "").Replace("\\r","\r").Replace("\\n", "\n"))) 74 | { 75 | var match = regex.Match(line); 76 | if(match.Success) { 77 | var styledLine = $"{WebUtility.HtmlEncode(match.Groups[1].Value)}{WebUtility.HtmlEncode(match.Groups[3].Value)}"; 78 | outputBuilder.AppendLine(styledLine); 79 | } 80 | else 81 | { 82 | outputBuilder.AppendLine(WebUtility.HtmlEncode(line)); 83 | } 84 | } 85 | 86 | outputBuilder.AppendLine(_footer); 87 | 88 | return outputBuilder.ToString(); 89 | } 90 | } 91 | } -------------------------------------------------------------------------------- /src/Cake.Terraform/Show/OutputFormat.cs: -------------------------------------------------------------------------------- 1 | namespace Cake.Terraform.Show 2 | { 3 | public enum OutputFormat 4 | { 5 | PlainText, 6 | Html 7 | } 8 | } -------------------------------------------------------------------------------- /src/Cake.Terraform/Show/OutputFormatter.cs: -------------------------------------------------------------------------------- 1 | using System.Collections.Generic; 2 | 3 | namespace Cake.Terraform.Show 4 | { 5 | internal abstract class OutputFormatter 6 | { 7 | public abstract string FormatLines(IEnumerable lines); 8 | } 9 | } -------------------------------------------------------------------------------- /src/Cake.Terraform/Show/PlainTextFormatter.cs: -------------------------------------------------------------------------------- 1 | using System; 2 | using System.Collections.Generic; 3 | 4 | namespace Cake.Terraform.Show 5 | { 6 | internal class PlainTextFormatter : OutputFormatter 7 | { 8 | public override string FormatLines(IEnumerable lines) 9 | { 10 | return string.Join(Environment.NewLine, lines); 11 | } 12 | } 13 | } -------------------------------------------------------------------------------- /src/Cake.Terraform/Show/TerraformShowRunner.cs: -------------------------------------------------------------------------------- 1 | using System; 2 | using System.Collections.Generic; 3 | using System.IO; 4 | using Cake.Core; 5 | using Cake.Core.IO; 6 | using Cake.Core.Tooling; 7 | 8 | namespace Cake.Terraform.Show 9 | { 10 | public class TerraformShowRunner : TerraformRunner 11 | { 12 | private readonly Dictionary _formatters = new Dictionary 13 | { 14 | {OutputFormat.PlainText, new PlainTextFormatter()}, 15 | {OutputFormat.Html, new HtmlFormatter()} 16 | }; 17 | 18 | public TerraformShowRunner(IFileSystem fileSystem, ICakeEnvironment environment, IProcessRunner processRunner, IToolLocator tools) 19 | : base(fileSystem, environment, processRunner, tools) 20 | { 21 | } 22 | 23 | public void Run(TerraformShowSettings settings) 24 | { 25 | if (settings.PlanFile == null) 26 | { 27 | throw new ArgumentNullException(nameof(settings.PlanFile)); 28 | } 29 | 30 | var arguments = new ProcessArgumentBuilder() 31 | .Append("show") 32 | .Append(settings.PlanFile.FullPath); 33 | 34 | if (settings.OutputFormat == OutputFormat.PlainText) 35 | { 36 | arguments.Append("-no-color"); 37 | } 38 | 39 | var processSettings = new ProcessSettings(); 40 | if (settings.OutFile != null) 41 | { 42 | processSettings.RedirectStandardOutput = true; 43 | } 44 | 45 | Run(settings, arguments, processSettings, x => 46 | { 47 | if (settings.OutFile != null) 48 | { 49 | if (!_formatters.TryGetValue(settings.OutputFormat, out var formatter)) 50 | { 51 | formatter = _formatters[OutputFormat.PlainText]; 52 | } 53 | 54 | File.WriteAllText(settings.OutFile.FullPath, formatter.FormatLines(x.GetStandardOutput())); 55 | } 56 | }); 57 | } 58 | } 59 | } -------------------------------------------------------------------------------- /src/Cake.Terraform/Show/TerraformShowSettings.cs: -------------------------------------------------------------------------------- 1 | using Cake.Core.IO; 2 | 3 | namespace Cake.Terraform.Show 4 | { 5 | public class TerraformShowSettings : TerraformSettings 6 | { 7 | public FilePath OutFile { get; set; } 8 | public FilePath PlanFile { get; set; } 9 | public OutputFormat OutputFormat { get; set; } = OutputFormat.PlainText; 10 | } 11 | } -------------------------------------------------------------------------------- /src/Cake.Terraform/TerraformAliases.cs: -------------------------------------------------------------------------------- 1 | using System.Collections.Generic; 2 | using Cake.Core; 3 | using Cake.Core.Annotations; 4 | using Cake.Terraform.Apply; 5 | using Cake.Terraform.Destroy; 6 | using Cake.Terraform.EnvDelete; 7 | using Cake.Terraform.EnvList; 8 | using Cake.Terraform.EnvNew; 9 | using Cake.Terraform.EnvSelect; 10 | using Cake.Terraform.Init; 11 | using Cake.Terraform.Output; 12 | using Cake.Terraform.Plan; 13 | using Cake.Terraform.Refresh; 14 | using Cake.Terraform.Show; 15 | using Cake.Terraform.Validate; 16 | 17 | namespace Cake.Terraform 18 | { 19 | [CakeAliasCategory("Terraform")] 20 | public static class TerraformAliases 21 | { 22 | [CakeMethodAlias] 23 | public static void TerraformInit(this ICakeContext context) 24 | { 25 | TerraformInit(context, new TerraformInitSettings()); 26 | } 27 | 28 | [CakeMethodAlias] 29 | public static void TerraformInit(this ICakeContext context, TerraformInitSettings settings) 30 | { 31 | var runner = new TerraformInitRunner(context.FileSystem, context.Environment, context.ProcessRunner, context.Tools); 32 | runner.Run(settings); 33 | } 34 | 35 | [CakeMethodAlias] 36 | public static bool TerraformPlan(this ICakeContext context) 37 | { 38 | return TerraformPlan(context, new TerraformPlanSettings()); 39 | } 40 | 41 | [CakeMethodAlias] 42 | public static bool TerraformPlan(this ICakeContext context, TerraformPlanSettings settings) 43 | { 44 | var runner = new TerraformPlanRunner(context.FileSystem, context.Environment, context.ProcessRunner, context.Tools); 45 | runner.Run(settings); 46 | return runner.HasChanges; 47 | } 48 | 49 | [CakeMethodAlias] 50 | public static void TerraformApply(this ICakeContext context) 51 | { 52 | TerraformApply(context, new TerraformApplySettings()); 53 | } 54 | 55 | [CakeMethodAlias] 56 | public static void TerraformApply(this ICakeContext context, TerraformApplySettings settings) 57 | { 58 | var runner = new TerraformApplyRunner(context.FileSystem, context.Environment, context.ProcessRunner, context.Tools); 59 | runner.Run(settings); 60 | } 61 | 62 | [CakeMethodAlias] 63 | public static void TerraformShow(this ICakeContext context) 64 | { 65 | TerraformShow(context, new TerraformShowSettings()); 66 | } 67 | 68 | [CakeMethodAlias] 69 | public static void TerraformShow(this ICakeContext context, TerraformShowSettings settings) 70 | { 71 | var runner = new TerraformShowRunner(context.FileSystem, context.Environment, context.ProcessRunner, context.Tools); 72 | runner.Run(settings); 73 | } 74 | 75 | [CakeMethodAlias] 76 | public static void TerraformDestroy(this ICakeContext context) 77 | { 78 | TerraformDestroy(context, new TerraformDestroySettings()); 79 | } 80 | 81 | [CakeMethodAlias] 82 | public static void TerraformDestroy(this ICakeContext context, TerraformDestroySettings settings) 83 | { 84 | var runner = new TerraformDestroyRunner(context.FileSystem, context.Environment, context.ProcessRunner, context.Tools); 85 | runner.Run(settings); 86 | } 87 | 88 | [CakeMethodAlias] 89 | public static void TerraformEnvDelete(this ICakeContext context) 90 | { 91 | TerraformEnvDelete(context, new TerraformEnvDeleteSettings()); 92 | } 93 | 94 | [CakeMethodAlias] 95 | public static void TerraformEnvDelete(this ICakeContext context, TerraformEnvDeleteSettings settings) 96 | { 97 | var runner = new TerraformEnvDeleteRunner(context.FileSystem, context.Environment, context.ProcessRunner, context.Tools); 98 | runner.Run(settings); 99 | } 100 | 101 | [CakeMethodAlias] 102 | public static void TerraformEnvList(this ICakeContext context) 103 | { 104 | TerraformEnvList(context, new TerraformEnvListSettings()); 105 | } 106 | 107 | [CakeMethodAlias] 108 | public static List TerraformEnvList(this ICakeContext context, TerraformEnvListSettings settings) 109 | { 110 | var runner = new TerraformEnvListRunner(context.FileSystem, context.Environment, context.ProcessRunner, context.Tools); 111 | return runner.Run(settings); 112 | } 113 | 114 | [CakeMethodAlias] 115 | public static void TerraformEnvNew(this ICakeContext context, string environment) 116 | { 117 | TerraformEnvNew(context, new TerraformEnvNewSettings { Environment = environment }); 118 | } 119 | 120 | [CakeMethodAlias] 121 | public static void TerraformEnvNew(this ICakeContext context, TerraformEnvNewSettings settings) 122 | { 123 | var runner = new TerraformEnvNewRunner(context.FileSystem, context.Environment, context.ProcessRunner, context.Tools); 124 | runner.Run(settings); 125 | } 126 | 127 | [CakeMethodAlias] 128 | public static void TerraformEnvSelect(this ICakeContext context, string environment) 129 | { 130 | TerraformEnvSelect(context, new TerraformEnvSelectSettings { Environment = environment }); 131 | } 132 | 133 | [CakeMethodAlias] 134 | public static void TerraformEnvSelect(this ICakeContext context, TerraformEnvSelectSettings settings) 135 | { 136 | var runner = new TerraformEnvSelectRunner(context.FileSystem, context.Environment, context.ProcessRunner, context.Tools); 137 | runner.Run(settings); 138 | } 139 | 140 | [CakeMethodAlias] 141 | public static void TerraformRefresh(this ICakeContext context) 142 | { 143 | TerraformRefresh(context, new TerraformRefreshSettings()); 144 | } 145 | 146 | [CakeMethodAlias] 147 | public static void TerraformRefresh(this ICakeContext context, TerraformRefreshSettings settings) 148 | { 149 | var runner = new TerraformRefreshRunner(context.FileSystem, context.Environment, context.ProcessRunner, context.Tools); 150 | runner.Run(settings); 151 | } 152 | 153 | [CakeMethodAlias] 154 | public static void TerraformValidate(this ICakeContext context) 155 | { 156 | TerraformValidate(context, new TerraformValidateSettings()); 157 | } 158 | 159 | [CakeMethodAlias] 160 | public static void TerraformValidate(this ICakeContext context, TerraformValidateSettings settings) 161 | { 162 | var runner = new TerraformValidateRunner(context.FileSystem, context.Environment, context.ProcessRunner, context.Tools); 163 | runner.Run(settings); 164 | } 165 | 166 | [CakeMethodAlias] 167 | public static string TerraformOutput(this ICakeContext context, TerraformOutputSettings settings) 168 | { 169 | var runner = new TerraformOutputRunner(context.FileSystem, context.Environment, context.ProcessRunner, context.Tools); 170 | return runner.Run(settings); 171 | } 172 | } 173 | } 174 | -------------------------------------------------------------------------------- /src/Cake.Terraform/TerraformEnvSettings.cs: -------------------------------------------------------------------------------- 1 | namespace Cake.Terraform 2 | { 3 | public class TerraformEnvSettings : TerraformSettings 4 | { 5 | 6 | public enum EnvCommandType 7 | { 8 | Workspace, 9 | Env 10 | } 11 | 12 | public EnvCommandType EnvCommand { get; set; } = EnvCommandType.Workspace; 13 | } 14 | } -------------------------------------------------------------------------------- /src/Cake.Terraform/TerraformRunner.cs: -------------------------------------------------------------------------------- 1 | using System.Collections.Generic; 2 | using Cake.Core; 3 | using Cake.Core.IO; 4 | using Cake.Core.Tooling; 5 | 6 | namespace Cake.Terraform 7 | { 8 | public abstract class TerraformRunner : Tool where TTerraformSettings : TerraformSettings 9 | { 10 | private readonly ICakePlatform _platform; 11 | 12 | protected TerraformRunner(IFileSystem fileSystem, ICakeEnvironment environment, IProcessRunner processRunner, IToolLocator tools) 13 | : base(fileSystem, environment, processRunner, tools) 14 | { 15 | _platform = environment.Platform; 16 | } 17 | 18 | protected override string GetToolName() 19 | { 20 | return "Terraform"; 21 | } 22 | 23 | protected override IEnumerable GetToolExecutableNames() 24 | { 25 | return new[] { _platform.IsUnix() ? "terraform" : "terraform.exe" }; 26 | } 27 | } 28 | } -------------------------------------------------------------------------------- /src/Cake.Terraform/TerraformSettings.cs: -------------------------------------------------------------------------------- 1 | using Cake.Core.Tooling; 2 | 3 | namespace Cake.Terraform 4 | { 5 | public abstract class TerraformSettings : ToolSettings 6 | { 7 | } 8 | } -------------------------------------------------------------------------------- /src/Cake.Terraform/Validate/TerraformValidateRunner.cs: -------------------------------------------------------------------------------- 1 | using System; 2 | using System.Collections.Generic; 3 | using System.Linq; 4 | using System.Text; 5 | using System.Threading.Tasks; 6 | using Cake.Core; 7 | using Cake.Core.IO; 8 | using Cake.Core.Tooling; 9 | using Cake.Terraform.Init; 10 | 11 | namespace Cake.Terraform.Validate 12 | { 13 | public class TerraformValidateRunner : TerraformRunner 14 | { 15 | public TerraformValidateRunner(IFileSystem fileSystem, ICakeEnvironment environment, IProcessRunner processRunner, IToolLocator tools) 16 | : base(fileSystem, environment, processRunner, tools) 17 | { 18 | } 19 | 20 | public void Run(TerraformValidateSettings settings) 21 | { 22 | var builder = new ProcessArgumentBuilder().Append("validate"); 23 | 24 | 25 | Run(settings, builder); 26 | } 27 | } 28 | 29 | public class TerraformValidateSettings : TerraformSettings 30 | { 31 | } 32 | } 33 | -------------------------------------------------------------------------------- /src/Directory.Build.props: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4.0.0 4 | 5 | 6 | -------------------------------------------------------------------------------- /src/Directory.Build.targets: -------------------------------------------------------------------------------- 1 | 2 | 3 | 5 | 6 | 7 | $(AllowedOutputExtensionsInPackageBuildOutputFolder);.pdb 8 | true 9 | true 10 | $([System.IO.Path]::Combine('$(IntermediateOutputPath)','$(TargetFrameworkMoniker).AssemblyAttributes$(DefaultLanguageSourceExtension)')) 11 | 12 | 13 | 14 | 15 | 16 | 17 | 18 | 19 | 23 | 24 | <_LocalTopLevelSourceRoot Include="@(SourceRoot)" Condition="'%(SourceRoot.NestedRoot)' == ''"/> 25 | 26 | 27 | 28 | --------------------------------------------------------------------------------