#Terraform
1 messages · Page 1 of 1 (latest)
Yes, but rather than print to screen you need to think more about having the function return a string. When you call a function in the CLI that returns a string, it'll be printed to the screen.
As for error types, just need to raise any exception.
Based on your code, a few tips for migration:
- Instead of a single
run_terraform, you can have several functions in aTerraformclass:runfor general commands →cmd: list[str]as argument, replaces the force argument- a function for each key in
command_mapping→ just callsself.run()with the value of that mapping, replacing it completely - not necessary to validate if command is invalid since the function won't be available
- ColorPrinted can be removed since we'll rely on
dagger callTUI - For the
repo, the functions can accept adagger.Directoryargument. In the CLI you can pass a local directory or a remote repo very easily, without having to change any code - ArgumentParser is replaced with normal function arguments
- No need to manage connection, just
from dagger import dag(dag == client) - There's two ways to run with the multiple versions:
- Concurrency like you're doing
- Have a function return a list of two instances of
Terraform, each with the different version. In the CLI you can choose which function from these objects to run and it'll run in parallel, without you having to do concurrency yourself (example,dagger call all apply stdout)
Rather than returning the value of stdout it's more flexible to return the dagger.Container. In the CLI you can specify stdout or something else, and any error will be presented to the screen, so you don't need to capture if you're not adding information. For example, the error Error executing {command} on Terraform v{version} {e} isn't useful since that information is already readily available via the module, the function and the arguments that you're calling. Additionally, returning a container allows you to drop into a shell in that container easily, to make it easier to debug.
I invite you to follow our CLI quickstart to give a better idea of the new flow and possibilities when using dagger functions. And then go to the Python developer manual to learn more about how to create your own functions in Python.
@subtle ginkgo, if you'd give a name to a function that runs what's on __main__, what would that be? Example: dagger call <name>. Easy to have the following:
dagger call --src=./terraform run --cmd=some,command stdout(replaces force argument)dagger call --src=./terraform apply stdout(replaces apply command mapping)dagger call --src=./terraform --version=1.4 apply(same as before but overrides the default version 1.5)
Putting the version in the constructor is easier because then you don't have to put it in every function, but then it doesn't make sense if you need multiple versions. Maybe you don't need that and can just have the default and override when needed? Otherwise, you can also create a different object to put the functions (class Instance:), and have the main class Terraform accept just the --src, and include two functions:
dagger call --src=./terraform default apply stdout(for the default version, allowing an override);dagger call --src=./terraform all apply stdout(to return a list of twoInstanceobjects, with 1.4 and 1.5 versions (or more), which makes this command run in parallel.
Yeah I don’t need to run multiple version, I think async was overkill but that’s what all the other examples had to is kinda leveraged it ahha. That makes sense with the output stuff tho, I’ll have to see how it works out
Yeah I tried looking at that, but it was just a little overwhelming to convert what I have to that stuff.
I like the version override tho, that makes the most sense to me
Fear not, I'm doing it now, just give me 10 mins 🙂 Can't run it but you can take off with it 🙂
Don't know what you intend to do with command fmt and exit_code == 3. Comment says it should be nonterminating but that branch ends there.
This is basically it:
from datetime import datetime
from typing import Final
import dagger
from dagger import dag, function, object_type
VERSIONS: Final = ["1.5", "1.4"]
DEFAULT_VERSION: Final = VERSIONS[0]
@object_type
class Terraform:
src: dagger.Directory
version: str = DEFAULT_VERSION
platform: str = "linux/amd64" # do you need this?
@function
def run(self, cmd: list[str]) -> dagger.Container:
"""Run any command in the Terraform container."""
return (
dag.container(platform=dagger.Platform(self.platform))
.from_(f"hashicorp/terraform:{self.version}")
.with_directory("/terraform", self.src)
.with_workdir("/terraform")
# TODO: this enforces a new image build each time - look into leveraging cache
.with_env_variable("CACHEBUSTER", str(datetime.now()))
.with_exec(["init", "-input=false", "-upgrade"])
.with_exec(cmd)
)
@function
def init(self) -> dagger.Container:
return self.run(["init", "-input=false", "-upgrade"])
@function
def plan(self) -> dagger.Container:
return self.run(["plan", "-input=false"])
@function
def apply(self) -> dagger.Container:
return self.run(["apply", "-input=false", "-auto-approve"])
@function
def destroy(self) -> dagger.Container:
return self.run(["destroy", "-input=false", "-auto-approve"])
@function
def validate(self) -> dagger.Container:
return self.run(["validate", "-json"])
@function
def fmt(self) -> dagger.Container:
return self.run(["fmt", "-recursive", "-check"])
Um so basically if the person is running fmt and it returns files that are “at fault” not formatted, it should be more of a warning than an error basically. But that’s not critical
Needs more docstrings:
$ dagger functions
Name Description
apply -
destroy -
fmt -
init -
plan -
run Run any command in the Terraform container.
validate -
Ok so the thing with the terraform image is that I wasn’t able to figure out how to add in extra applications like terragrunt or vault. I did a revamp and used alpine, but if I can’t take lean docker images of the pure software and combine them that would be sweet
There's ways to do that 🙂
Would you be open to a zoom call? Haha this is a HUGE help, but I just have a few questions on how to carry on and like make sure I understand it all
Maybe a wolfi image 🙂
Yeah, what's your time zone?
I’m CST
Now it's a bit late for me, are you available tomorrow until your 12pm?
I can do 8-10am my time tomorrow!
Ok, send a link to helder@dagger.io 🙂