# How to Build OCI Images Using `container build` with BuildKit

> Learn to build OCI images on macOS with BuildKit and container build. Orchestrate Dockerfiles for multi-architecture outputs with this powerful builder.

- Repository: [Apple/container](https://github.com/apple/container)
- Tags: how-to-guide
- Published: 2026-06-11

---

**You can build OCI-compliant container images on macOS by using `container build`, which orchestrates a BuildKit-powered builder VM to execute Dockerfiles and produce multi-architecture outputs.**

Apple's `container` CLI provides native OCI container support for Apple Silicon, leveraging the same high-performance BuildKit engine used by Docker. When you invoke `container build`, the CLI communicates with the `container-builder-shim` image to launch a lightweight Linux VM, mount your build context, and execute the Dockerfile instructions. The result is a fully OCI-compliant image stored locally or exported to a tarball.

## Architecture Overview

The `container build` workflow relies on three core components working together to transform Dockerfiles into runnable images.

### The `container build` Command

As documented in [`docs/command-reference.md`](https://github.com/apple/container/blob/main/docs/command-reference.md), the `container build` command parses CLI flags, prepares the local build context, and forwards the request to the builder container. It supports standard Dockerfile instructions alongside Apple-specific extensions for multi-architecture output and custom export formats.

### Builder VM and Shim

The builder runs inside a lightweight Linux VM launched by `container builder start`. This VM executes the `container-builder-shim` image (default `ghcr.io/apple/container-builder-shim/builder:<tag>`), which contains the BuildKit daemon. Resource limits for this VM—including CPU count, memory allocation, and Rosetta usage—are configurable via the `[build]` section of `~/.config/container/config.toml`, as detailed in [`docs/container-system-config.md`](https://github.com/apple/container/blob/main/docs/container-system-config.md).

### BuildKit Integration

BuildKit provides the underlying execution engine, enabling parallel step processing, intelligent cache sharing, and multi-platform output. According to [`docs/command-reference.md`](https://github.com/apple/container/blob/main/docs/command-reference.md), you can target specific architectures using the `--arch`, `--os`, and `--platform` flags to produce images for multiple architectures (e.g., `arm64` and `amd64`) in a single build invocation.

## Starting the Builder

Before building images, you must start the builder VM with sufficient resources for your workload.

```bash

# Start with default resources (2 CPU / 2 GiB)

container builder start

# Or allocate specific resources for large builds

container builder start --cpus 8 --memory 32g

```

The builder persists across builds, maintaining the BuildKit cache for faster incremental builds. To apply configuration changes or free system resources, stop the builder:

```bash
container builder stop

```

## Configuring Builder Resources

Persistent builder settings reside in `~/.config/container/config.toml`. The `[build]` section controls the VM resources and the builder image version.

```toml
[build]
cpus = 8
memory = "16g"
rosetta = false          # Disable Rosetta for native-arm builds

image = "ghcr.io/apple/container-builder-shim/builder:0.12.0"

```

After modifying this file, restart the builder to apply changes:

```bash
container builder stop
container builder start

```

These configuration options are documented in [`docs/container-system-config.md`](https://github.com/apple/container/blob/main/docs/container-system-config.md) and [`docs/how-to.md`](https://github.com/apple/container/blob/main/docs/how-to.md).

## Building OCI Images

### Basic Build Workflow

Create a `Dockerfile` (or `Containerfile`) in your project directory, then run:

```bash
container build --tag myorg/app:latest .

```

The CLI automatically pulls the builder shim if absent, launches the VM, and streams build progress to your terminal. The resulting image is stored in the local OCI-compliant image store.

### Multi-Architecture Builds

Produce images for multiple architectures simultaneously using the `--arch` flag:

```bash
container build \
  --tag myorg/web-app:latest \
  --arch arm64 \
  --arch amd64 \
  --file Dockerfile \
  .

```

This leverages BuildKit's cross-compilation capabilities to generate a multi-platform manifest, as supported by the flags documented in [`docs/command-reference.md`](https://github.com/apple/container/blob/main/docs/command-reference.md).

### Exporting to Tarball

By default, `container build` writes type `oci` images to the local store. To export the image as a tarball for sharing or archiving, use the `--output` flag:

```bash
container build \
  --tag myorg/web-app:latest \
  --output type=tar,dest=./web-app.tar \
  .

```

## Advanced Build Options

### Multi-Stage and Secret-Aware Builds

BuildKit supports advanced Dockerfile features including multi-stage builds, build secrets, and cache control:

```bash
container build \
  --target production \
  --no-cache \
  --secret id=MY_API_KEY,env=API_KEY \
  --tag myorg/web-app:prod \
  .

```

This command builds only the `production` stage, bypasses the cache, and injects the `API_KEY` environment variable as a build secret without persisting it in the final image layers.

## Verifying and Running Images

After building, verify the image exists in the local store:

```bash
container image list --quiet

```

Test the image immediately using `container run`:

```bash
container run -it myorg/web-app:latest

```

## Summary

- **`container build`** orchestrates BuildKit inside a lightweight VM to execute Dockerfiles and produce OCI-compliant images.
- The **builder VM** runs the `container-builder-shim` image and is configured via `~/.config/container/config.toml` in the `[build]` section.
- **Multi-architecture builds** use the `--arch` and `--platform` flags to target multiple CPU architectures in a single invocation.
- **Output formats** include the default OCI local store or tarball exports via `--output type=tar,dest=...`.
- Control **resource allocation** with `container builder start --cpus` and `--memory`, or set defaults in the configuration file.

## Frequently Asked Questions

### What is the builder shim image?

The builder shim is the container image `ghcr.io/apple/container-builder-shim/builder:<tag>` that runs inside the builder VM. It contains the BuildKit daemon and supporting tools necessary to execute builds. The specific version is controlled by the `image` key in the `[build]` section of your configuration file.

### How do I change CPU and memory limits for builds?

You can specify resources temporarily when starting the builder with `container builder start --cpus 8 --memory 32g`, or permanently by setting `cpus` and `memory` values in the `[build]` section of `~/.config/container/config.toml`. Changes to the configuration file require a builder restart to take effect.

### Can I build images for Intel Macs from my Apple Silicon Mac?

Yes. Use the `--arch amd64` flag (or `--arch arm64 --arch amd64` for both) to cross-compile images for x86_64 architectures. BuildKit handles the cross-compilation automatically, and the resulting multi-platform image can run on both Apple Silicon and Intel systems.

### How do I export a built image to a Docker-compatible tarball?

Use the `--output` flag with type `tar`: `container build --output type=tar,dest=./image.tar .`. This creates a tarball containing the OCI image layers and manifest, which can be imported into Docker or other container runtimes using standard `docker load` or similar commands.