Skip to content

Quick Start

Gale integrates with Elixir 1.20 and OTP 28 through mix_gale. Add the Gale compiler before Mix’s standard compilers and include the runtime support and standard library dependencies.

For a new project:

Terminal window
mix new hello
cd hello

Merge these settings into project/0 and deps/0 in mix.exs. Keep the existing app, version, and other project settings:

def project do
[
compilers: [:gale | Mix.compilers()],
test_load_filters: [~r/_test(\.g)?\.exs$/],
gale: [runtime_typechecks: Mix.env() == :test],
deps: deps()
]
end
defp deps do
[
{:mix_gale, git: "git@github.com:cloudloom-ai/gale.git", branch: "main", subdir: "libs/mix_gale", override: true},
{:gale_std, git: "git@github.com:cloudloom-ai/gale.git", branch: "main", subdir: "libs/gale_std"}
]
end

Fetch the dependencies with GitHub access and commit the resulting mix.lock. It records the commit used by each Git dependency:

Terminal window
mix deps.get

Add Gale files to .formatter.exs so mix format formats them and mix format --check-formatted checks them:

[
plugins: [MixGale.Formatter],
inputs: ["{mix,.formatter}.exs", "{lib,test}/**/*.{ex,exs,gale,🌀}"]
]

On the first compile, mix_gale downloads the compiler matching the version in its mix.exs and verifies the SHA-256 checksum. To take newer Gale source, run mix deps.update mix_gale gale_std and commit the updated lockfile. Use the same full commit SHA with ref: "<sha>" on both dependencies if you want an explicit source pin.

Create lib/hello.gale (.🌀 is also supported). In the hello project, replace the generated lib/hello.ex so both files do not define Hello. Gale library module names must match the Mix app name or start with it and a dot. For an existing app named my_app, use lib/my_app/hello.gale with module my_app.hello instead.

mod hello
pub fn greet(name: String) -> String {
"Hello, #{name}!"
}

Compile and call the function from Elixir:

Terminal window
mix compile
iex -S mix
iex> Hello.greet("world")
"Hello, world!"

An existing my_app project would call MyApp.Hello.greet("world"). mix compile checks the Gale types and generates Elixir beside the source as lib/hello.g.ex. Edit the Gale source and let Mix regenerate that file.

Add the generated files to .gitignore:

*.g.ex
*.g.exs

The settings above also enable runtime type checks in tests and let mix test discover generated Gale test files.

For local compiler development, use gale: [compiler_path: ...] to override the compiler executable. The override takes precedence over the package-matched compiler and skips the download entirely:

gale: [compiler_path: "/absolute/path/to/gale"]

If the path comes from an environment variable, make that explicit in the project with gale: [compiler_path: System.get_env("GALE_COMPILER_PATH")]. See toolchain releases for supported platforms and release artifact details, then continue with Numbers. The tour later covers proving contracts.