Skip to main content

Quickstart

Build a binary with a function

Not only can functions use Dagger's core types in their arguments; they can use them in their return value as well.

This opens powerful applications to Dagger Functions. For example, a function that builds binaries could take a directory as argument (the source code) and return another directory (containing binaries).

Call a builder function

Try calling this Go builder Dagger Function, which builds the Dagger CLI:

dagger -m github.com/kpenfound/dagger-modules/golang@v0.1.10 call build --source=https://github.com/dagger/dagger --args=./cmd/dagger --os=$(uname -s | awk '{print tolower($0)}')

This function takes a project argument of type Directory. Here, you're passing the address of Dagger's open-source repository. It also takes an args argument, which is a list of strings representing the arguments to be passed to the go build command.

note

By default, the Go builder Dagger Function builds a binary based on information derived from the runtime container. Since the runtime container uses Linux, this usually means that the compiled binary will be a linux/amd64 binary. This can be overridden by passing additional --os and --arch arguments to the Go builder Dagger Function. The previous example uses uname to dynamically derive the host operating system type, and passes that to the Dagger Function via the --os argument.

Once the command completes, you should see this output:

Directory evaluated. Use "dagger call build --help" to see available sub-commands.

This means that the build succeeded, and a directory was returned. But how do you use it?

tip

It's important to realize that even though you're building a Go application in this example, you don't need to have Go, Git or any other local dependencies installed on the Dagger host. You only need the Dagger CLI and the ability to run containers. This is a very powerful feature of Dagger, because it allows development teams to create standardized tooling and eliminates all the variables and dependencies related to the host environment and/or configuration.

Understand function chaining

Dagger Functions can return either basic types or objects. Objects can define their own functions (in the classic object-oriented model). When calling a function that returns an object, the Dagger API lets you follow up by calling one of that object's functions, which itself can return another object, and so on. This is called function chaining, and is a core feature of Dagger.

Dagger's core types (Container, Directory, Service, Secret, ...) are all objects. They each define various functions for interacting with their respective objects.

When a function returns a core type - for example, a directory - the caller typically continues the chain by calling a function from that directory - for example, export it to the local filesystem, modify it, mount it into a container, etc.

Export the built binary

Using this knowledge of function chaining, call the builder function again and continue the chain by interacting with the resulting directory.

Begin by listing the directory's contents:

dagger -m github.com/kpenfound/dagger-modules/golang@v0.1.10 call build --source=https://github.com/dagger/dagger --args=./cmd/dagger --os=$(uname -s | awk '{print tolower($0)}') entries

The result should look like this:

dagger

This does look like a compiled binary. Great!

Next, export the directory to the host filesystem. You can do this by using the global -o (shorthand for --output) flag to export the directory to a custom path (./my-dagger-build) on the host:

dagger -m github.com/kpenfound/dagger-modules/golang@v0.1.10 call build --source=https://github.com/dagger/dagger --args=./cmd/dagger --os=$(uname -s | awk '{print tolower($0)}') -o=./my-dagger-build

Validate the exported binary by calling it:

./my-dagger-build/dagger version

You should see output similar to the following, which confirms that you've just remotely built a development version of the Dagger CLI:

dagger (registry.dagger.io/engine) linux/amd64
tip

As you've seen in the previous examples, Dagger modules can contain one or more Dagger Functions, each with different arguments and return values. You can list all the functions available in a module with the dagger functions command, or append --help to any dagger call command to see a context-sensitive list of supported arguments and sub-commands. Try it with the Go builder module:

dagger -m github.com/kpenfound/dagger-modules/golang@v0.1.10 functions
dagger -m github.com/kpenfound/dagger-modules/golang@v0.1.10 call --help