Skip to content

Commit

Permalink
experimental: Add build-chunked-oci
Browse files Browse the repository at this point in the history
Closes: coreos#5221

Signed-off-by: Colin Walters <[email protected]>
  • Loading branch information
cgwalters committed Jan 20, 2025
1 parent c424510 commit 6a699f4
Show file tree
Hide file tree
Showing 5 changed files with 446 additions and 4 deletions.
82 changes: 82 additions & 0 deletions docs/experimental-build-chunked-oci.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,82 @@
---
nav_order: 5
---

# experimental compose build-chunked-oci

Currently this project supports `rpm-ostree compose image` which is a highly
opinionated tool which consumes treefiles and outputs an OCI archive.

However, it does not support common container-native workflows such
as copying content from a distinct container image.

The `rpm-ostree experimental compose build-chunked-oci` command
accepts an arbitrary root filesystem, and synthesizes an OSTree-based
container from it.

At the current time, it is recommended that the input
root filesystem be derived from a reference maintained base image,
such as the fedora-bootc ones. Especially if you are
targeting bootc systems with this, please trakc

## Example as part of a Containerfile

This relies on a podman-ecosystem specific feature: `FROM oci:`
which allows ingesting into the container build flow an OCI
archive built inside a stage. With this, we can generate
arbitrary container structure, in particular "chunked"
images. A bit more in [container.md](container).

In this example, we will dramatically trim out the current reference
base image, including especially the rpm-ostree and dnf stacks.

```Dockerfile
FROM quay.io/fedora/fedora-bootc:rawhide as rootfs
RUN <<EORUN
set -xeuo pipefail
# Remove some high level superfulous stuff
dnf -y remove sos NetworkManager-tui vim nano
# And this only targets VMs, so flush out all firmware
rpm -qa --queryformat=%{NAME} | grep -Fe '-firmware-' | xargs dnf -y remove
# We don't want any python, and we don't need rpm-ostree either.
dnf -y remove python3 rpm-ostree{,-libs}
bootc container lint
EORUN

# This builder image can be anything as long as it has a new enough
# rpm-ostree.
FROM quay.io/fedora/fedora-bootc:rawhide as builder
RUN --mount=type=bind,rw=true,src=.,dst=/buildcontext,bind-propagation=shared \
--mount=from=rootfs,dst=/rootfs <<EORUN
set -xeuo pipefail
rm /buildcontext/out.oci -rf
rpm-ostree experimental compose build-chunked-oci --bootc --format-version=1 \
--rootfs=/rootfs --output /buildcontext/out.oci
EORUN

# Finally, output the OCI archive back into our final container image. Here we
# can add labels and other metadata - note that no metadata was inherited from
# the source image - only the root filesystem!
FROM oci:./out.oci
# Need to reference builder here to force ordering. But since we have to run
# something anyway, we might as well cleanup after ourselves.
RUN --mount=type=bind,from=builder,src=.,target=/var/tmp \
--mount=type=bind,rw=true,src=.,dst=/buildcontext,bind-propagation=shared rm /buildcontext/out.oci -rf
```

## Using outside of container builds

There is no requirement to run as part of a container build, or even a container.
You can generate a root filesystem however you want, and get an OCI archive
out, which can be pushed directly to a registry using a tool such as `skopeo`.

```
mkdir -p rootfs
...
rpm-ostree experimental compose build-chunked-oci --bootc --format-version=1 \
--rootfs=rootfs --output out.oci
skopeo copy --authfile=/path/to/auth.json oci:out.oci docker://quay.io/exampleos/exampleos:latest
```

However as noted above, it is recommended to follow e.g. the
[fedora-bootc documentation](https://docs.fedoraproject.org/en-US/bootc/) around custom base images.
1 change: 1 addition & 0 deletions docs/experimental.md
Original file line number Diff line number Diff line change
Expand Up @@ -7,6 +7,7 @@ nav_order: 7
# Experimental features
{: .no_toc }

1. [build-chunked-oci](build-chunked-oci.md)
1. [Wrapping other CLI entrypoints](cliwrap.md)
1. [ostree native containers](container.md)
1. [rebuild](ex-rebuild.md)
Expand Down
31 changes: 29 additions & 2 deletions rust/src/cli_experimental.rs
Original file line number Diff line number Diff line change
Expand Up @@ -18,14 +18,38 @@ enum Cmd {
/// This command does nothing, it's a placeholder for future expansion.
#[clap(hide = true)]
Stub,
/// Options for building.
Compose {
#[clap(subcommand)]
cmd: ComposeCmd,
},
}

#[derive(Debug, clap::Subcommand)]
enum ComposeCmd {
BuildChunkedOCI {
#[clap(flatten)]
opts: crate::compose::BuildChunkedOCI,
},
}

impl ComposeCmd {
fn run(self) -> Result<()> {
match self {
ComposeCmd::BuildChunkedOCI { opts } => opts.run(),
}
}
}

impl Cmd {
fn run(self) -> Result<()> {
match self {
Cmd::Stub => println!("Did nothing successfully."),
Cmd::Stub => {
println!("Did nothing successfully.");
Ok(())
}
Cmd::Compose { cmd } => cmd.run(),
}
Ok(())
}
}

Expand All @@ -45,6 +69,9 @@ mod tests {
let opt = Experimental::try_parse_from(["experimental", "stub"]).unwrap();
match opt.cmd {
Cmd::Stub => {}
o => {
panic!("Unexpected {o:?}")
}
}
Ok(())
}
Expand Down
Loading

0 comments on commit 6a699f4

Please sign in to comment.