Guide

Everything you can put in a caml.yaml.

Tasks

Each top-level key is a task. A task has a desc and an execute shell command. Run caml or caml help to list every task with its description.

test:
  desc: Run the test suite
  execute: bundle exec rspec

Multi-line execute

Pass a list to run multiple steps. Steps run with fail-fast semantics — the first non-zero exit aborts.

setup:
  desc: Install and migrate
  execute:
    - bundle install
    - bin/rails db:migrate

Arguments

Positional arguments substitute into the execute template via {{name}}. Values are shell-escaped.

greet:
  desc: Say hello to someone
  args:
    name:
      desc: Person to greet
      type: string
  execute: echo Hello, {{name}}!
caml greet world
# Hello, world!

Options

Flags with type, optional aliases, a default value, and an optional override execute.

build:
  desc: Build the project
  opts:
    target:
      type: string
      default: dist
      aliases:
        - t
      desc: Output directory
    verbose:
      type: boolean
      aliases:
        - v
      desc: Print verbose output
  execute: make build TARGET={{target}}
caml build --target release
caml build -t release -v

Option-driven dispatch

When a boolean option carries its own execute, that command runs instead of the task's default.

start:
  desc: Start the app
  opts:
    background:
      type: boolean
      aliases:
        - b
      desc: Run as a daemon
      execute: app start --daemon
  execute: app start
caml start                # app start
caml start --background   # app start --daemon

Aliases

Add shortcut names for a task.

test:
  desc: Run the test suite
  aliases:
    - t
  execute: bundle exec rspec
caml t   # same as caml test

Dependencies

A task can declare prerequisites with needs. Deps run in declared order, each at most once per invocation; failures abort the run.

test:
  desc: Run tests
  execute: bundle exec rspec

lint:
  desc: Check style
  execute: bundle exec rubocop

ci:
  desc: Lint and test
  needs:
    - lint
    - test
caml ci   # runs lint, then test

A task with only needs: and no execute is a pure orchestrator — useful for grouping.

Discovery

caml walks up from the current directory to find a caml.yaml, just like git. You can run it from any subdirectory of your project.

Built-in commands

Command Description
caml init Scaffold a starter caml.yaml
caml --version Print the installed version
caml help [cmd] Show help for a specific task (its args and opts)