Skip to main content

Documentation Index

Fetch the complete documentation index at: https://mintlify.com/chainguard-dev/melange/llms.txt

Use this file to discover all available pages before exploring further.

melange build is the core command that reads a declarative YAML pipeline file and produces one or more .apk package files. It provisions a sandboxed build environment, fetches sources, executes every pipeline step, runs the configured linters, and writes the finished packages to the output directory (default ./packages/). Builds can target multiple CPU architectures in a single invocation, running each architecture’s build concurrently.

Usage

melange build [config.yaml] [flags]
The positional argument is optional. When omitted, melange looks for a config file in the current directory based on the pipeline configuration.

Basic examples

# Build for the host architecture using bubblewrap (Linux default)
melange build crane.yaml

# Build for multiple architectures at once
melange build crane.yaml --arch x86_64,aarch64

# Build and sign in one step
melange build crane.yaml --signing-key local-melange.rsa

# Build inside Docker (useful on macOS)
melange build crane.yaml --runner docker

# Build with extra Alpine/Wolfi repositories and keys
melange build crane.yaml \
  --repository-append https://packages.wolfi.dev/os \
  --keyring-append https://packages.wolfi.dev/os/wolfi-signing.rsa.pub

Output structure

By default, packages are written to ./packages/ with one subdirectory per architecture:
packages/
├── x86_64/
│   ├── crane-0.19.1-r0.apk
│   └── APKINDEX.tar.gz
└── aarch64/
    ├── crane-0.19.1-r0.apk
    └── APKINDEX.tar.gz
The APKINDEX.tar.gz repository index is generated automatically unless --generate-index=false is passed.

Flags

Output

FlagDefaultDescription
--out-dir./packages/Directory where built APKs and the index are written
--generate-indextrueAutomatically create APKINDEX.tar.gz after the build
--create-build-logfalseWrite a package.log listing every package built
--dependency-log(empty)Log resolved dependencies to the specified file
--persist-lint-resultsfalseWrite lint results as JSON files under packages/{arch}/

Build environment

FlagDefaultDescription
--source-dir(config file dir)Directory containing patches and other included sources
--workspace-dir(temp dir)Path mounted as /home/build inside the build sandbox
--pipeline-dir(empty)Extra directory to search for named pipeline definitions
--pipeline-dirs(empty)Additional directories for pipeline definitions (plural form)
--env-file(empty)Files containing environment variables to pre-load
--vars-file(empty)File containing build configuration variables
--build-option(empty)Named build options to enable (defined in the config’s options: block)
--empty-workspacefalseStart with an empty workspace instead of pre-populating it
--build-date(empty)Override file timestamps inside the package (for reproducibility)
--timeout(none)Maximum wall-clock duration for the build (e.g. 30m, 2h)
--package-append(empty)Extra APK packages to install in every build environment
--keyring-append / -k(empty)Extra public key files to trust in the build environment
--repository-append / -r(empty)Extra APK repository URLs or paths to add
--ignore-signaturesfalseSkip repository signature verification
--override-host-triplet-libc-substitution-flavorgnulibc flavor for ${{host.triplet.*}} substitutions (gnu or musl)

Architecture

FlagDefaultDescription
--arch(all from config)Comma-separated list of target architectures: x86_64, aarch64, ppc64le, arm, s390x, etc.
If neither --arch nor target-architecture in the config specifies anything, melange builds for all architectures supported by the config’s environment.

Runner

FlagDefaultDescription
--runner(platform default)Sandbox runner: bubblewrap (Linux), docker (macOS/Windows), or qemu
--cpu(none)CPU resource limit passed to the runner
--cpumodel(none)CPU model string (used by QEMU runner)
--memory(none)Memory resource limit
--disk(none)Disk size for the build environment
--rmtrueClean up containers/temp dirs after the build
--cleanuptrueRemove the guest temp directory after completion
--debug-runnerfalseKeep the runner (container/VM) alive after build completes or fails
--interactive / -ifalseAttach a TTY to the build sandbox on failure for interactive debugging
On Linux, melange defaults to the bubblewrap runner, which requires no extra setup. On macOS and Windows the docker runner is used automatically — Docker Desktop must be running.

Signing

FlagDefaultDescription
--signing-key(empty)RSA private key file used to sign the built APKs

Caching

FlagDefaultDescription
--cache-dir./melange-cache/Local directory for source artifact caching
--cache-source(empty)Pre-populate the cache from this directory or GCS/S3 bucket
--apk-cache-dir(system cache)Directory for caching downloaded APK packages

Provenance and SBOM

FlagDefaultDescription
--generate-provenancefalseEmit a SLSA provenance attestation as a .attest.tar.gz beside each APK
--namespaceunknownNamespace for package URLs in the generated SBOM (e.g. wolfi, alpine)
--git-commit(auto-detected)Git commit hash of the config file’s repository
--git-repo-url(auto-detected)URL of the repository containing the config file
--licenseNOASSERTIONSPDX license identifier for the build config file itself

Linting

FlagDefaultDescription
--lint-requiredev,infodir,libtool/la-files,setuidgid,tempdir,usrmerge,varempty,worldwriteLinters that cause build failure when triggered
--lint-warnbinaryarch,cudaruntimelib,dll,duplicate,dylib,lddcheck,maninfo,nonlinux,object,opt,pkgconf,python/docs,python/multiple,python/test,sbom,srv,staticarchive,strip,unsupportedarch,usrlocalLinters that emit warnings but do not fail the build

Debugging

FlagDefaultDescription
--debugfalseEnable verbose pipeline step logging (sets -x in shell steps)
--trace(empty)Write OpenTelemetry trace output to the specified file
--strip-origin-namefalseStrip origin package names from subpackages (used for bootstrapping)

Docker runner example

When building on macOS or in environments without bubblewrap, use the Docker runner:
docker run --rm --privileged \
  -v "$(pwd)":/work \
  -w /work \
  cgr.dev/chainguard/melange \
  build package.yaml \
    --arch x86_64 \
    --runner docker \
    --signing-key local-melange.rsa

SLSA provenance

Passing --generate-provenance produces a signed attestation file next to each APK:
melange build package.yaml \
  --generate-provenance \
  --namespace wolfi \
  --signing-key signing.rsa
This creates packages/x86_64/mypackage-1.0.0-r0.apk.attest.tar.gz alongside the APK.
The --fail-on-lint-warning flag is deprecated. Use --lint-require and --lint-warn to control which checks are enforced vs. advisory.

Build docs developers (and LLMs) love