# How to Build Multi-Platform Images with Apple Container: A Complete Guide

> Learn how to build multi-platform images with Apple Container. Use the container build command with --arch or --platform flags to create OCI manifest lists for specific architectures.

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

---

**Use the `container build` command with repeated `--arch` flags or the unified `--platform` flag to generate OCI manifest lists containing multiple platform variants, then push and run specific architectures using the Apple Container CLI.**

Apple Container is an open-source Swift-based container runtime that enables developers to build and manage OCI-compliant images on macOS. When you need to distribute applications for both Apple Silicon (arm64) and Intel (x86-64) architectures, the `container` CLI provides native multi-platform build capabilities through BuildKit integration. This workflow produces a single image reference that contains distinct variants for each target platform.

## Understanding Multi-Platform Image Architecture

Multi-platform images (also called manifest lists) bundle multiple architecture-specific variants under a single image reference. When you build multi-platform images with Apple Container, the tool constructs an OCI manifest list containing separate layer sets for each target platform. The BuildKit integration defined in [`Package.swift`](https://github.com/apple/container/blob/main/Package.swift) orchestrates the cross-platform compilation, ensuring that each architecture receives its own optimized binary layers while sharing a unified manifest structure.

## Building Multi-Platform Images

### Using the `--arch` Flag for Multiple Architectures

The simplest method to target multiple platforms uses the `--arch` flag repeatedly. According to [`docs/command-reference.md`](https://github.com/apple/container/blob/main/docs/command-reference.md), each `--arch` entry adds a new variant to the resulting image manifest. The CLI passes these values to BuildKit, which creates distinct image layers for each architecture.

Create a simple `Dockerfile` in your project directory:

```dockerfile

# example-app/Dockerfile

FROM ubuntu:22.04
RUN apt-get update && apt-get install -y python3
CMD ["python3", "--version"]

```

Build for both arm64 (Apple Silicon) and amd64 (x86-64):

```bash
container build \
  --arch arm64 \
  --arch amd64 \
  --tag ghcr.io/example/multi-platform:latest \
  --file example-app/Dockerfile .

```

### Using the `--platform` Flag for OS/Architecture Combinations

For explicit control over both operating system and architecture, use the unified `--platform` flag (e.g., `linux/arm64`). As documented in [`docs/command-reference.md`](https://github.com/apple/container/blob/main/docs/command-reference.md), the `--platform` flag takes precedence over both `--arch` and `--os` when conflicts arise.

```bash
container build \
  --platform linux/arm64 \
  --platform linux/amd64 \
  --tag ghcr.io/example/multi-platform:latest \
  --file example-app/Dockerfile .

```

## Verifying Platform Variants

After building, verify that the image contains all requested platform variants using the `container image inspect` command. This outputs the manifest list details showing each architecture configuration.

```bash
container image inspect ghcr.io/example/multi-platform:latest | jq '.variants[].platform'

```

Expected output shows distinct platform objects:

```json
{
  "os": "linux",
  "architecture": "arm64"
}
{
  "os": "linux",
  "architecture": "amd64"
}

```

## Pushing Multi-Platform Images

A single `container image push` command uploads the entire manifest list along with all platform-specific blobs. The image name is shared by all variants, ensuring that consumers automatically receive the correct architecture for their runtime environment.

```bash
container image push ghcr.io/example/multi-platform:latest

```

The push operation uploads the manifest list and both platform-specific layer sets in a single atomic operation.

## Running Specific Platform Variants

When executing containers on Apple Silicon hardware, you can select specific variants using either `--arch` or `--platform` with the `container run` command. The arm64 variant runs natively on Apple Silicon, while the amd64 variant executes under Rosetta translation for x86-64 compatibility.

```bash

# Run the arm64 variant (native on Apple Silicon)

container run --arch arm64 ghcr.io/example/multi-platform:latest uname -a

# Run the amd64 variant (executed under Rosetta on Apple Silicon)

container run --arch amd64 ghcr.io/example/multi-platform:latest uname -a

```

Alternatively, use the platform-specific syntax:

```bash
container run --platform linux/arm64 ghcr.io/example/multi-platform:latest uname -a

```

## Configuration Architecture

### BuildConfig and Platform Storage

The architecture selections specified via CLI flags are persisted in the `BuildConfig` class. According to the source code in [`Sources/ContainerPersistence/ContainerSystemConfig.swift`](https://github.com/apple/container/blob/main/Sources/ContainerPersistence/ContainerSystemConfig.swift), this Swift model records the list of target platforms for a build, enabling BuildKit to reference the configuration during the compilation phase.

### CLI Flag Precedence Rules

The command reference documentation establishes a strict hierarchy for platform selection flags:

- **`--platform`** takes highest precedence and overrides both `--arch` and `--os`
- **`--arch`** and **`--os`** can be used independently but are superseded by `--platform`
- Multiple values for `--arch` are accumulated to form the complete target platform list

## Summary

- **Apple Container** generates OCI manifest lists containing multiple platform variants through BuildKit integration.
- Use repeated `--arch` flags (e.g., `--arch arm64 --arch amd64`) or the unified `--platform` flag to specify target architectures.
- The `BuildConfig` class in [`Sources/ContainerPersistence/ContainerSystemConfig.swift`](https://github.com/apple/container/blob/main/Sources/ContainerPersistence/ContainerSystemConfig.swift) stores architecture selections during the build process.
- A single `container image push` uploads the manifest list and all platform-specific layers simultaneously.
- Execute specific variants using `container run --arch <architecture>` or `--platform <os/arch>`, with native execution on Apple Silicon and Rosetta translation for x86-64.

## Frequently Asked Questions

### What is the difference between `--arch` and `--platform`?

The `--arch` flag specifies only the CPU architecture (e.g., `arm64`, `amd64`), while the `--platform` flag accepts the full OS/architecture combination (e.g., `linux/arm64`). According to [`docs/command-reference.md`](https://github.com/apple/container/blob/main/docs/command-reference.md), `--platform` takes precedence when both are specified, and `--arch` can be repeated multiple times to target several architectures in one build.

### How does Apple Container execute x86-64 images on Apple Silicon?

When you run an amd64 variant on Apple Silicon using `container run --arch amd64`, the container executes under Rosetta translation. The arm64 variant runs natively without translation overhead, while the x86-64 variant automatically uses Apple's Rosetta 2 technology for compatibility.

### Where is the target platform configuration stored during builds?

The target platform configuration is stored in the `BuildConfig` class, defined in [`Sources/ContainerPersistence/ContainerSystemConfig.swift`](https://github.com/apple/container/blob/main/Sources/ContainerPersistence/ContainerSystemConfig.swift). This Swift model persists the list of architecture selections specified via CLI flags, allowing BuildKit to reference the complete target configuration throughout the build process.

### Can I build for more than two architectures simultaneously?

Yes. You can specify as many architectures as your BuildKit backend supports by repeating the `--arch` flag for each target. Each occurrence adds a new variant to the manifest list, enabling you to build for arm64, amd64, riscv64, or other supported architectures in a single invocation.