Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

feat: OpenTofu support #4499

Draft
wants to merge 12 commits into
base: main
Choose a base branch
from
Draft

feat: OpenTofu support #4499

wants to merge 12 commits into from

Conversation

meringu
Copy link
Contributor

@meringu meringu commented May 2, 2024

what

This is an early attempt at getting OpenTofu to work with Atlantis. I thought I'd get open this PR sooner rather than later, as conflicts with #4494 and would be interested to see what people think or get any feedback.

I'm just starting to test this internally and have made some quick decisions in order to get it working:

  • Introduces a --tf-distribution setting that can be set to terraform or opentofu.
  • OpenTofu is downloaded through GitHub releases from https://github.com/opentofu/opentofu
    • This method is not compatible with releases.hashicorp.com, so currently ignores --tf-download-url
  • OpenTofu ships the archives with additional files, just like Terraform 1.8.2. Therefore this change should also resolve the need for Consider using hc-install instead of go-getter to install terraform binary #4483.
  • Added an interface to server/core/terraform/terraform_client.go for the Terraform distribution. This matches up with the --tf-distribution setting. I'm not sure if this is the right place or the right abstraction, but seemed to be a relatively low effort place to implement it.
  • I would like to also support configuring Terraform or OpenTofu per project in the server side config or repo level config. This would support an easier path to migrate between the two.
  • There is a small change to set a default TARGETPLATFORM in the Dockerfile. This is to support kaniko, which I'm using internally to build and test this. Happy to revert that.
  • I'm not checking the signature of the opentofu archive yet.

I've done limited testing so far, but would like to get some feedback before I continue down the wrong rabbit hole.

why

#3741

tests

I've got them working for the new download method, but should also add some for the new OpenTofu code paths.

references

#3741

@meringu meringu requested review from a team as code owners May 2, 2024 10:51
@meringu meringu requested review from jamengual, nitrocode and X-Guardian and removed request for a team May 2, 2024 10:51
@github-actions github-actions bot added build Relating to how we build Atlantis docs Documentation go Pull requests that update Go code labels May 2, 2024
@meringu meringu changed the title [WIP] OpenTofu support feat: [WIP] OpenTofu support May 2, 2024
@james0209
Copy link

james0209 commented May 2, 2024

I agree with the premise of this, and I like the solution, but I don't agree that it stops the need for hc-install - I think that is worthy of a discussion.

I do not think your changes inherently conflict with the hc-install PR - it is very easy to do this for example

func (c *DefaultClient) DetectVersion(log logging.SimpleLogging, projectDirectory string) *version.Version {
	return c.distribution.DetectVersion(log, c, projectDirectory)
}

type Distribution interface {
	BinName() string
	SourceURL(v *version.Version, downloadURL string) string
	DetectVersion(log logging.SimpleLogging, c *DefaultClient, projectDirectory string) *version.Version
}

func (*DistributionTerraform) DetectVersion(log logging.SimpleLogging, c DefaultClient, projectDirectory string) *version.Version {
// use hc-install
}

func (*DistributionOpenTofu) ListAvailableVersions(log logging.SimpleLogging, downloadBaseURL string, downloadAllowed bool) ([]string, error) {
// use current implementation - only called by the DetectVersion below
}

func (dt *DistributionOpenTofu) DetectVersion(log logging.SimpleLogging, c DefaultClient, projectDirectory string) *version.Version {
// use current implementation
e.g. tfVersions, err := dt.ListAvailableVersions(log, c.downloadBaseURL, c.downloadAllowed)
}

Especially as the ListAvailableVersions func is only called in the current implementation of DetectVersion - there is no other usage.

I think if you are going to have separate interfaces for OpenTofu vs Terraform implementations, then a discussion on whether to use the same logic vs different logic for each Distribution should be had.

  • An example being how this PR already introduces 2 different logic flows for ListAvailableVersions (due to tagging, pre-relese etc.) - with hc-install, that would only be needed by OpenTofu, as it is handled by hc-install for Terraform

@jamengual jamengual added needs discussion Large change that needs review from community/maintainers waiting-on-review Waiting for a review from a maintainer labels May 2, 2024
@meringu
Copy link
Contributor Author

meringu commented May 2, 2024

Thanks @james0209, that makes sense.

I'd be happy to rebase this over the hc-install change. As you point out, that should be fairly straightforward.

@nitrocode nitrocode marked this pull request as draft May 3, 2024 12:23
@nitrocode nitrocode changed the title feat: [WIP] OpenTofu support feat: OpenTofu support May 3, 2024
@nitrocode
Copy link
Member

Due to wip status, I switched this to a draft as a non draft means that it's ready for review. Please set it as ready to review when ready.

Thank you for the contribution

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
build Relating to how we build Atlantis docs Documentation go Pull requests that update Go code needs discussion Large change that needs review from community/maintainers waiting-on-review Waiting for a review from a maintainer
Projects
None yet
Development

Successfully merging this pull request may close these issues.

None yet

4 participants