diff --git a/config/_default/menus/menus.en.toml b/config/_default/menus/menus.en.toml index 489220496e..b687290ecd 100644 --- a/config/_default/menus/menus.en.toml +++ b/config/_default/menus/menus.en.toml @@ -64,23 +64,11 @@ parent = "menu-oss" weight = 15 -[[main]] - name = "apko" - url = "/open-source/apko/" - parent = "menu-oss" - weight = 20 - -[[main]] - name = "melange" - url = "/open-source/melange/" - parent = "menu-oss" - weight = 30 - [[main]] name = "Open Containers" url = "/open-source/oci/" parent = "menu-oss" - weight = 35 + weight = 35 [[main]] name = "SBOMs" @@ -116,7 +104,7 @@ url = "/software-security/what-is-software-supply-chain-security/" parent = "menu-security" weight = 20 - + [[main]] name = "How to Select a Secure Base Image" url = "/software-security/selecting-a-base-image/" diff --git a/content/chainguard/chainguard-images/faq.md b/content/chainguard/chainguard-images/faq.md index 2f6bc7f161..fa3b19f3d9 100644 --- a/content/chainguard/chainguard-images/faq.md +++ b/content/chainguard/chainguard-images/faq.md @@ -22,7 +22,7 @@ Chainguard Images are based on [Wolfi](/open-source/wolfi/), a Linux _undistro_ We do have some images with Alpine-based variants in order to support musl or unusual architectures. ## How do Chainguard Images relate to the Google Distroless Images? -The [Google distroless](https://github.com/GoogleContainerTools/distroless) images follow a similar philosophy to many of our images: they are minimal images that don't include package managers or shells. The main difference is in the implementation. The Google distroless images are built with [Bazel](https://bazel.build) and based on the Debian distribution, whereas Chainguard Images are built with [apko](/open-source/apko) based on the [Wolfi](/open-source/wolfi) distribution. Wolfi is a community Linux [undistro](/open-source/wolfi/overview/#why-undistro). We believe our approach is more maintainable and extensible. +The [Google distroless](https://github.com/GoogleContainerTools/distroless) images follow a similar philosophy to many of our images: they are minimal images that don't include package managers or shells. The main difference is in the implementation. The Google distroless images are built with [Bazel](https://bazel.build) and based on the Debian distribution, whereas Chainguard Images are built with [apko](https://github.com/chainguard-dev/apko) based on the [Wolfi](/open-source/wolfi) distribution. Wolfi is a community Linux [undistro](/open-source/wolfi/overview/#why-undistro). We believe our approach is more maintainable and extensible. ## What is an "undistro"? We call Wolfi an undistro because unlike a typical Linux distribution, Wolfi is a stripped-down distribution designed for the cloud-native era. Most notably, we don’t include a Linux kernel, instead relying on the environment (such as the container runtime) to provide this. diff --git a/content/chainguard/chainguard-images/how-to-use-chainguard-images.md b/content/chainguard/chainguard-images/how-to-use-chainguard-images.md index 5a3b09b5d8..7a4c6b781e 100644 --- a/content/chainguard/chainguard-images/how-to-use-chainguard-images.md +++ b/content/chainguard/chainguard-images/how-to-use-chainguard-images.md @@ -135,7 +135,7 @@ It often happens that you want a [distroless](/chainguard/chainguard-images/gett 1. Compile the dependency from source and use a multi-stage Dockerfile to create a new base image. This works, but may require considerable effort to get the dependency compiling and to keep it up to date. This process quickly becomes untenable if you require several dependencies. 2. Use the `wolfi-base` image that includes apk tools to install the package in the traditional Dockerfile manner. This works but sacrifices a lot of the advantages of the “distroless” philosophy. -3. Use Chainguard’s [melange and apko tooling to create a custom base image](/open-source/melange/tutorials/getting-started-with-melange/). This keeps the image as minimal as possible without sacrificing maintainability. +3. Use Chainguard’s [melange](https://github.com/chainguard-dev/melange) and [apko](https://github.com/chainguard-dev/apko) tooling to create a custom base image. This keeps the image as minimal as possible without sacrificing maintainability. ### Using the wolfi-base Image The `wolfi-base` image is a good starting point to try out Chainguard Images. Unlike most of the other images, which are strictly distroless, `wolfi-base` includes the `apk` package manager, which facilitates composing additional software into it. Just keep in mind that the resulting image will be a little larger due to the extra software and won't have a comprehensive SBOM that covers all your dependencies, since the new software will be added as a layer on top of `wolfi-base`. diff --git a/content/open-source/build-tools/_index.md b/content/open-source/build-tools/_index.md deleted file mode 100644 index 575298e519..0000000000 --- a/content/open-source/build-tools/_index.md +++ /dev/null @@ -1,12 +0,0 @@ ---- -title: "Build Tools" -lead: "Open source images build tools" -type: "article" -date: 2024-05-02T08:49:15+00:00 -lastmod: 2024-05-02T08:49:15+00:00 -draft: false -images: [] -weight: 20 ---- - -The open source tools that were developed for the [Wolfi](/open-source/wolfi) operating system. \ No newline at end of file diff --git a/content/open-source/build-tools/apko/_index.md b/content/open-source/build-tools/apko/_index.md deleted file mode 100644 index e0ce0b3268..0000000000 --- a/content/open-source/build-tools/apko/_index.md +++ /dev/null @@ -1,12 +0,0 @@ ---- -title: "apko" -lead: "Minimalist OCI image builder based on apk" -aliases: -- /open-source/apko -description: "Minimalist OCI image builder based on apk" -type: "article" -date: 2022-08-08T08:49:15+00:00 -lastmod: 2024-05-02T08:49:15+00:00 -draft: false -images: [] ---- diff --git a/content/open-source/build-tools/apko/bazel-rules.md b/content/open-source/build-tools/apko/bazel-rules.md deleted file mode 100644 index c97dd8bdee..0000000000 --- a/content/open-source/build-tools/apko/bazel-rules.md +++ /dev/null @@ -1,252 +0,0 @@ ---- -title: "Bazel Rules for apko" -linktitle: "Bazel Rules" -aliases: -- /open-source/apko/bazel-rules -type: "article" -lead: "Build secure, minimal Wolfi-based container images using Bazel" -description: "Build secure, minimal Wolfi-based container images using Bazel" -date: 2023-10-23T08:49:31+00:00 -lastmod: 2024-05-02T16:49:31+00:00 -draft: false -tags: ["apko", "Procedural",] -images: [] -menu: - docs: - parent: "apko" -weight: 900 -toc: true ---- - -`rules_apko` is an open source plugin for Bazel that makes it possible to build secure, minimal Wolfi-based container images using the popular Bazel build system. This wraps the [apko](https://github.com/chainguard-dev/apko) tool for use under Bazel. - -## Prerequisites - -First, be sure you have Bazel installed, you can follow the [Bazel installation guide](https://bazel.build/install) for more details. - -Next, `rules_apko` requires a one-time setup to configure Bazel to be able to make partial fetches. - -Paste the following into your root `BUILD` file. - -```py -load("@rules_apko//apko:defs.bzl", "apko_bazelrc") - -apko_bazelrc() -``` - -> **Note**: By default, `apko_bazelrc` will generate `.bazelrc` to accomodate for fetching from `dl-cdn.alpinelinux.org` and `packages.wolfi.dev`. this can be configured by passing the `repositories` attribute to `apko_bazelrc()` call. - -Then, run the following command. - -```sh -bazel run @@//:apko_bazelrc && chmod +x .apko/range.sh -``` - -Finally, paste this into your preferred \`.bazelrc\` file, - -```sh -# Required for rules_apko to make range requests -try-import %workspace%/.apko/.bazelrc -``` - -Review additional [initial setup documentation](https://github.com/chainguard-dev/rules_apko/blob/main/docs/initial-setup.md) updates in the `rules_apko` [repo](https://github.com/chainguard-dev/rules_apko). - -## Installation - -To install v1.0.0, you can follow one of the options below. For other releases, follow the instructions in the release notes from the release you wish to use: [https://github.com/chainguard-dev/rules_apko/releases](https://github.com/chainguard-dev/rules_apko/releases). - -### Using Bzlmod with Bazel 6 - -1. Enable with `common --enable_bzlmod` in `.bazelrc`. -1. Add to your `MODULE.bazel` file: - -```starlark -bazel_dep(name = "rules_apko", version = "1.0.0-rc1") -``` - -### Using WORKSPACE - -Paste this snippet into your file: - -```starlark -load("@bazel_tools//tools/build_defs/repo:http.bzl", "http_archive") -http_archive( - name = "rules_apko", - sha256 = "5c91a2322bec84a0005dd8178495775938b581053812e70d21b030bef3625623", - strip_prefix = "rules_apko-1.0.0-rc1", - url = "https://github.com/chainguard-dev/rules_apko/releases/download/v1.0.0-rc1/rules_apko-v1.0.0-rc1.tar.gz", -) - -###################### -# rules_apko setup # -###################### -# Fetches the rules_apko dependencies. -# If you want to have a different version of some dependency, -# you should fetch it *before* calling this. -# Alternatively, you can skip calling this function, so long as you've -# already fetched all the dependencies. -load("@rules_apko//apko:repositories.bzl", "apko_register_toolchains", "rules_apko_dependencies") - -rules_apko_dependencies() - -apko_register_toolchains(name = "apko") - -load("@rules_apko//apko:translate_lock.bzl", "translate_apko_lock") - -translate_apko_lock( - name = "example_lock", - lock = "@//:apko.lock.json", -) - -load("@example_lock//:repositories.bzl", "apko_repositories") - -apko_repositories() -``` -## Rules - -Public API re-exports - -## apko_image - -
-apko_image(name, architecture, args, config, contents, output, tag)
-
- -Build OCI images from APK packages directly without Dockerfile. - -This rule creates Alpine images using the `apko.yaml` configuration file and relies on cache contents generated by [translate_lock](https://github.com/chainguard-dev/rules_apko/blob/main/docs/translate_lock.md) to be fast. - -```starlark -apko_image( - name = "example", - config = "apko.yaml", - contents = "@example_lock//:contents", - tag = "example:latest", -) -``` - -The label `@example_lock//:contents` is generated by the `translate_lock` extension, which consumes an 'apko.lock.json' file. For more details, refer to the [apko cache documentation](#fetching-and-caching-contents). - -An example demonstrating usage with [rules_oci](https://github.com/bazel-contrib/rules_oci): - -```starlark -apko_image( - name = "alpine_base", - config = "apko.yaml", - contents = "@alpine_base_lock//:contents", - tag = "alpine_base:latest", -) - -oci_image( - name = "app", - base = ":alpine_base" -) -``` - -For more examples checkout the [examples](https://github.com/chainguard-dev/rules_apko/tree/main/examples) directory. - -### Attributes - -| Name | Description | Type | Mandatory | Default | -| :------------- | :------------- | :------------- | :------------- | :------------- | -| name | A unique name for this target. | Name | required | | -| architecture | the CPU architecture which this image should be built to run on. See https://github.com/chainguard-dev/apko/blob/main/docs/apko_file.md#archs-top-level-element | String | optional | "" | -| args | additional arguments to provide when running the apko build command. | List of strings | optional | [] | -| config | Label to the apko.yaml file. | Label | required | | -| contents | Label to the contents repository generated by translate_lock. See [apko-cache](https://github.com/chainguard-dev/rules_apko/blob/main/docs/apko-cache.md) documentation. | Label | required | | -| output | - | String | optional | "oci" | -| tag | tag to apply to the resulting docker tarball. only applicable when output is docker | String | required | | - -### apko_bazelrc - -
-apko_bazelrc(name, repositories, kwargs)
-
- -Helper macro for generating `.bazelrc` and `range.sh` files to allow for partial package fetches. - -Review [Prerequisites](#prerequisites) documentation for more information. - -### Parameters - -| Name | Description | Default Value | -| :------------- | :------------- | :------------- | -| name | name of the target | "apko_bazelrc" | -| repositories | list of repositories to generate .bazelrc for | ["dl-cdn.alpinelinux.org", "packages.wolfi.dev"] | -| kwargs | passed to expanding targets. only well known attributes such as tags testonly ought to be present. | none | - -## Fetching and Caching Contents - -To ensure efficient operation, the `apko_image` rule must maintain a cache of remote contents that it fetches from repositories. While outside of Bazel, `apko` manages its own cache, under Bazel, the cache must be maintained by Bazel to ensure correctness and speed. Therefore, Bazel needs to know what needs to be fetched and from where to cache these HTTP requests and provide them to `apko` as required. - -The `apko.lock.json` file contains all the necessary information about how to perform the HTTP fetches required by `apko` to build the container image. - -### Generating the Lock File - -> **Note:** Documentation for lockfile generation [will be added to the repository docs](https://github.com/chainguard-dev/rules_apko/blob/main/docs/apko-cache.md) once the `apko resolve` command is available. - -### Using `translate_lock` - -Having just the `apko.lock.json` file alone is insufficient; all the information needs to be converted into `apk_` repository calls to make them accessible to Bazel. The `translate_lock` tool accomplishes this by taking the `apko.lock.json` file and dynamically generating the required Bazel repositories. - -`translate_lock` will create a new bazel repository named after itself. This repository will also have a target named contents, which you can pass to `apko_image`: - -```starlark -apko_image( - name = "lock", - config = "apko.yaml", - # name of the repository is the same translate_lock! - contents = "@examples_lock//:contents", - tag = "lock:latest", -) -``` - -#### Usage with `bzlmod` - -```starlark -apk = use_extension("//apko:extensions.bzl", "apko") - -apk.translate_lock( - name = "examples_lock", - lock = "//path/to/lock:apko.lock.json", -) -use_repo(apk, "examples_lock") -``` - -#### Usage with Workspace - -```starlark -load("@rules_apko//apko:translate_lock.bzl", "translate_apko_lock") - -translate_apko_lock( - name = "example_lock", - lock = "//path/to/lock:apko.lock.json", -) - -load("@example_lock//:repositories.bzl", "apko_repositories") - -apko_repositories() -``` - -## Repository rules for translating apko.lock.json - -`translate_apko_lock` - -
-translate_apko_lock(name, lock, repo_mapping, target_name)
-
- -## Repository rule to generate starlark code from an `apko.lock.json` file. - -Review [the section above](http://localhost:1313/open-source/apko/bazel-rules/#fetching-and-caching-contents) for more information. - - -### Attributes - - -| Name | Description | Type | Mandatory | Default | -| :------------- | :------------- | :------------- | :------------- | :------------- | -| name | A unique name for this repository. | Name | required | | -| lock | label to the apko.lock.json file. | Label | required | | -| repo_mapping | A dictionary from local repository name to global repository name. This allows controls over workspace dependency resolution for dependencies of this repository.<p>For example, an entry "@foo": "@bar" declares that, for any time this repository depends on @foo (such as a dependency on @foo//some:target, it should actually resolve that dependency within globally-declared @bar (@bar//some:target). | Dictionary: String -> String | required | | -| target_name | internal. do not use! | String | optional | "" | diff --git a/content/open-source/build-tools/apko/faq.md b/content/open-source/build-tools/apko/faq.md deleted file mode 100644 index 98848255bc..0000000000 --- a/content/open-source/build-tools/apko/faq.md +++ /dev/null @@ -1,37 +0,0 @@ ---- -title: "apko FAQs" -aliases: -- /open-source/apko/faq -type: "article" -lead: "Frequently asked questions about apko" -description: "Frequently asked questions about apko" -date: 2022-10-10T11:07:52+02:00 -lastmod: 2024-05-02T11:07:52+02:00 -draft: false -tags: ["apko", "FAQ",] -images: [] -menu: - docs: - parent: "apko" -weight: 50 -toc: true ---- - -## Do I need to understand apko to use Chainguard Images? -No. Chainguard built [apko](https://github.com/chainguard-dev/apko) as part of its open source tooling under the [Wolfi](/open-source/wolfi) operating system. While you can check out the [project on GitHub](https://github.com/chainguard-dev/apko) and learn more, it's not a prerequisite for using or [working with Chainguard Images](/chainguard/chainguard-images/working-with-images). - -## How are melange packages defined? -melange apks are defined declaratively using a YAML file. - -## Are melange apks compatible with Alpine? -Yes, melange apks are built to be compatible with apk-based systems including Alpine. - -## Can I mix Alpine and Wolfi package repositories to create my melange build environment? -No, it's not possible to mix Alpine apks with Wolfi apks. If you have unmet dependencies, you'll need to build those first as separate packages. - -## Is it mandatory to sign packages with a melange key? -Signing packages is not mandatory, but it is a recommended practice that is enforced by some systems. Signing packages allows users and automated systems to verify that the package they downloaded was built by the same person who signed it, and that it hasn't been tampered with. - -## Can I create custom pipelines and embed them into my main pipeline? -Although melange supports inclusion of sub-pipelines, this feature currently only supports the built-in pipelines (such as `make`, `split` and others) that can be found at the [pkg/build/pipelines](https://github.com/chainguard-dev/melange/tree/main/pkg/build/pipelines) directory on the main project repository. -The ability to embed custom pipelines is on the roadmap, but it's not a priority at the moment. diff --git a/content/open-source/build-tools/apko/getting-started-with-apko.md b/content/open-source/build-tools/apko/getting-started-with-apko.md deleted file mode 100644 index 10d96c65b2..0000000000 --- a/content/open-source/build-tools/apko/getting-started-with-apko.md +++ /dev/null @@ -1,172 +0,0 @@ ---- -title: "Getting Started with apko" -aliases: -- /open-source/apko/getting-started-with-apko -type: "article" -lead: "Minimalist OCI image builder based on APK" -description: "Quickstart to get apko up and running" -date: 2022-07-06T08:49:31+00:00 -lastmod: 2024-05-02T16:49:31+00:00 -draft: false -tags: ["apko", "Procedural",] -images: [] -menu: - docs: - parent: "apko" -weight: 100 -terminalImage: apko:latest -toc: true ---- - -[apko](http://github.com/chainguard-dev/apko) is a command-line tool to build container images using a declarative language based on YAML. apko is so named as it uses the [apk](https://wiki.alpinelinux.org/wiki/Package_management) package format and is inspired by the [ko](https://github.com/google/ko) build tool. It is part of the open source tooling Chainguard developed to create the [Wolfi](/open-source/wolfi) operating system which is used in [Chainguard Images](/chainguard/chainguard-images). - -## Why apko -Container images are typically assembled in multiple steps. A tool like Docker, for example, combines building steps (as in, running commands to copy files, build and deploy applications) and composition (as in, composing a base image with pre-built packages) in a single piece of software. apko, on the other hand, is solely a **composition** tool that focuses on producing lightweight, "flat" base images that are fully reproducible and contain auto generated [SBOM](https://www.cisa.gov/sbom) files for every successful build. - -Instead of building your application together with your components and system dependencies, you can build your application once and compose it into different architectures and distributions, using a tool such as [melange](https://github.com/chainguard-dev/melange) in combination with apko. For more information on how melange and apko work together, you can check this blog post: [Secure your Software Factory with melange and apko](https://blog.chainguard.dev/secure-your-software-factory-with-melange-and-apko/). - -In this guide, we'll learn how to use apko to build a base [Wolfi](/open-source/wolfi/overview/) image. - -## Requirements - -The fastest way to get apko up and running on your system is by using the [official apko image](/chainguard/chainguard-images/reference/apko/overview/) with Docker. This method is compatible with all operating systems that support Docker and shared volumes. Please follow the [appropriate Docker installation instructions](https://docs.docker.com/get-docker/) for your operating system. - -If you want to run apko on CI/CD pipelines built on top of GitHub Actions, check the [apko build action](https://github.com/chainguard-images/actions/tree/main/apko-build) on GitHub. - -The instructions in this document were validated on an Ubuntu 22.04 workstation running Docker 20.10. - -## Step 1 — Download the apko Image - -Start by pulling the official apko image into your local system: - -```shell -docker pull cgr.dev/chainguard/apko -``` - -This will download the latest version of the distroless apko image, which is rebuilt every night for extra freshness. - -Check that you're able to run apko with: - -```shell -docker run --rm cgr.dev/chainguard/apko version -``` - -You should get output similar to this: - -``` - _ ____ _ __ ___ - / \ | _ \ | |/ / / _ \ - / _ \ | |_) | | ' / | | | | - / ___ \ | __/ | . \ | |_| | - /_/ \_\ |_| |_|\_\ \___/ -apko - -GitVersion: v0.6.0 -... -``` - -In the next step, you'll build your first apko image. - - -## Step 2 — Build a Test Image - -To test that you're able to build images, you can use one of the example `yaml` definition files that are included in the [official apko code repository](https://github.com/chainguard-dev/apko/tree/main/examples). Here we'll use the `wolfi-base.yaml` for demonstration. - -Create a new folder to save your image files, them move to that directory: - -```shell -mkdir ~/apko -cd ~/apko -``` - -Next, create a file named `wolfi-base.yaml` to save your image definition. You can use `nano` for that: - -```shell -nano wolfi-base.yaml -``` - -The `wolfi-base.yaml` example image is defined as follows: - -```yaml -contents: - keyring: - - https://packages.wolfi.dev/os/wolfi-signing.rsa.pub - repositories: - - https://packages.wolfi.dev/os - packages: - - ca-certificates-bundle - - wolfi-base - -entrypoint: - command: /bin/sh -l - -archs: - - x86_64 -``` - -The `contents` node is used to define allowed package sources and which packages should be included in the image. Here we'll be using only packages from the main Wolfi APK repository. In the `packages` section, we require the [wolfi-base](https://github.com/wolfi-dev/os/blob/main/wolfi-base.yaml) package, which is a meta-package to set up a bare minimum Wolfi system. - -The `command` field within the `entrypoint` node defines the image entry point command `/bin/sh -l`, which will land you in a shell prompt whenever the image is executed. Finally, the `archs` node specifies that this image will be built for the `x86-64` architecture. - -Save and close the file after you're done including these contents. With `nano`, you can do that by pressing `CTRL+X`, then confirming with `Y` and `ENTER`. - -The only thing left to do now is run apko to build this image. The following build command will: - -- set up a volume share in the current directory, synchronizing its contents with apko's image workdir; this way, the generated artifacts will be available on your host system. -- execute the `cgr.dev/chainguard/apko` image with the `build` command, tagging the image as `wolfi-base:test-amd64` and saving the build as `wolfi-test.tar`. - -```shell -docker run --rm -v ${PWD}:/work -w /work cgr.dev/chainguard/apko build wolfi-base.yaml wolfi-base:test wolfi-test.tar -``` - -You should get output similar to this: - -``` -. . . -Mar 15 20:17:02.023 [INFO] [arch:x86_64] Building images for 1 architectures: [amd64] -Mar 15 20:17:02.023 [INFO] [arch:x86_64] building tags [wolfi-base:test] -. . . -Mar 15 20:17:04.261 [INFO] loading config file: wolfi-base.yaml -Mar 15 20:17:04.416 [INFO] [arch:x86_64] adding amd64 to index -Mar 15 20:17:04.419 [INFO] [arch:x86_64] Generating index SBOM -Mar 15 20:17:04.420 [INFO] [arch:x86_64] Final index tgz at: wolfi-test.tar -``` - -From the output, you can notice that the image was successfully built as `wolfi-test.tar` in the container, which is shared with your local folder on the host thanks to the volume you created when running the `docker run` command. - -## Step 3 — Test the Image with Docker - -To test the generated image with Docker, you'll need to use the `docker load` command and import the `.tar` file you created in the previous step: - -```shell -docker load < wolfi-test.tar -``` -You'll get output like this: -``` -bf6e72d71c13: Loading layer [==================================================>] 5.491MB/5.491MB -Loaded image: wolfi-base:test-amd64 -``` - -You can check that the image is available at the host system with: - -```shell -docker image list -``` - -You should be able to find the `wolfi-base` image with the `test-amd64` tag among the results. - -Now you can run the image with: - -```shell -docker run -it wolfi-base:test-amd64 -``` - -This will get you into a container running the apko-built image `wolfi-base:test-amd64`. It's a regular shell that you can explore to see what's included - just keep in mind that this is a minimalist image with only the base Wolfi system. To include additional software packages, check the [Wolfi repository](https://github.com/wolfi-dev/os) to find the packages you'll need for your specific use case, or check out [melange](/open-source/melange/), apko's companion project that allows users to build their own APK packages from source. - -## Conclusion - -In this guide, you learned what apko is and what makes it a powerful resource in your cloud-native tooling. - -If you need help debugging your build, check our [Troubleshooting apko](/open-source/apko/troubleshooting/) page for more information. -Check the [official apko repository](https://github.com/chainguard-dev/apko/) if you want to report an issue or suggest new features. - diff --git a/content/open-source/build-tools/apko/overview/apko_melange_ecosystem.png b/content/open-source/build-tools/apko/overview/apko_melange_ecosystem.png deleted file mode 100644 index 2f006c792e..0000000000 Binary files a/content/open-source/build-tools/apko/overview/apko_melange_ecosystem.png and /dev/null differ diff --git a/content/open-source/build-tools/apko/overview/index.md b/content/open-source/build-tools/apko/overview/index.md deleted file mode 100644 index 73c5977226..0000000000 --- a/content/open-source/build-tools/apko/overview/index.md +++ /dev/null @@ -1,37 +0,0 @@ ---- -title: "apko Overview" -aliases: -- /open-source/apko/overview -type: "article" -description: "apko Overview" -date: 2022-10-10T11:07:52+02:00 -lastmod: 2024-05-02T11:07:52+02:00 -draft: false -tags: ["apko", "Overview",] -images: [] -menu: - docs: - parent: "apko" -weight: 10 -toc: true ---- - -[apko](http://github.com/chainguard-dev/apko) is a command-line tool that was developed for [Chainguard Images](/chainguard/chainguard-images). - -apko is so named as it uses the [APK](https://wiki.alpinelinux.org/wiki/Package_management) package format and is inspired by the [ko](https://github.com/google/ko) build tool. - -The following image contains an overview of the apko ecosystem and how it interacts with melange for building apk-based images, using either Alpine or Wolfi as base system. - -![The following image contains an overview of the apko ecosystem and how it interacts with melange for building apk-based images, using either Alpine or Wolfi as base system.](apko_melange_ecosystem.png) - -apko and [melange](/open-source/melange) are part of the open source toolkit developed by Chainguard to build [Wolfi](/open-source/wolfi) and [Chainguard Images](/chainguard/chainguard-images). - -### apko Features - -- **Fully reproducible by default.** Run apko twice and you will get exactly the same binary. -- **Fast.** apko aims to build images in ms. -- **Small.** apko generated images only contain what's needed by the application, in the style of distroless. -- **SBOM Support.** apko produces a Software Bill of Materials (SBOM) for images, detailing all the packages inside. -- **Services.** apko supports using the s6 supervision suite to run multiple processes in a container without reaping or signalling issues. - - diff --git a/content/open-source/build-tools/apko/reference.md b/content/open-source/build-tools/apko/reference.md deleted file mode 100644 index 09feaef12c..0000000000 --- a/content/open-source/build-tools/apko/reference.md +++ /dev/null @@ -1,203 +0,0 @@ ---- -title: "apko YAML Reference" -aliases: -- /open-source/apko/reference -type: "article" -description: "A reference guide for writing YAML for apko" -date: 2022-10-10T11:07:52+02:00 -lastmod: 2024-05-02T11:07:52+02:00 -draft: false -tags: ["apko", "Reference",] -images: [] -menu: - docs: - parent: "apko" -weight: 150 -toc: true ---- - -Apko files are a YAML based declarative definition of an image to be built by apko. Unlike Dockerfiles, there is no support for running arbitrary Unix commands (i.e. there is no equivalent of `RUN` statements). This means apko can guarantee the contents and reproducibility of the final image, as well as produce extra metadata such as SBOMs. - -This page provides a reference for apko's YAML specification. - -## contents -This section defines sources and packages you want to include in your image. - -| Directive | Description | -|----------------|:-------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------| -| `repositories` | Defines a list of repositories to look in for packages. These can be either URLs or file paths. File paths should start with a label like @local e.g: `@local /github/workspace/packages`. | -| `packages` | A list containing all packages that should be installed as part of a given image's requirements. | -| `keyring` | PGP keys to add to the keyring for verifying packages. | - - -### Example - -```yaml -contents: - keyring: - - https://packages.wolfi.dev/os/wolfi-signing.rsa.pub - repositories: - - https://packages.wolfi.dev/os - packages: - - wolfi-base - - nginx -``` - -## entrypoint -This section defines the default commands and/or services to be executed by the container at runtime. - -| Directive | Description | -|------------------|:---------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------| -| `type` | When this is set to `service-bundle`, the s6 supervisor will be used to start commands listed in `services`. | -| `command` | Specifies a command to run when the container starts. Note that this sets the image _entrypoint_, not the _cmd_ top level element. Only valid when `type` is **not** `service-bundle`. | -| `shell-fragment` | Behaves like `command`, except that the command is a shell fragment. Only valid when `type` is **not** `service-bundle`. | -| `services` | Maps **service names** to **commands** that should be started by the s6 supervisor when the container starts. This option is only valid when `type` is set to `service-bundle`. | - -Services are monitored with the [s6 supervisor](https://skarnet.org/software/s6/index.html). - -### Examples - -**Example 1: Command entrypoint** -```yaml -entrypoint: - command: /usr/bin/php81 -``` - -**Example 2: Service entrypoint** -```yaml -entrypoint: - type: service-bundle - services: - php-fpm: /usr/sbin/php-fpm -``` - -## cmd -Defines a command to run when the container starts up. If `entrypoint.command` is not set, it will be executed with `/bin/sh -c`. If `entrypoint.command` is set, `cmd` will be passed as arguments to `entrypoint.command`. This sets the "cmd" value on OCI images. - -### Example - -```yaml -cmd: help -``` - -## stop-signal -Configures the shutdown signal sent to the main process in the container by the runtime. By default, this is `SIGTERM`. Be mindful when using this alongside a `service-bundle` entrypoint, which will intercept and potentially reinterpret the signal. - -### Example - -```yaml -stop-signal: SIGQUIT -``` - -## work-dir -Sets the working directory for the image. Commands defined within the image `entrypoint` are taken as relative to this path. Equivalent to [WORKDIR](https://docs.docker.com/engine/reference/builder/#workdir) in Dockerfile syntax. - -### Example - -```yaml -work-dir: /app -``` -## archs -The architectures to build. This top-level directive expects a list with all architectures that should be a target for the build. By default, apko will try to build for all architectures that are currently supported. - -### Example - -```yaml -archs: - - x86_64 -``` - -## environment -This section defines environment variables that will be set for this image. - -### Example - -```yaml -environment: - PATH: /usr/sbin:/sbin:/usr/bin:/bin - myVAR: "test" -``` - -## accounts -This section defines users and groups that should be added to this image. - -| Directive | Description | -|-----------|:--------------------------------------------------------------------| -| groups | A list with the groups that should be present in this image. | -| users | A list with the user accounts that should be present in this image. | -| run-as | The default user to run the entrypoint command. | - - -### Example - -```yaml - users: - - username: php - uid: 65532 - gid: 65532 - - username: laravel - uid: 1000 - gid: 1000 - run-as: 65532 -``` -## Paths - -Defines filesystem operations that can be applied to the image. This includes setting permissions on files or directories as well as creating empty files, directories, and links. - -| Directive | Description | -|---------------|:--------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------| -| `path` | Filesystem path to handle. | -| `type` | The type of file operation to perform. This can be one of the following:
- `directory`: create an empty directory at the path
- `empty-file`: create an empty file at the path
- `hardlink`: create a hardlink (`ln`) at the path, linking to the value specified in `source`
- `symlink`: create a symbolic link (`ln -s`) at the path, linking to the value specified in `source`
- `permissions`: sets file permissions on the file or directory at the path. | -| `run-as` | The default user to run the entrypoint command. | -| `uid` | UID to associate with the file | -| `gid` | GID to associate with the file | -| `permissions` | File permissions to set. Permissions should be specified in octal e.g. 0o755 (see `man chmod` for details). | -| `source` | Used in `hardlink` and `symlink`, this represents the path to link to. | - -### Example - -```yaml -paths: - - path: /app - type: directory - permissions: 0o777 - uid: 65532 - gid: 65532 -``` - -## Includes - -Defines a path to a configuration file which should be used as the base config. By default, there is no base config used. - -The path can be either a local file, or a file in a remote git repository, in the same style as Go package names and GitHub Actions. - -### Example - -```yaml -include: github.com/chainguard-dev/apko/examples/alpine-base.yaml@main -``` -This would reference the file `examples/alpine-base.yaml` in the `main` branch of the apko git repository. - -At present, the path structure assumes that the git repository lives on a site similar to -GitHub, GitLab, or Gitea. In other words, given an include path like the above, it will -parse as: - -``` -host: github.com -repository: chainguard-dev/apko -path: examples/alpine-base.yaml -reference: main -``` - - -## Annotations - -`annotations` defines the set of annotations that should be applied to images and indexes. - -### Example - -```yaml -annotations: - image-author: Chainguard - image-source: http://gihub.com/chainguard-images/images -``` diff --git a/content/open-source/build-tools/apko/troubleshooting.md b/content/open-source/build-tools/apko/troubleshooting.md deleted file mode 100644 index 99f5a24357..0000000000 --- a/content/open-source/build-tools/apko/troubleshooting.md +++ /dev/null @@ -1,82 +0,0 @@ ---- -title: "Troubleshooting apko Builds" -aliases: -- /open-source/apko/troubleshooting -type: "article" -lead: "Debugging and common errors" -description: "Debugging and common errors in apko" -date: 2022-08-10T11:07:52+02:00 -lastmod: 2022-08-10T11:07:52+02:00 -contributors: ["Erika Heidi"] -draft: false -tags: ["apko", "Troubleshooting",] -images: [] -menu: - docs: - parent: "apko" -weight: 300 -toc: true ---- - -## Debug Options - -To include debug-level information on apko builds, add `--debug` to your build command: - -```shell -docker run --rm -v ${PWD}:/work cgr.dev/chainguard/apko build --debug \ - apko.yaml hello-minicli:test hello-minicli.tar \ - -k melange.rsa.pub -``` -## Common Errors - -When the apk package manager is unable to resolve your requirements to a set of installable packages, you will get an error similar to this: - -{{< alert context="danger" text="Error: failed to build layer image: initializing apk: failed to fixate apk world: exit status 1" />}} - - -There are two main root causes for this error, which we'll explain in more detail in the upcoming section: - -- apk cannot find the package in the included repositories, or -- apk cannot find the apk index for your custom-built packages. - -### The requested package is not in the included repositories -Make sure you've added the relevant package repositories you need and the package name is correct. -Check the [Wolfi repository](https://github.com/wolfi-dev/os) for available packages if you are building Wolfi images, -or the [Alpine APK index](https://pkgs.alpinelinux.org/packages) if you are using Alpine as base. - -If this is your case, you should find error messages similar to this when enabling debug info with the `--debug` flag: - -{{< alert context="danger" text="ERROR: unable to select packages: hello-minicli (no such package)" />}} - -### apko is unable to find the local packages folder -With melange-built package(s), make sure you have a volume sharing your apko / melange files with the location `/work` inside the apko container. - -### The apk index is missing -If you have a functional volume sharing your packages with the apko container and you're still getting this error, make sure you built a valid apk index as described in [step 4 of the Getting Started with melange Guide](/open-source/melange/tutorials/getting-started-with-melange/#step-4--building-your-apk). - -If this is your case, you should find error messages similar to this when enabling debug info with the `--debug` flag: - -{{< alert context="danger" text="ERROR: Not committing changes due to missing repository tags. Use --force-broken-world to override." />}} - -This is how your packages directory tree should be set up, including the `APKINDEX.tgz` file for each architecture: - -``` -packages -├── aarch64 -│   ├── APKINDEX.tar.gz -│   └── hello-minicli-0.1.0-r0.apk -├── armv7 -│   ├── APKINDEX.tar.gz -│   └── hello-minicli-0.1.0-r0.apk -├── x86 -│   ├── APKINDEX.tar.gz -│   └── hello-minicli-0.1.0-r0.apk -└── x86_64 - ├── APKINDEX.tar.gz - └── hello-minicli-0.1.0-r0.apk - -4 directories, 8 files -``` -## Further Resources - -For additional guidance, please refer to the [apko repository](https://github.com/chainguard-dev/apko) on GitHub, where you can find [more examples](https://github.com/chainguard-dev/apko/tree/main/examples) or [open an issue](https://github.com/chainguard-dev/apko/issues/new/choose) in case of problems. diff --git a/content/open-source/build-tools/melange/_index.md b/content/open-source/build-tools/melange/_index.md deleted file mode 100644 index 68cc681024..0000000000 --- a/content/open-source/build-tools/melange/_index.md +++ /dev/null @@ -1,14 +0,0 @@ ---- -title: "melange" -aliases: -- /open-source/melange -description: "An apk builder tool" -lead: "The declarative APK builder" -type: "article" -date: 2020-10-06T08:49:15+00:00 -lastmod: 2024-05-02T08:49:15+00:00 -draft: false -images: [] ---- - -melange is an apk builder tool that uses declarative pipelines to create apk packages. diff --git a/content/open-source/build-tools/melange/faq.md b/content/open-source/build-tools/melange/faq.md deleted file mode 100644 index ebb09fa8bd..0000000000 --- a/content/open-source/build-tools/melange/faq.md +++ /dev/null @@ -1,42 +0,0 @@ ---- -title: "melange FAQs" -aliases: -- /open-source/melange/faq -type: "article" -lead: "Frequently asked questions about melange" -description: "Frequently asked questions about melange" -date: 2022-10-17T11:07:52+02:00 -lastmod: 2022-10-17T11:07:52+02:00 -draft: false -tags: ["melange", "FAQ"] -images: [] -menu: - docs: - parent: "melange" -weight: 900 -toc: true ---- - -## Do I need to understand melange to use Chainguard Images? - -No. Chainguard built [melange](https://github.com/chainguard-dev/melange) as part of its open source tooling used for the [Wolfi](/open-source/wolfi) operating system. While you can check out the [project on GitHub](https://github.com/chainguard-dev/melange) and learn more, it’s not a prerequisite for using or working with [Chainguard Images](/chainguard/chainguard-images). - -## How are melange packages defined? -melange apks are defined declaratively using a YAML file. - -## Are melange apks compatible with Alpine? -Yes, melange apks are built to be compatible with apk-based systems including Alpine. - -## Can I mix Alpine and Wolfi package repositories to create my melange build environment? -No, it's not possible to mix Alpine apks with Wolfi apks. If you have unmet dependencies, you'll need to build those first as separate packages. - -## Is it mandatory to sign packages with a melange key? -Signing packages is not mandatory, but it is a recommended practice, because it allows users and automated systems to verify that the package they downloaded was built by the same person who signed it, and that it hasn't been tampered with. - -## What happens if I don't provide a key to sign my package(s)? -Some systems may prevent installation of your apk if they can't attest the package provenance. This is the case with apko, which by default will fail any builds that reference unsigned packages. - -## Can I create custom pipelines and embed them into my main pipeline? -Although melange supports inclusion of sub-pipelines, this feature currently only supports the built-in pipelines (such as `make`, `split` and others) that can be found at the [pkg/build/pipelines](https://github.com/chainguard-dev/melange/tree/main/pkg/build/pipelines) directory on the main project repository. -The ability to embed custom pipelines is on the roadmap, but it's not a priority at the moment. - diff --git a/content/open-source/build-tools/melange/getting-started-with-melange.md b/content/open-source/build-tools/melange/getting-started-with-melange.md deleted file mode 100644 index 3b90e903a7..0000000000 --- a/content/open-source/build-tools/melange/getting-started-with-melange.md +++ /dev/null @@ -1,407 +0,0 @@ ---- -title: "Getting Started with melange" -aliases: -- /open-source/melange/getting-started-with-melange -- /open-source/melange/tutorials/getting-started-with-melange -lead: "An apk builder tool" -type: "article" -description: "melange is a declarative apk builder" -date: 2022-07-21T15:21:01+02:00 -lastmod: 2024-05-02T15:21:01+02:00 -draft: false -tags: ["melange", "Procedural"] -images: [] -menu: - docs: - parent: "melange-tutorials" -weight: 100 -toc: true -# terminalImage: melange:latest ---- - -[melange](https://github.com/chainguard-dev/melange) is an [apk](https://wiki.alpinelinux.org/wiki/Package_management) builder tool that uses declarative pipelines to create apk packages. From a single YAML file, users are able to generate multi-architecture apks that can be injected directly into [apko](https://github.com/chainguard-dev/apko) builds, which renders apko and melange a [powerful combination for any container image factory](https://blog.chainguard.dev/secure-your-software-factory-with-melange-and-apko/). - -Understanding melange can help you better understand the [Wolfi](/open-source/wolfi) operating system and how [Chainguard Images](/chainguard/chainguard-images) are made to be minimal and secure, but it is not necessary to have a background in melange in order to use Chainguard Images. - -## Why melange - -Software supply chain threats have been growing exponentially in the last few years, according to [industry leaders and security researchers (PDF)](https://www.usenix.org/system/files/login/articles/login_winter20_17_geer.pdf). With the popularization of automated workflows and cloud native deployments, it is more important than ever to provide users with the ability to attest the provenance of all relevant software artifacts. - -Instead of building your application together with your components and system dependencies, you can build your application once and compose it into different architectures and distributions using melange, as if they were any other component of an image. - -In this guide, you'll learn how to build a software package with melange. To demonstrate the versatile combination of melange and apko builds, we'll package a small command-line PHP script and build a minimalist container image with the generated apk. All files used in this demo are open source and available at the [melange-php-demos](https://github.com/chainguard-dev/melange-php-demos/tree/main/hello-minicli) repository. - -## Requirements - -Our guide is compatible with operating systems that support Docker and shared volumes. Please follow the [appropriate Docker installation instructions](https://docs.docker.com/get-docker/) for your operating system. - -You won't need PHP or Composer installed on your system, since we'll be using Docker to build the demo app. - -### Note for Linux Users - -In order to be able to build apks for multiple architectures using Docker, you'll need to register additional QEMU headers within your kernel. This is done automatically for Docker Desktop users, so if you are on macOS you don't need to run this additional step. - -Run the following command to register the necessary handlers within your kernel, using the [multiarch/qemu-user-static](https://github.com/multiarch/qemu-user-static) image. - -```shell -docker run --rm --privileged multiarch/qemu-user-static --reset -p yes -``` - -You should now be able to build apks for all architectures that melange supports. - -## Step 1 — Downloading the melange Image - -The fastest way to get melange up and running on your system is by using the [official melange image](https://github.com/distroless/melange) with Docker. Start by pulling the official melange image into your local system: - -```shell -docker pull cgr.dev/chainguard/melange:latest -``` - -This will download the latest version of the distroless melange image, which is rebuilt every night for extra freshness. - -Check that you're able to run melange with `docker run`. - -```shell -docker run --rm cgr.dev/chainguard/melange version -``` - -You should get output similar to the following: - -``` - __ __ _____ _ _ _ _ ____ _____ - | \/ | | ____| | | / \ | \ | | / ___| | ____| - | |\/| | | _| | | / _ \ | \| | | | _ | _| - | | | | | |___ | |___ / ___ \ | |\ | | |_| | | |___ - |_| |_| |_____| |_____| /_/ \_\ |_| \_| \____| |_____| -melange - -GitVersion: v0.1.0-67-g108fd6a -GitCommit: 108fd6a5e400bd100ef6db813380de44516de6e6 -GitTreeState: clean -BuildDate: 2022-08-01T13:36:41 -GoVersion: go1.18.5 -Compiler: gc -Platform: linux/amd64 -``` - -With melange installed, you’re ready to proceed. - -## Step 2 — Preparing the Demo App - -To demonstrate melange's features with a minimalist application that has real-world functionality, we'll create a PHP command line app that queries the [Slip advice](https://api.adviceslip.com/) API and outputs a random piece of advice. The app is a single-file script built with [Minicli](https://github.com/minicli). - -Create a folder in your home directory to place your demo files, then `cd` into it: - -```shell -mkdir ~/hello-minicli && cd $_ -``` - -Run the following command, which will use the official Composer image to generate a `composer.json` file and download `minicli/minicli`: - -```shell -docker run --rm -it -v "${PWD}":/app composer require minicli/minicli -``` - -Once you receive confirmation that the download was completed, we'll need a second dependency to query the advice slip API. Run the following command to include `minicli/curly`, a simple curl wrapper for Minicli: - -```shell -docker run --rm -it -v "${PWD}":/app composer require minicli/curly -``` - -Next, create a new file called `minicli` using your text editor of choice. This will be the executable we'll ship with our apk package. - -```shell -nano minicli -``` - -The following code will set up a new Minicli application and define a single command called `advice`. This will make a GET query to the advice slip API, check the return code, and print the resulting quote when the query is successful. - -Because our app will be built into an apk and later on embedded on a container image, we'll check for the right location of the vendor folder before requiring the `autoload.php` file. This file must be included before the application is instantiated. The `MINICLI_HOME` environment variable can be used to customize the vendor location, which is by default set to `/usr/share/minicli`. - -Place the following code in your `minicli` file: - -```php -#!/usr/bin/env php - - true -]); - -$app->setSignature('Usage: ./minicli advice'); - -$app->registerCommand('advice', function () use ($app) { - $client = new Client(); - - $response = $client->get('https://api.adviceslip.com/advice'); - if ($response['code'] !== 200) { - $app->getPrinter()->error('An API error has occurred.'); - return; - } - - $advice = json_decode($response['body'], true); - $app->getPrinter()->info($advice['slip']['advice']); -}); - -try { - $app->runCommand($argv); -} catch (CommandNotFoundException $notFoundException) { - $app->getPrinter()->error("Command Not Found."); - return 1; -} catch (Exception $exception) { - if ($app->config->debug) { - $app->getPrinter()->error("An error occurred:"); - $app->getPrinter()->error($exception->getMessage()); - } - return 1; -} - -return 0; - -``` - -Save and close the file when you're done. If you're using `nano`, you can do that by typing `CTRL+X`, then `Y` and `ENTER` to confirm. - -Set the script as executable with: - -```shell -chmod +x minicli -``` - -Now you can run the application to make sure it's functional. We'll also use Docker for that: - -```shell -docker run --rm -it -v "${PWD}":/app php:8.1-cli php /app/minicli advice -``` - -You should get a random piece of advice such as: - -``` -Gratitude is said to be the secret to happiness. -``` - -With the application ready, you can start building your package. - -## Step 3 — Creating the melange YAML File -The `melange.yaml` file is where you'll declare the details and specifications of your apk package. For code that generates self-contained binaries, this is typically where you'll build your application artifacts with compiler tools. In the case of interpreted languages, you'll likely build your application by downloading vendor dependencies, setting up relevant paths, and setting the environment up for production. - -Create a new file in your `hello-minicli` folder called `melange.yaml`: - -```shell -nano melange.yaml -``` - -The melange specification file contains three main sections: - -- **package**: defines package specs, such as name, license, and runtime dependencies. Runtime dependencies will be brought into the system automatically as dependencies when the apk is installed. -- **environment**: defines how the environment should be prepared for the build, including required packages and their source repositories. Anything that is only required at build time goes here, and shouldn't be part of the runtime dependencies. -- **pipeline**: defines the build pipeline for this package. - -One of the best advantages of using melange is to be able to control all steps of your build pipeline, and include only what's absolutely necessary. This way, you'll be able to build smaller and more secure container images by removing unnecessary dependencies. - -Place the following content in your `melange.yaml` file: - -```yaml -package: - name: hello-minicli - version: 0.1.0 - description: Minicli melange demo - target-architecture: - - all - copyright: - - license: Apache-2.0 - paths: - - "*" - dependencies: - runtime: - - php81 - - php81-common - - php81-curl - - php81-openssl - -environment: - contents: - repositories: - - https://dl-cdn.alpinelinux.org/alpine/edge/main - - https://dl-cdn.alpinelinux.org/alpine/edge/community - packages: - - alpine-baselayout-data - - ca-certificates-bundle - - curl - - php81 - - php81-common - - php81-curl - - php81-openssl - - composer - -pipeline: - - name: Build Minicli application - runs: | - MINICLI_HOME="${{targets.destdir}}/usr/share/minicli" - EXEC_DIR="${{targets.destdir}}/usr/bin" - mkdir -p "${MINICLI_HOME}" "${EXEC_DIR}" - cp ./composer.json "${MINICLI_HOME}" - /usr/bin/composer install -d "${MINICLI_HOME}" --no-dev - cp ./minicli "${EXEC_DIR}" - chmod +x "${EXEC_DIR}/minicli" - -``` - -Save and close the file when you're done. - -Our build pipeline will set up two distinct directories, separating the application dependencies from its executable entry point. The executable `minicli` script will be copied into `/usr/bin`, while the vendor files will be located at `/usr/share/minicli`. - -## Step 4 — Building your apk - -First make sure you're at the `~/hello-minicli` directory. - -To get started, create a temporary keypair to sign your melange packages: - -```shell -docker run --rm -v "${PWD}":/work cgr.dev/chainguard/melange keygen -``` -This will generate a `melange.rsa` and `melange.rsa.pub` files in the current directory. - -``` -2022/08/05 14:46:05 generating keypair with a 4096 bit prime, please wait... -2022/08/05 14:46:08 wrote private key to melange.rsa -2022/08/05 14:46:08 wrote public key to melange.rsa.pub -``` - -Next, build the apk defined in the `melange.yaml` file with the following command: - -```shell -docker run --privileged --rm -v "${PWD}":/work \ - cgr.dev/chainguard/melange build melange.yaml \ - --arch x86,amd64,aarch64,armv7 \ - --signing-key melange.rsa -``` -This will set up a volume sharing your current folder with the location `/work` inside the container. We'll build packages for `x86`, `amd64`, `aarch64`, and `armv7` platforms and sign them using the `melange.rsa` key. - -When the build is finished, you should be able to find a `packages` folder containing the generated apks (and associated apk index files): - -``` -packages -├── aarch64 -│   ├── APKINDEX.tar.gz -│ └── hello-minicli-0.1.0-r0.apk -├── armv7 -│   ├── APKINDEX.tar.gz -│ └── hello-minicli-0.1.0-r0.apk -├── x86 -│   ├── APKINDEX.tar.gz -│ └── hello-minicli-0.1.0-r0.apk -└── x86_64 -│   ├── APKINDEX.tar.gz - └── hello-minicli-0.1.0-r0.apk - -4 directories, 8 files -``` - -You have successfully built a multi-architecture software package with melange! - -## Step 5 — Building a Container Image with apko - -With the apk packages and apk index in place, you can now build a container image and have your apk(s) installed within it. - -Create a new file called `apko.yaml` in your `~/hello-minicli` directory: - -```shell -nano apko.yaml -``` - -The following apko specification will create a container image tailored to the application we built in the previous steps. Because we defined the PHP dependencies as runtime dependencies within the apk, you don't need to require these packages again here. The container entrypoint command will be set to `/usr/bin/minicli`, where the application executable is located. - -One important thing to note is how we reference the `hello-minicli` apk as a local package within the `repositories` section of the YAML file. The `@local` notation tells apko to search for apks in the specified directory, in this case `/work/packages`. - -Place the following text in your `apko.yaml` file: - -```yaml -contents: - repositories: - - https://dl-cdn.alpinelinux.org/alpine/edge/main - - https://dl-cdn.alpinelinux.org/alpine/edge/community - - '@local /work/packages' - packages: - - alpine-baselayout-data - - ca-certificates-bundle - - hello-minicli@local -accounts: - groups: - - groupname: nonroot - gid: 65532 - users: - - username: nonroot - uid: 65532 - run-as: 65532 -entrypoint: - command: /usr/bin/minicli advice -``` - -Save and close the file when you're done. You are now ready to build your container image. - -The following command will set up a volume sharing your current folder with the location `/work` in the apko container, running the `apko build` command to generate an image based on your `apko.yaml` definition file. - -```shell -docker run --rm --workdir /work -v ${PWD}:/work cgr.dev/chainguard/apko \ - build apko.yaml hello-minicli:test hello-minicli.tar \ - --arch host \ - -k melange.rsa.pub -``` -This will build an OCI image based on your host system's architecture (specified by the `--arch host` flag). If you receive warnings at this point, those are likely related to the types of SBOMs being uploaded and can be safely ignored. - -The command will generate a few new files in the app's directory: - -- `hello-minicli.tar` — the packaged OCI image that can be imported with a `docker load` command -- `sbom-%host-architecture%.cdx` — an SBOM file for your host architecture in `cdx` format -- `sbom-%host-architecture%.spdx.json` — an SBOM file for your host architecture in `spdx-json` format - -Next, load your image within Docker: - -```shell -docker load < hello-minicli.tar -``` -``` -10f951ac3cd2: Loading layer [==================================================>] 7.764MB/7.764MB -Loaded image: hello-minicli:test-%host-architecture% -``` - -Note that the `%host-architecture%` will vary, and there may be multiple images loaded into your Docker daemon. Be sure to edit the variable in the following `docker run` command to match your target architecture. You can also click to edit it inline on this page. - -Now you can run your Minicli program with: - -```shell -docker run --rm hello-minicli:test-%host-architecture% -``` -The demo should output an advice slip such as: - -``` -Only those who attempt the impossible can achieve the absurd. -``` - -You have successfully built a minimalist container image with your apk package installed on it. This image is fully [OCI](https://opencontainers.org/) compatible and can be signed with [Cosign](/open-source/sigstore/cosign/how-to-sign-a-container-with-cosign/) for provenance attestation. - -## Conclusion - -In this guide, we built a demo command line application and packaged it with melange. We also built a container image to install and run our custom apk, using the apko tool. For more information about apko, check our [Getting Started with apko](/open-source/apko/getting-started-with-apko/) guide. - -The demo files are available at the repository [melange-php-demos](https://github.com/chainguard-dev/melange-php-demos), in the `hello-minicli` subfolder. For more information on how to debug your builds, please refer to the demo's [README](https://github.com/chainguard-dev/melange-php-demos/tree/main/hello-minicli) file and check the official documentation for [melange](https://github.com/chainguard-dev/melange) and [apko](https://github.com/chainguard-dev/apko). diff --git a/content/open-source/build-tools/melange/melange-pipelines/_index.md b/content/open-source/build-tools/melange/melange-pipelines/_index.md deleted file mode 100644 index e61b8f40f1..0000000000 --- a/content/open-source/build-tools/melange/melange-pipelines/_index.md +++ /dev/null @@ -1,14 +0,0 @@ ---- -title: "melange Pipelines" -aliases: -- /open-source/melange/melange-pipelines/ -description: "Built-in melange pipelines reference" -lead: "The declarative APK builder" -type: "article" -date: 2022-11-28T08:49:15+00:00 -lastmod: 2022-11-28T08:49:15+00:00 -draft: false -images: [] ---- - -melange has several built-in pipelines to facilitate repeating common tasks. diff --git a/content/open-source/build-tools/melange/melange-pipelines/autoconf/configure.md b/content/open-source/build-tools/melange/melange-pipelines/autoconf/configure.md deleted file mode 100644 index c9387eb98b..0000000000 --- a/content/open-source/build-tools/melange/melange-pipelines/autoconf/configure.md +++ /dev/null @@ -1,40 +0,0 @@ ---- -title: "autoconf/configure" -aliases: -- /open-source/melange/melange-pipelines/autoconf/configure -type: "article" -description: "Reference docs for the autoconf/configure melange pipeline" -date: 2022-11-01T11:07:52+02:00 -lastmod: 2022-11-01T11:07:52+02:00 -draft: false -tags: ["melange", "Reference"] -images: [] -menu: - docs: - parent: "melange" -weight: 600 -toc: true ---- - - -Run the autoconf configure script - -### Dependencies -None - -### Reference -| Input | Description | -|-------|----------------------------------------------------------------------| -| `dir` | The directory containing the configure script. Default is set to `.` | - - -### Example -```yaml -- uses: autoconf/configure - with: - opts: | - PYTHON=/usr/bin/python3 \ - --with-lzma \ - --with-zlib - -``` diff --git a/content/open-source/build-tools/melange/melange-pipelines/autoconf/make-install.md b/content/open-source/build-tools/melange/melange-pipelines/autoconf/make-install.md deleted file mode 100644 index f22e1f5e5f..0000000000 --- a/content/open-source/build-tools/melange/melange-pipelines/autoconf/make-install.md +++ /dev/null @@ -1,36 +0,0 @@ ---- -title: "autoconf/make-install" -aliases: -- /open-source/melange/melange-pipelines/autoconf/make-install -type: "article" -description: "Reference docs for the autoconf/make-install melange pipeline" -date: 2022-11-01T11:07:52+02:00 -lastmod: 2022-11-01T11:07:52+02:00 -draft: false -tags: ["melange", "Reference"] -images: [] -menu: - docs: - parent: "melange" -weight: 600 -toc: true ---- - - -Run autoconf make install - -### Dependencies -- make - - -### Reference -| Input | Description | -|-------|--------------------------------------------------------------| -| `dir` | The directory containing the Makefile. Default is set to `.` | - - -### Example -```yaml -- uses: autoconf/make-install - -``` diff --git a/content/open-source/build-tools/melange/melange-pipelines/autoconf/make.md b/content/open-source/build-tools/melange/melange-pipelines/autoconf/make.md deleted file mode 100644 index e4482bf806..0000000000 --- a/content/open-source/build-tools/melange/melange-pipelines/autoconf/make.md +++ /dev/null @@ -1,37 +0,0 @@ ---- -title: "autoconf/make" -aliases: -- /open-source/melange/melange-pipelines/autoconf/make -type: "article" -description: "Reference docs for the autoconf/make melange pipeline" -date: 2022-11-01T11:07:52+02:00 -lastmod: 2022-11-01T11:07:52+02:00 -draft: false -tags: ["melange", "Reference"] -images: [] -menu: - docs: - parent: "melange" -weight: 600 -toc: true ---- - - -Run autoconf make - -### Dependencies -- make - - -### Reference -| Input | Description | -|--------|--------------------------------------------------------------| -| `dir` | The directory containing the Makefile. Default is set to `.` | -| `opts` | Options to pass to the make command. Default is set to `` | - - -### Example -```yaml -- uses: autoconf/make - -``` diff --git a/content/open-source/build-tools/melange/melange-pipelines/cmake/build.md b/content/open-source/build-tools/melange/melange-pipelines/cmake/build.md deleted file mode 100644 index f3334d2b2a..0000000000 --- a/content/open-source/build-tools/melange/melange-pipelines/cmake/build.md +++ /dev/null @@ -1,37 +0,0 @@ ---- -title: "cmake/build" -aliases: -- /open-source/melange/melange-pipelines/cmake/build -type: "article" -description: "Reference docs for the cmake/build melange pipeline" -date: 2022-11-01T11:07:52+02:00 -lastmod: 2022-11-01T11:07:52+02:00 -draft: false -tags: ["melange", "Reference"] -images: [] -menu: - docs: - parent: "melange" -weight: 600 -toc: true ---- - - -Build a CMake project - -### Dependencies -- cmake -- ninja - - -### Reference -| Input | Description | -|--------------|----------------------------------------------------------------------| -| `output-dir` | The output directory for the CMake build. Default is set to `output` | - - -### Example -```yaml -uses: cmake/build - -``` diff --git a/content/open-source/build-tools/melange/melange-pipelines/cmake/configure.md b/content/open-source/build-tools/melange/melange-pipelines/cmake/configure.md deleted file mode 100644 index 7e44f2f2e3..0000000000 --- a/content/open-source/build-tools/melange/melange-pipelines/cmake/configure.md +++ /dev/null @@ -1,38 +0,0 @@ ---- -title: "cmake/configure" -aliases: -- /open-source/melange/melange-pipelines/cmake/configure -type: "article" -description: "Reference docs for the cmake/configure melange pipeline" -date: 2022-11-01T11:07:52+02:00 -lastmod: 2022-11-01T11:07:52+02:00 -draft: false -tags: ["melange", "Reference"] -images: [] -menu: - docs: - parent: "melange" -weight: 600 -toc: true ---- - - -Configure a CMake project - -### Dependencies -- cmake -- ninja - - -### Reference -| Input | Description | -|--------------|----------------------------------------------------------------------| -| `output-dir` | The output directory for the CMake build. Default is set to `output` | -| `opts` | Compile options for the CMake build. | - - -### Example -```yaml -uses: cmake/configure - -``` diff --git a/content/open-source/build-tools/melange/melange-pipelines/cmake/install.md b/content/open-source/build-tools/melange/melange-pipelines/cmake/install.md deleted file mode 100644 index 183a68ba70..0000000000 --- a/content/open-source/build-tools/melange/melange-pipelines/cmake/install.md +++ /dev/null @@ -1,37 +0,0 @@ ---- -title: "cmake/install" -aliases: -- /open-source/melange/melange-pipelines/cmake/install -type: "article" -description: "Reference docs for the cmake/install melange pipeline" -date: 2022-11-01T11:07:52+02:00 -lastmod: 2022-11-01T11:07:52+02:00 -draft: false -tags: ["melange", "Reference"] -images: [] -menu: - docs: - parent: "melange" -weight: 600 -toc: true ---- - - -Build a CMake project - -### Dependencies -- cmake -- ninja - - -### Reference -| Input | Description | -|--------------|----------------------------------------------------------------------| -| `output-dir` | The output directory for the CMake build. Default is set to `output` | - - -### Example -```yaml -uses: cmake/install - -``` diff --git a/content/open-source/build-tools/melange/melange-pipelines/fetch.md b/content/open-source/build-tools/melange/melange-pipelines/fetch.md deleted file mode 100644 index ba2f2270fe..0000000000 --- a/content/open-source/build-tools/melange/melange-pipelines/fetch.md +++ /dev/null @@ -1,44 +0,0 @@ ---- -title: "fetch" -aliases: -- /open-source/melange/melange-pipelines/fetch -type: "article" -description: "Reference docs for the fetch melange pipeline" -date: 2022-11-01T11:07:52+02:00 -lastmod: 2022-11-01T11:07:52+02:00 -draft: false -tags: ["melange", "Reference"] -images: [] -menu: - docs: - parent: "melange" -weight: 600 -toc: true ---- - - -Fetch and extract external object into workspace - -### Dependencies -- wget - - -### Reference -| Input | Description | -|--------------------|------------------------------------------------------------------------------------------| -| `strip-components` | The number of path components to strip while extracting. Default is set to `1` | -| `extract` | Whether to extract the downloaded artifact as a source tarball. Default is set to `true` | -| `expected-sha256` | The expected SHA256 of the downloaded artifact. | -| `expected-sha512` | The expected SHA512 of the downloaded artifact. | -| `uri`* | The URI to fetch as an artifact. | - - -### Example -```yaml -pipeline: - - uses: fetch - with: - uri: https://www.php.net/distributions/php-${{package.version}}.tar.gz - expected-sha256: 3660e8408321149f5d382bb8eeb9ea7b12ea8dd7ea66069da33f6f7383750ab2 - -``` diff --git a/content/open-source/build-tools/melange/melange-pipelines/git-checkout.md b/content/open-source/build-tools/melange/melange-pipelines/git-checkout.md deleted file mode 100644 index bee4710655..0000000000 --- a/content/open-source/build-tools/melange/melange-pipelines/git-checkout.md +++ /dev/null @@ -1,42 +0,0 @@ ---- -title: "git-checkout" -aliases: -- /open-source/melange/melange-pipelines/git-checkout -type: "article" -description: "Reference docs for the git-checkout melange pipeline" -date: 2022-11-01T11:07:52+02:00 -lastmod: 2022-11-01T11:07:52+02:00 -draft: false -tags: ["melange", "Reference"] -images: [] -menu: - docs: - parent: "melange" -weight: 600 -toc: true ---- - - -Check out sources from git - -### Dependencies -- git - - -### Reference -| Input | Description | -|---------------|-------------------------------------------------------------| -| `repository`* | The repository to check out sources from. | -| `destination` | The path to check out the sources to. Default is set to `.` | -| `depth` | The depth to use when cloning. Default is set to `50` | -| `branch` | The branch to check out, otherwise HEAD is checked out. | - - -### Example -```yaml -- uses: git-checkout - with: - repository: https://github.com/envoyproxy/envoy - branch: v${{package.version}} - destination: envoy -``` diff --git a/content/open-source/build-tools/melange/melange-pipelines/go/build.md b/content/open-source/build-tools/melange/melange-pipelines/go/build.md deleted file mode 100644 index bb773b8f72..0000000000 --- a/content/open-source/build-tools/melange/melange-pipelines/go/build.md +++ /dev/null @@ -1,41 +0,0 @@ ---- -title: "go/build" -aliases: -- /open-source/melange/melange-pipelines/go/build -type: "article" -description: "Reference docs for the go/build melange pipeline" -date: 2023-04-06T11:07:52+02:0 -lastmod: 2023-04-06T11:07:52+02:0 -draft: false -tags: ["melange", "Reference"] -images: [] -menu: - docs: - parent: "melange" -weight: 600 -toc: true ---- - - -Run a build using the go compiler - -### Dependencies -- go -- busybox -- ca-certificates-bundle - - -### Reference -| Input | Description | -|---------------|--------------------------------------------------------------------------------------------------------------------------------------------------------------------| -| `packages`* | List of space-separated packages to compile. Files con also be specified.This value is passed as an argument to go build. All paths are relativeto inputs.modroot. | -| `tags` | A comma-separated list of build tags to pass to the go compiler | -| `output`* | Filename to use when writing the binary. The final install location inside the apk will be in prefix / install-dir / output | -| `modroot` | Top directory of the go module, this is where go.mod lives. Before buidingthe go pipeline wil cd into this directory. Default is set to `.` | -| `prefix` | Prefix to relocate binaries Default is set to `usr` | -| `ldflags` | List of [pattern=]arg to pass to the go compiler with -ldflags | -| `install-dir` | Directory where binaries will be installed Default is set to `bin` | - - -### Example -There are no examples available. diff --git a/content/open-source/build-tools/melange/melange-pipelines/go/install.md b/content/open-source/build-tools/melange/melange-pipelines/go/install.md deleted file mode 100644 index 38f22b31a4..0000000000 --- a/content/open-source/build-tools/melange/melange-pipelines/go/install.md +++ /dev/null @@ -1,41 +0,0 @@ ---- -title: "go/install" -aliases: -- /open-source/melange/melange-pipelines/go/install -type: "article" -description: "Reference docs for the go/install melange pipeline" -date: 2023-04-06T11:07:52+02:00 -lastmod: 2023-04-06T11:07:52+02:0 -draft: false -tags: ["melange", "Reference"] -images: [] -menu: - docs: - parent: "melange" -weight: 600 -toc: true ---- - - -Run a build using the go compiler - -### Dependencies -- go -- busybox -- ca-certificates-bundle -- git - - -### Reference -| Input | Description | -|---------------|-------------------------------------------------------------------------------------------------------------------| -| `package`* | Import path to the package | -| `version` | Package version to install. This can be a version tag (v1.0.0), a commit hash or another ref (eg latest or HEAD). | -| `prefix` | Prefix to relocate binaries Default is set to `usr` | -| `install-dir` | Directory where binaries will be installed Default is set to `bin` | -| `ldflags` | List of [pattern=]arg to pass to the go compiler with -ldflags | -| `tags` | A comma-separated list of build tags to pass to the go compiler | - - -### Example -There are no examples available. diff --git a/content/open-source/build-tools/melange/melange-pipelines/meson/compile.md b/content/open-source/build-tools/melange/melange-pipelines/meson/compile.md deleted file mode 100644 index 5a2b58183e..0000000000 --- a/content/open-source/build-tools/melange/melange-pipelines/meson/compile.md +++ /dev/null @@ -1,36 +0,0 @@ ---- -title: "meson/compile" -aliases: -- /open-source/melange/melange-pipelines/meson/compile -type: "article" -description: "Reference docs for the meson/compile melange pipeline" -date: 2022-11-01T11:07:52+02:00 -lastmod: 2022-11-01T11:07:52+02:00 -draft: false -tags: ["melange", "Reference"] -images: [] -menu: - docs: - parent: "melange" -weight: 600 -toc: true ---- - - -Compile project with meson - -### Dependencies -- meson - - -### Reference -| Input | Description | -|--------------|----------------------------------------------------------------------| -| `output-dir` | The output directory for the Meson build. Default is set to `output` | - - -### Example -```yaml -uses: meson/compile - -``` diff --git a/content/open-source/build-tools/melange/melange-pipelines/meson/configure.md b/content/open-source/build-tools/melange/melange-pipelines/meson/configure.md deleted file mode 100644 index 7395c5f9bb..0000000000 --- a/content/open-source/build-tools/melange/melange-pipelines/meson/configure.md +++ /dev/null @@ -1,37 +0,0 @@ ---- -title: "meson/configure" -aliases: -- /open-source/melange/melange-pipelines/meson/configure -type: "article" -description: "Reference docs for the meson/configure melange pipeline" -date: 2022-11-01T11:07:52+02:00 -lastmod: 2022-11-01T11:07:52+02:00 -draft: false -tags: ["melange", "Reference"] -images: [] -menu: - docs: - parent: "melange" -weight: 600 -toc: true ---- - - -Configure project with meson - -### Dependencies -- meson - - -### Reference -| Input | Description | -|--------------|----------------------------------------------------------------------| -| `output-dir` | The output directory for the Meson build. Default is set to `output` | -| `opts` | Compile options for the Meson build. | - - -### Example -```yaml -uses: meson/configure - -``` diff --git a/content/open-source/build-tools/melange/melange-pipelines/meson/install.md b/content/open-source/build-tools/melange/melange-pipelines/meson/install.md deleted file mode 100644 index 98e40573a5..0000000000 --- a/content/open-source/build-tools/melange/melange-pipelines/meson/install.md +++ /dev/null @@ -1,36 +0,0 @@ ---- -title: "meson/install" -aliases: -- /open-source/melange/melange-pipelines/meson/install -type: "article" -description: "Reference docs for the meson/install melange pipeline" -date: 2022-11-01T11:07:52+02:00 -lastmod: 2022-11-01T11:07:52+02:00 -draft: false -tags: ["melange", "Reference"] -images: [] -menu: - docs: - parent: "melange" -weight: 600 -toc: true ---- - - -Install project with meson - -### Dependencies -- meson - - -### Reference -| Input | Description | -|--------------|----------------------------------------------------------------------| -| `output-dir` | The output directory for the Meson build. Default is set to `output` | - - -### Example -```yaml -uses: meson/install - -``` diff --git a/content/open-source/build-tools/melange/melange-pipelines/patch.md b/content/open-source/build-tools/melange/melange-pipelines/patch.md deleted file mode 100644 index 82118850a3..0000000000 --- a/content/open-source/build-tools/melange/melange-pipelines/patch.md +++ /dev/null @@ -1,38 +0,0 @@ ---- -title: "patch" -aliases: -- /open-source/melange/melange-pipelines/patch -type: "article" -description: "Reference docs for the patch melange pipeline" -date: 2022-11-01T11:07:52+02:00 -lastmod: 2022-11-01T11:07:52+02:00 -draft: false -tags: ["melange", "Reference"] -images: [] -menu: - docs: - parent: "melange" -weight: 600 -toc: true ---- - - -Apply patches - -### Dependencies -- patch - - -### Reference -| Input | Description | -|--------------------|--------------------------------------------------------------------------------| -| `strip-components` | The number of path components to strip while extracting. Default is set to `1` | -| `patches`* | A list of patches to apply, as a whitespace delimited string. | - - -### Example -```yaml -- uses: patch - with: - patches: libtool-fix-cross-compile.patch -``` diff --git a/content/open-source/build-tools/melange/melange-pipelines/ruby/build.md b/content/open-source/build-tools/melange/melange-pipelines/ruby/build.md deleted file mode 100644 index 56aa18ef53..0000000000 --- a/content/open-source/build-tools/melange/melange-pipelines/ruby/build.md +++ /dev/null @@ -1,36 +0,0 @@ ---- -title: "ruby/build" -aliases: -- /open-source/melange/melange-pipelines/ruby/build -type: "article" -description: "Reference docs for the ruby/build melange pipeline" -date: 2023-04-06T11:07:52+02:0 -lastmod: 2023-04-06T11:07:52+02:0 -draft: false -tags: ["melange", "Reference"] -images: [] -menu: - docs: - parent: "melange" -weight: 600 -toc: true ---- - - -Build a ruby gem - -### Dependencies -- busybox -- ca-certificates-bundle - - -### Reference -| Input | Description | -|----------|------------------------------| -| `gem`* | Gem name | -| `output` | Gem output filename | -| `opts` | Options to pass to gem build | - - -### Example -There are no examples available. diff --git a/content/open-source/build-tools/melange/melange-pipelines/ruby/clean.md b/content/open-source/build-tools/melange/melange-pipelines/ruby/clean.md deleted file mode 100644 index 1d804b0a9c..0000000000 --- a/content/open-source/build-tools/melange/melange-pipelines/ruby/clean.md +++ /dev/null @@ -1,31 +0,0 @@ ---- -title: "ruby/clean" -aliases: -- /open-source/melange/melange-pipelines/ruby/clean -type: "article" -description: "Reference docs for the ruby/clean melange pipeline" -date: 2023-04-06T11:07:52+02:0 -lastmod: 2023-04-06T11:07:52+02:0 -draft: false -tags: ["melange", "Reference"] -images: [] -menu: - docs: - parent: "melange" -weight: 600 -toc: true ---- - - -Clean a ruby gem - -### Dependencies -- busybox -- ca-certificates-bundle - - -### Reference -This pipeline doesn't expect any input arguments. - -### Example -There are no examples available. diff --git a/content/open-source/build-tools/melange/melange-pipelines/ruby/install.md b/content/open-source/build-tools/melange/melange-pipelines/ruby/install.md deleted file mode 100644 index 9ed3ed6021..0000000000 --- a/content/open-source/build-tools/melange/melange-pipelines/ruby/install.md +++ /dev/null @@ -1,37 +0,0 @@ ---- -title: "ruby/install" -aliases: -- /open-source/melange/melange-pipelines/autoconf/configure -type: "article" -description: "Reference docs for the ruby/install melange pipeline" -date: 2023-04-06T11:07:52+02:0 -lastmod: 2023-04-06T11:07:52+02:0 -draft: false -tags: ["melange", "Reference"] -images: [] -menu: - docs: - parent: "melange" -weight: 600 -toc: true ---- - - -Install a ruby gem - -### Dependencies -- busybox -- ca-certificates-bundle - - -### Reference -| Input | Description | -|------------|-----------------------------------------------------------------| -| `gem` | Gem name | -| `gem-file` | The full filename of the gem to build | -| `version`* | Gem version to install. This can be a version tag (1.0.0) | -| `opts` | Options to pass to the gem install command Default is set to `` | - - -### Example -There are no examples available. diff --git a/content/open-source/build-tools/melange/melange-pipelines/split/dev.md b/content/open-source/build-tools/melange/melange-pipelines/split/dev.md deleted file mode 100644 index 569da1fa31..0000000000 --- a/content/open-source/build-tools/melange/melange-pipelines/split/dev.md +++ /dev/null @@ -1,32 +0,0 @@ ---- -title: "split/dev" -aliases: -- /open-source/melange/melange-pipelines/split/dev -type: "article" -description: "Reference docs for the split/dev melange pipeline" -date: 2022-11-01T11:07:52+02:00 -lastmod: 2022-11-01T11:07:52+02:00 -draft: false -tags: ["melange", "Reference"] -images: [] -menu: - docs: - parent: "melange" -weight: 600 -toc: true ---- - - -Split development files - -### Dependencies -None - -### Reference -This pipeline doesn't expect any input arguments. - -### Example -```yaml -uses: split/dev - -``` diff --git a/content/open-source/build-tools/melange/melange-pipelines/split/infodir.md b/content/open-source/build-tools/melange/melange-pipelines/split/infodir.md deleted file mode 100644 index f61fc7e3cc..0000000000 --- a/content/open-source/build-tools/melange/melange-pipelines/split/infodir.md +++ /dev/null @@ -1,32 +0,0 @@ ---- -title: "split/infodir" -aliases: -- /open-source/melange/melange-pipelines/split/infodir -type: "article" -description: "Reference docs for the split/infodir melange pipeline" -date: 2022-11-01T11:07:52+02:00 -lastmod: 2022-11-01T11:07:52+02:00 -draft: false -tags: ["melange", "Reference"] -images: [] -menu: - docs: - parent: "melange" -weight: 600 -toc: true ---- - - -Split GNU info pages - -### Dependencies -None - -### Reference -This pipeline doesn't expect any input arguments. - -### Example -```yaml -uses: split/infodir - -``` diff --git a/content/open-source/build-tools/melange/melange-pipelines/split/locales.md b/content/open-source/build-tools/melange/melange-pipelines/split/locales.md deleted file mode 100644 index 510a70abc7..0000000000 --- a/content/open-source/build-tools/melange/melange-pipelines/split/locales.md +++ /dev/null @@ -1,32 +0,0 @@ ---- -title: "split/locales" -aliases: -- /open-source/melange/melange-pipelines/split/locales -type: "article" -description: "Reference docs for the split/locales melange pipeline" -date: 2022-11-01T11:07:52+02:00 -lastmod: 2022-11-01T11:07:52+02:00 -draft: false -tags: ["melange", "Reference"] -images: [] -menu: - docs: - parent: "melange" -weight: 600 -toc: true ---- - - -Split locales - -### Dependencies -None - -### Reference -This pipeline doesn't expect any input arguments. - -### Example -```yaml -uses: split/locales - -``` diff --git a/content/open-source/build-tools/melange/melange-pipelines/split/manpages.md b/content/open-source/build-tools/melange/melange-pipelines/split/manpages.md deleted file mode 100644 index a86c7755cd..0000000000 --- a/content/open-source/build-tools/melange/melange-pipelines/split/manpages.md +++ /dev/null @@ -1,32 +0,0 @@ ---- -title: "split/manpages" -aliases: -- /open-source/melange/melange-pipelines/split/manpages -type: "article" -description: "Reference docs for the split/manpages melange pipeline" -date: 2022-11-01T11:07:52+02:00 -lastmod: 2022-11-01T11:07:52+02:00 -draft: false -tags: ["melange", "Reference"] -images: [] -menu: - docs: - parent: "melange" -weight: 600 -toc: true ---- - - -Split manpages - -### Dependencies -None - -### Reference -This pipeline doesn't expect any input arguments. - -### Example -```yaml -uses: split/manpages - -``` diff --git a/content/open-source/build-tools/melange/melange-pipelines/split/static.md b/content/open-source/build-tools/melange/melange-pipelines/split/static.md deleted file mode 100644 index bde312fdf1..0000000000 --- a/content/open-source/build-tools/melange/melange-pipelines/split/static.md +++ /dev/null @@ -1,32 +0,0 @@ ---- -title: "split/static" -aliases: -- /open-source/melange/melange-pipelines/split/static -type: "article" -description: "Reference docs for the split/static melange pipeline" -date: 2022-11-01T11:07:52+02:00 -lastmod: 2022-11-01T11:07:52+02:00 -draft: false -tags: ["melange", "Reference"] -images: [] -menu: - docs: - parent: "melange" -weight: 600 -toc: true ---- - - -Split static library files - -### Dependencies -None - -### Reference -This pipeline doesn't expect any input arguments. - -### Example -```yaml -uses: split/static - -``` diff --git a/content/open-source/build-tools/melange/melange-pipelines/strip.md b/content/open-source/build-tools/melange/melange-pipelines/strip.md deleted file mode 100644 index 15ab8292a7..0000000000 --- a/content/open-source/build-tools/melange/melange-pipelines/strip.md +++ /dev/null @@ -1,33 +0,0 @@ ---- -title: "strip" -aliases: -- /open-source/melange/melange-pipelines/strip -type: "article" -description: "Reference docs for the strip melange pipeline" -date: 2022-11-01T11:07:52+02:00 -lastmod: 2022-11-01T11:07:52+02:00 -draft: false -tags: ["melange", "Reference"] -images: [] -menu: - docs: - parent: "melange" -weight: 600 -toc: true ---- - - -Strip binaries - -### Dependencies -- binutils -- scanelf - - -### Reference -This pipeline doesn't expect any input arguments. - -### Example -```yaml -uses: strip -``` diff --git a/content/open-source/build-tools/melange/overview/apko_melange_ecosystem.png b/content/open-source/build-tools/melange/overview/apko_melange_ecosystem.png deleted file mode 100644 index 2f006c792e..0000000000 Binary files a/content/open-source/build-tools/melange/overview/apko_melange_ecosystem.png and /dev/null differ diff --git a/content/open-source/build-tools/melange/overview/index.md b/content/open-source/build-tools/melange/overview/index.md deleted file mode 100644 index 732380ed32..0000000000 --- a/content/open-source/build-tools/melange/overview/index.md +++ /dev/null @@ -1,32 +0,0 @@ ---- -title: "melange Overview" -aliases: -- /open-source/melange/overview -type: "article" -description: "melange Overview" -date: 2022-10-17T11:07:52+02:00 -lastmod: 2024-05-02T11:07:52+02:00 -draft: false -tags: ["melange", "Overview"] -images: [] -menu: - docs: - parent: "melange" -weight: 10 -toc: true ---- -[melange](https://github.com/chainguard-dev/melange) is an [apk](https://wiki.alpinelinux.org/wiki/Package_management) builder tool that uses declarative pipelines to create apk packages. It is part of the open source tooling used for [Wolfi](/open-source/wolfi), which is the operating system used to power [Chainguard Images](/chainguard/chainguard-images). - -From a single YAML file, users are able to generate multi-architecture apks that can be injected directly into [apko](https://github.com/chainguard-dev/apko) builds. This renders apko and melange a [good combination for container image factories](https://blog.chainguard.dev/secure-your-software-factory-with-melange-and-apko/). - -The following diagram contains an overview of the apko and melange ecosystem and how they work together to compose apk-based images, using either Alpine or Wolfi as base system. - -![The diagram shows an overview of the apko and melange ecosystem and their relationships. melange apks can be used to compose both Alpine-based and Wolfi-based container images using apko.](apko_melange_ecosystem.png) - -melange offers the following features: - -- **Fully reproducible by default.** Run melange twice and you will get exactly the same binary. -- **Pipeline-oriented builds.** Every step of the build pipeline is defined and controlled by you, unlike traditional package managers which have distinct phases. -- **Multi-architecture by default.** QEMU is used to emulate various architectures, avoiding the need for cross-compilation steps. - -apko and [melange](/open-source/melange) are part of the open source toolkit developed by Chainguard to build [Wolfi](/open-source/wolfi) and [Chainguard Images](/chainguard/chainguard-images). diff --git a/content/open-source/build-tools/melange/reference.md b/content/open-source/build-tools/melange/reference.md deleted file mode 100644 index 8b5ee630a2..0000000000 --- a/content/open-source/build-tools/melange/reference.md +++ /dev/null @@ -1,122 +0,0 @@ ---- -title: "melange YAML Reference" -aliases: -- /open-source/melange/reference -type: "article" -description: "A reference guide for writing YAML for melange" -date: 2022-10-17T11:07:52+02:00 -lastmod: 2022-10-17T11:07:52+02:00 -draft: false -tags: ["melange", "Reference"] -images: [] -menu: - docs: - parent: "melange" -weight: 150 -toc: true ---- - -This page provides a reference for melange's YAML specification. - -## package -This section defines metadata about the apk package being built. - - -| Directive | Expects | -|-----------------------|--------------------------------------------------------------------------------------------------------------------------------------------| -| `name` | (String) Name of the package. | -| `version` | (String) Version of the package. | -| `epoch` | (String) Useful to force the package to be seen as newer than any previous version with a lower epoch. | -| `description` | (String) A description of the package. | -| `target-architecture` | (Array) Architectures for which the package will be built. Use 'all' for all available architectures. | -| `copyright` | (Array) License and copyright information. | -| `dependencies` | (Array) List of runtime dependencies for this package. These will get pulled via apk as system dependencies when the package is installed. | - -#### Example - -```yaml -package: - name: hello - version: 2.12 - epoch: 0 - description: 'the GNU hello world program' - target-architecture: - - all - copyright: - - paths: - - '*' - attestation: | - Copyright 1992, 1995, 1996, 1997, 1998, 1999, 2000, 2001, 2002, 2005, - 2006, 2007, 2008, 2010, 2011, 2013, 2014, 2022 Free Software Foundation, - Inc. - license: GPL-3.0-or-later - dependencies: - runtime: - -``` - -## environment -This section defines the build environment, specifying dependencies that need to be present at build time. - -| Directive | Expects | -|------------|----------------------------------------------------------------------------------------------------------------------------------| -| `contents` | (Array) Defines the packages that will be installed for running the build pipeline, and the repositories where to download them. | - -#### Example - -```yaml -environment: - contents: - repositories: - - 'https://dl-cdn.alpinelinux.org/alpine/edge/main' - packages: - - alpine-baselayout-data - - busybox - - build-base - - scanelf - - ssl_client - - ca-certificates-bundle - -``` -_NOTE: do not mix Alpine apk repositories with Wolfi apk repositories when defining your software sources._ - -## pipeline -Defines the build steps. - -| Directive | Expects | -|-----------|---------------------------------------------------| -| `uses` | (String) Uses a built-in pipeline. | -| `with` | (Array) Provide parameters to a "uses" directive. | - -#### Example - -```yaml -- uses: fetch - with: - uri: https://ftp.gnu.org/gnu/hello/hello-${{package.version}}.tar.gz - expected-sha256: cf04af86dc085268c5f4470fbae49b18afbc221b78096aab842d934a76bad0ab -- uses: autoconf/configure -- uses: autoconf/make -- uses: autoconf/make-install -- uses: strip - -``` -## subpackages -Creates subpackages for documentation and additional (dev) headers, which may not be necessary at runtime. - - -| Directive | Expects | -|------------|----------| -| `name` | (String) | -| `pipeline` | (Array) | - - -#### Example - -```yaml -subpackages: - - name: hello-doc - pipeline: - - uses: split/manpages - -``` diff --git a/content/open-source/build-tools/melange/troubleshooting.md b/content/open-source/build-tools/melange/troubleshooting.md deleted file mode 100644 index c5119df1b2..0000000000 --- a/content/open-source/build-tools/melange/troubleshooting.md +++ /dev/null @@ -1,62 +0,0 @@ ---- -title: "Troubleshooting melange Builds" -aliases: -- /open-source/melange/troubleshooting -linktitle: "Troubleshooting Builds" -type: "article" -lead: "Debugging and common errors" -description: "Debugging and common errors with melange build" -date: 2022-08-10T11:07:52+02:00 -lastmod: 2022-08-10T11:07:52+02:00 -contributors: ["Erika Heidi"] -draft: false -tags: ["melange", "Troubleshooting"] -images: [] -menu: -docs: - parent: "melange" -weight: 200 -toc: true ---- - -## Debug Options -To include debug-level information on melange builds, edit your `melange.yaml` file and include `set -x` in your pipeline. You can add this flag at any point of your pipeline commands to further debug a specific section of your build. - -```yaml -... -pipeline: - - name: Build Minicli application - runs: | - set -x - APP_HOME="${{targets.destdir}}/usr/share/hello-minicli" -... -``` -## Common Errors - -When melange is unable to finish a build successfully, you will get an error similar to this: - -{{< alert context="danger" text="Error: failed to build package: unable to run pipeline: exit status 127" />}} - -The build could not be completed due to an error at some point of your pipeline. Enable debug by including `set -x` at the beginning of your build pipeline so that you can nail down where the issue occurs. - -### Missing QEMU user-space emulation packages - -Linux users using the Docker melange image may get errors when building packages for other architectures than `x86` and `x86_64`. This won't happen for Docker Desktop users, since the additional architectures are automatically enabled upon installation. - -To enable additional architectures, you'll need to enable them within your kernel with the following command: - -```shell -docker run --rm --privileged multiarch/qemu-user-static --reset -p yes -``` - -An alternate approach to achieve the same result is to run the following command: - -```shell -docker run --privileged --rm tonistiigi/binfmt --install all -``` - -### Missing build-time dependencies -You may get errors from missing build-time dependences such as `busybox`. In this case you may get "No such file or directory" errors when enabling debug with `set -x`. To fix this, you'll need to locate which package has the commands that your build needs, and add it to the list of your build-time dependencies. -## Further Resources - -For additional guidance, please refer to the [melange repository](https://github.com/chainguard-dev/melange) on GitHub, where you can find [more examples](https://github.com/chainguard-dev/melange/tree/main/examples) or [open an issue](https://github.com/chainguard-dev/melange/issues/new/choose) in case of problems. diff --git a/content/open-source/oci/what-is-the-oci.md b/content/open-source/oci/what-is-the-oci.md index 55df6bac10..aa7021f19b 100644 --- a/content/open-source/oci/what-is-the-oci.md +++ b/content/open-source/oci/what-is-the-oci.md @@ -14,31 +14,31 @@ menu: weight: 100 toc: true --- -The [Open Container Initiative](https://opencontainers.org/) (OCI) is a Linux Foundation project dedicated to managing specifications and projects related to the storage, distribution, and execution of container images. The OCI was formed in 2015 when developers recognized that the quickly growing container industry needed standards to ensure the portability of containers across systems and platforms. As one of the most popular container developers, Docker was a key partner in the formation of the OCI and donated its specifications and associated code for OCI image formats and runtime specifications. Today, the OCI manages three specifications (the Image Specification, the Runtime Specification, and the Distribution Specification), which are evolving according to community participation and industry development. +The [Open Container Initiative](https://opencontainers.org/) (OCI) is a Linux Foundation project dedicated to managing specifications and projects related to the storage, distribution, and execution of container images. The OCI was formed in 2015 when developers recognized that the quickly growing container industry needed standards to ensure the portability of containers across systems and platforms. As one of the most popular container developers, Docker was a key partner in the formation of the OCI and donated its specifications and associated code for OCI image formats and runtime specifications. Today, the OCI manages three specifications (the Image Specification, the Runtime Specification, and the Distribution Specification), which are evolving according to community participation and industry development. -The OCI is committed to promoting common, minimal, and open standards and specifications with the aim of protecting interoperability without sacrificing developers’ ability to innovate. These standards and specifications play a critical role in enabling developers to trust that their containers will work regardless of the infrastructure, cloud provider, and DevOps tooling they choose to use. They also are vital in modern software supply chain security as they provide a strong foundation for developing security tooling and best practices related to container technology. Understanding the purpose and use of OCI specifications can help you understand the conditions of container interoperability and prepare you to learn emerging methods for securing and trusting container applications. +The OCI is committed to promoting common, minimal, and open standards and specifications with the aim of protecting interoperability without sacrificing developers’ ability to innovate. These standards and specifications play a critical role in enabling developers to trust that their containers will work regardless of the infrastructure, cloud provider, and DevOps tooling they choose to use. They also are vital in modern software supply chain security as they provide a strong foundation for developing security tooling and best practices related to container technology. Understanding the purpose and use of OCI specifications can help you understand the conditions of container interoperability and prepare you to learn emerging methods for securing and trusting container applications. -## What are the OCI Specifications? +## What are the OCI Specifications? -The OCI currently manages three specifications: the Runtime Specification, the Image Specification, and the Distribution Specification. These specifications work together to ensure that any OCI-compliant image can be run on any OCI-compliant runtime, and that OCI-compliant registries (such as Docker, Amazon Elastic Container Registry, or Google Container Registry) are able to distribute OCI images according to OCI guidelines. +The OCI currently manages three specifications: the Runtime Specification, the Image Specification, and the Distribution Specification. These specifications work together to ensure that any OCI-compliant image can be run on any OCI-compliant runtime, and that OCI-compliant registries (such as Docker, Amazon Elastic Container Registry, or Google Container Registry) are able to distribute OCI images according to OCI guidelines. The OCI offers a testing and peer validation process for individuals and organizations to certify their images or runtime software as OCI compliant. You can find information about the certification process on the [OCI website](https://opencontainers.org/community/certified/). -The three OCI specifications are outlined in the following sections. +The three OCI specifications are outlined in the following sections. ## OCI Image Format Specification -This specification defines an OCI Image as consisting of an image manifest, an optional image index, a set of filesystem layers, and a configuration. +This specification defines an OCI Image as consisting of an image manifest, an optional image index, a set of filesystem layers, and a configuration. ### Image manifest This document provides a configuration and set of layers for a single container image for a specific architecture and operating system. Note that the manifest specification has three goals: -* Enabling _content-addressable_ images, which means an image can be referred to by a unique ID — or digital fingerprint — that is generated by hashing its contents. Hashing is generated using the SHA256 algorithm, which generates a unique 32-byte signature for an image based on the contents of the image. Changing even one byte on the original image would result in a different hash, enabling developers to know with certainty that an image has not been altered. -* Allowing _multi-architecture_ images, or container images that can be used with different architectures such as AMD64 and ARM. Multi-architecture images enable a flexible approach to developing a container-based application or setting up CI/CD workflows without needing to commit to a specific architecture. +* Enabling _content-addressable_ images, which means an image can be referred to by a unique ID — or digital fingerprint — that is generated by hashing its contents. Hashing is generated using the SHA256 algorithm, which generates a unique 32-byte signature for an image based on the contents of the image. Changing even one byte on the original image would result in a different hash, enabling developers to know with certainty that an image has not been altered. +* Allowing _multi-architecture_ images, or container images that can be used with different architectures such as AMD64 and ARM. Multi-architecture images enable a flexible approach to developing a container-based application or setting up CI/CD workflows without needing to commit to a specific architecture. * Ensuring that images are compatible with any OCI-compliant runtime. -For an example manifest document and a list of properties, you can read the [OCI’s Image Manifest Specifications](https://github.com/opencontainers/image-spec/blob/main/manifest.md). +For an example manifest document and a list of properties, you can read the [OCI’s Image Manifest Specifications](https://github.com/opencontainers/image-spec/blob/main/manifest.md). ### Image index (optional) @@ -46,7 +46,7 @@ This document is an optional higher-level manifest which allows developers to po ### A set of filesystem layers -An image is composed of one or more _filesystem layers_, each of which represent a change to the file system such as the addition of another image or one or more commands. These layers are unpacked by the container engine to build the image and are referred to by their `digest`, a hash generated by applying the SHA 256 algorithm to their contents. Layers are described in the image manifest as follows: +An image is composed of one or more _filesystem layers_, each of which represent a change to the file system such as the addition of another image or one or more commands. These layers are unpacked by the container engine to build the image and are referred to by their `digest`, a hash generated by applying the SHA 256 algorithm to their contents. Layers are described in the image manifest as follows: ```json "layers": [ @@ -58,11 +58,11 @@ An image is composed of one or more _filesystem layers_, each of which represent ] ``` -For OCI guidance on filesystem layers, you can visit their [Image Layer Filesystem Changeset Documentation](https://github.com/opencontainers/image-spec/blob/main/layer.md). +For OCI guidance on filesystem layers, you can visit their [Image Layer Filesystem Changeset Documentation](https://github.com/opencontainers/image-spec/blob/main/layer.md). -### Configuration +### Configuration -The configuration document includes basic information like the author and creation date and describes execution parameters for translating the image to a container runtime. The configuration file is named after its cryptographic hash and can be located in the manifest as follows: +The configuration document includes basic information like the author and creation date and describes execution parameters for translating the image to a container runtime. The configuration file is named after its cryptographic hash and can be located in the manifest as follows: ```json { @@ -75,17 +75,17 @@ The configuration document includes basic information like the author and creati }, ``` -For more guidance on image configuration, visit the [official OCI documentation](https://github.com/opencontainers/image-spec/blob/main/config.md). +For more guidance on image configuration, visit the [official OCI documentation](https://github.com/opencontainers/image-spec/blob/main/config.md). -## Runtime Specification +## Runtime Specification -A container runtime is the software used to run and manage containers; essentially they create and run containers using specified images. The goal of the OCI Runtime Specification is to ensure consistency between different runtime environments and define common actions to manage a container’s lifecycle. An OCI-compliant image should run reliably on any OCI-compliant runtime. More information about the Runtime Specification can be found in the [OCI documentation](https://github.com/opencontainers/runtime-spec/blob/main/spec.md). +A container runtime is the software used to run and manage containers; essentially they create and run containers using specified images. The goal of the OCI Runtime Specification is to ensure consistency between different runtime environments and define common actions to manage a container’s lifecycle. An OCI-compliant image should run reliably on any OCI-compliant runtime. More information about the Runtime Specification can be found in the [OCI documentation](https://github.com/opencontainers/runtime-spec/blob/main/spec.md). -In addition to overseeing this specification, OCI develops the runtime `runc`, a command line client for creating, configuring, and managing containers. Originally developed by Docker, `runc` was donated to OCI as the reference for the specification and serves as the foundation for a variety of popular container tools such as containerd and Podman. +In addition to overseeing this specification, OCI develops the runtime `runc`, a command line client for creating, configuring, and managing containers. Originally developed by Docker, `runc` was donated to OCI as the reference for the specification and serves as the foundation for a variety of popular container tools such as containerd and Podman. ## Distribution Specification -The OCI Distribution Specification aims to standardize the way container registries and runtime tools push and pull container images and other content types. It is based on the specification for the Docker Registry HTTP API V2 protocol apdx-1, and has been adopted by major registries such as Amazon Elastic Container Registry, Google Container Registry, Azure Container Registry, and Github Container Registry. Any registry that is OCI-compliant supports interactions outlined by this specification, such as pushing, pulling, or storing images. More information about the Distribution Specification can be found in the OCI documentation [here](https://github.com/opencontainers/distribution-spec/blob/main/spec.md). +The OCI Distribution Specification aims to standardize the way container registries and runtime tools push and pull container images and other content types. It is based on the specification for the Docker Registry HTTP API V2 protocol apdx-1, and has been adopted by major registries such as Amazon Elastic Container Registry, Google Container Registry, Azure Container Registry, and Github Container Registry. Any registry that is OCI-compliant supports interactions outlined by this specification, such as pushing, pulling, or storing images. More information about the Distribution Specification can be found in the OCI documentation [here](https://github.com/opencontainers/distribution-spec/blob/main/spec.md). ## How to know if an image is OCI compliant @@ -95,18 +95,18 @@ Currently, most images encountered in the wild are either OCI or Docker images. "mediaType": "application/vnd.oci.image.manifest.v1+json", ``` -Otherwise, the mediatype string will likely include “docker” as follows: +Otherwise, the mediatype string will likely include “docker” as follows: -```json +```json "mediaType": "application/vnd.docker.distribution.manifest.v2+json" ``` -There are a few interesting nuances about OCI images that are worth pointing out. First, because Docker donated its image specifications to OCI, Docker and OCI image specifications are the same in substance. In fact, most images on Docker are _Docker_ images and not OCI images, which you can confirm by inspecting the image manifests. This is largely due to the fact that Docker’s tools for publishing and building images create _Docker_ images – not _OCI_ images — by default, a convention set by historical practice. If you want to build and publish OCI images, you must use tools that support OCI, such as [apko](/open-source/apko/overview/), an open source OCI image builder. +There are a few interesting nuances about OCI images that are worth pointing out. First, because Docker donated its image specifications to OCI, Docker and OCI image specifications are the same in substance. In fact, most images on Docker are _Docker_ images and not OCI images, which you can confirm by inspecting the image manifests. This is largely due to the fact that Docker’s tools for publishing and building images create _Docker_ images – not _OCI_ images — by default, a convention set by historical practice. If you want to build and publish OCI images, you must use tools that support OCI, such as [apko](https://github.com/chainguard-dev/apko), an open source OCI image builder. -Relatedly, a final nuance to point out is that OCI-compliant registries are only required to _support_ OCI images, but may distribute other image types as well. Thus, you should not expect all images distributed on an OCI-compliant registry to be OCI compliant themselves, such as evidenced by Docker Hub in the example above. +Relatedly, a final nuance to point out is that OCI-compliant registries are only required to _support_ OCI images, but may distribute other image types as well. Thus, you should not expect all images distributed on an OCI-compliant registry to be OCI compliant themselves, such as evidenced by Docker Hub in the example above. ## Wrap up -You should now understand the purpose of OCI and the three container specifications it oversees. While the OCI’s core function is protecting interoperability across the complex container ecosystem, its protocols are being recognized as useful for _signing_ software, a method for authenticating that the software is from a trusted source and has not been tampered with by a third party. You can learn more about container signing and how to sign, verify, and store image artifacts in an OCI registry in our [introductory guide to Cosign](/open-source/sigstore/cosign/an-introduction-to-cosign/). +You should now understand the purpose of OCI and the three container specifications it oversees. While the OCI’s core function is protecting interoperability across the complex container ecosystem, its protocols are being recognized as useful for _signing_ software, a method for authenticating that the software is from a trusted source and has not been tampered with by a third party. You can learn more about container signing and how to sign, verify, and store image artifacts in an OCI registry in our [introductory guide to Cosign](/open-source/sigstore/cosign/an-introduction-to-cosign/). diff --git a/content/open-source/sbom/sboms-and-attestations.md b/content/open-source/sbom/sboms-and-attestations.md index 99b92ddca8..7f55a1b49a 100644 --- a/content/open-source/sbom/sboms-and-attestations.md +++ b/content/open-source/sbom/sboms-and-attestations.md @@ -67,4 +67,4 @@ There are many tools available today — both proprietary and open source — th For example, SBOMs generated from source code can be valuable. But ultimately, you have no way of knowing whether the image has been tampered with between the time the SBOM was generated and the time you actually run the image. -[apko](/open-source/apko/overview/) is a command-line tool that allows users to build container images using a declarative language based on YAML. When building a container image, apko will generate an SBOM outlining each of the apks it uses to build it. When combined with [melange](/open-source/melange/overview/), an apk builder tool that uses declarative pipelines to create apk packages, these tools can serve as a good starting point for a secure container image factory. Checkout ["Secure Your Software Factory with melange and apko"](https://www.chainguard.dev/unchained/secure-your-software-factory-with-melange-and-apko) to learn more. +[apko](https://github.com/chainguard-dev/apko) is a command-line tool that allows users to build container images using a declarative language based on YAML. When building a container image, apko will generate an SBOM outlining each of the apks it uses to build it. When combined with [melange](https://github.com/chainguard-dev/melange), an apk builder tool that uses declarative pipelines to create apk packages, these tools can serve as a good starting point for a secure container image factory. Checkout ["Secure Your Software Factory with melange and apko"](https://www.chainguard.dev/unchained/secure-your-software-factory-with-melange-and-apko) to learn more. diff --git a/content/open-source/sigstore/cosign/how-to-verify-file-signatures-with-cosign.md b/content/open-source/sigstore/cosign/how-to-verify-file-signatures-with-cosign.md index c2a3248dd6..87b1a7e38e 100644 --- a/content/open-source/sigstore/cosign/how-to-verify-file-signatures-with-cosign.md +++ b/content/open-source/sigstore/cosign/how-to-verify-file-signatures-with-cosign.md @@ -17,7 +17,7 @@ toc: true Cosign can be used to verify file signatures as these are binary artifacts, as long as these are published to an OCI registry. This tutorial assumes you have Cosign installed, which you can achieve by following our [How to Install Cosign guide](/open-source/sigstore/cosign/how-to-sign-a-container-with-cosign/). -We’ll verify a binary artifact, in this case, a copy of [`apko`](/open-source/apko/overview/), which is a command-line tool for building container images using a declarative language based on YAML. The methods in this tutorial apply to any blob file Cosign has signed with a keyless signature. +We’ll verify a binary artifact, in this case, a copy of [`apko`](https://github.com/chainguard-dev/apko), which is a command-line tool for building container images using a declarative language based on YAML. The methods in this tutorial apply to any blob file Cosign has signed with a keyless signature. ### Verifying a binary with Cosign keyless signatures diff --git a/content/open-source/sigstore/rekor/how-to-verify-file-signatures-with-rekor-or-curl.md b/content/open-source/sigstore/rekor/how-to-verify-file-signatures-with-rekor-or-curl.md index 8c54520ea9..28920d1349 100644 --- a/content/open-source/sigstore/rekor/how-to-verify-file-signatures-with-rekor-or-curl.md +++ b/content/open-source/sigstore/rekor/how-to-verify-file-signatures-with-rekor-or-curl.md @@ -17,7 +17,7 @@ toc: true The `rekor-cli` tool or `curl` can be used to verify anything with a signature on a [Rekor transparency log](/open-source/sigstore/rekor/an-introduction-to-rekor/#transparency-log). This tutorial assumes you have the `rekor-cli` tool installed, which you can achieve by following our [How to Install the Rekor CLI](/open-source/sigstore/rekor/how-to-install-rekor/) guide. When verifying a signature using either tool, ensure that you have the `jq` utility installed so that you can parse their output. -We’ll verify a binary artifact, in this case, a copy of [apko](/open-source/apko/overview/), which is a tool for building container images using a declarative language based on YAML. The methods in this tutorial apply to any blob file that Cosign has signed with a keyless signature. +We’ll verify a binary artifact, in this case, a copy of [apko](https://github.com/chainguard-dev/apko), which is a tool for building container images using a declarative language based on YAML. The methods in this tutorial apply to any blob file that Cosign has signed with a keyless signature. ### Verifying a binary with rekor-cli @@ -83,7 +83,7 @@ If you are using `curl` then run this command: curl -X GET "https://rekor.sigstore.dev/api/v1/log/entries/${UUID?}" ``` -In both cases, if you would like to extract the signature and public key to verify your binary matches what is in the Rekor log, you will need to parse the output. You will need to use tools like `base64` to decode the data, `jq` to extract the relevant fields, and `openssl` to verify the signature. +In both cases, if you would like to extract the signature and public key to verify your binary matches what is in the Rekor log, you will need to parse the output. You will need to use tools like `base64` to decode the data, `jq` to extract the relevant fields, and `openssl` to verify the signature. ##### Fetch a signature and public certificate using `rekor-cli` diff --git a/content/open-source/wolfi/apk-package-manager.md b/content/open-source/wolfi/apk-package-manager.md index 0be5147581..757ee7174b 100644 --- a/content/open-source/wolfi/apk-package-manager.md +++ b/content/open-source/wolfi/apk-package-manager.md @@ -16,7 +16,7 @@ weight: 400 toc: true --- -[apko](/open-source/apko/getting-started-with-apko/) uses the [apk](https://wiki.alpinelinux.org/wiki/Package_management) package manager to compose container images based on declarative pipelines. +[apko](https://github.com/chainguard-dev/apko) uses the [apk](https://wiki.alpinelinux.org/wiki/Package_management) package manager to compose container images based on declarative pipelines. The apk format was introduced by [Alpine Linux](https://www.alpinelinux.org/) to address specific design requirements that could not be met by existing package managers such as `apt` and `dnf`. But what makes it different, and why does that matter in the context of apko? ## Manipulating the Desired State diff --git a/content/open-source/wolfi/building-a-wolfi-package.md b/content/open-source/wolfi/building-a-wolfi-package.md index 9e2590e164..5e584c9bc5 100644 --- a/content/open-source/wolfi/building-a-wolfi-package.md +++ b/content/open-source/wolfi/building-a-wolfi-package.md @@ -176,7 +176,7 @@ As indicated, a pipeline step will have either a `uses` or a `run` directive. Yo - `${{targets.destdir}}`: Directory where final package files will be stored. Everything that lives here will be packed into your final apk. - `${{targets.subpkgdir}}`: Directory where final subpackage files will be stored. Works the same way as `targets.destdir`, but for subpackages. -You can find more details about available pipelines in the [melange pipelines documentation](https://edu.chainguard.dev/open-source/melange/melange-pipelines). +You can find more details about available pipelines in the [melange documentation](https://github.com/chainguard-dev/melange). ### The `subpackages` Section As mentioned previously, a package may extract parts of its contents into subpackages in order to make for a slimmer final apk. Many packages have resources that are not required at execution time, including development headers, man pages, shared libraries that are optional. This part is really important in Wolfi, because we want packages to be minimal. The `subpackages` section of the melange YAML file looks a lot like the pipeline section, and it essentially works the same way. You'll just have to make sure you place any subpackage files in the `targets.subpkgdir` location. @@ -265,7 +265,7 @@ Again, this section is only required when submitting the package to Wolfi. For m ## Building Packages When you feel your YAML is good for a first run, it's time to build the package with melange. In this guide we'll use Docker to execute melange in a local environment, using [Wolfi's SDK](https://github.com/wolfi-dev/tools/pkgs/container/sdk) image. This image contains everything you need to build Wolfi packages with melange and Wolfi-based images with apko. -The procedure to build apk packages with melange is explained in more detail in our [Getting Started with melange](https://edu.chainguard.dev/open-source/melange/tutorials/getting-started-with-melange/) tutorial. +The procedure to build apk packages with melange is explained in more detail in our [melange GitHub repository](https://github.com/chainguard-dev/melange). ### Setting Up a Local Development Environment @@ -351,7 +351,7 @@ Another useful strategy is to include `set -x` before commands in your pipeline, chmod +x "${EXEC_DIR}/composer" ``` -Most build issues are caused by missed dependencies, even when the error message might be misleading. Another common reason for build errors are wrong file or directory paths. The [melange documentation](https://edu.chainguard.dev/open-source/melange/troubleshooting/) has more pointers to help with debugging, in case you need it. +Most build issues are caused by missed dependencies, even when the error message might be misleading. Another common reason for build errors are wrong file or directory paths. As mentioned before, there might be cases where you'll need to first build a dependency, and then use this dependency to build the package you need. diff --git a/content/open-source/wolfi/hello-wolfi.md b/content/open-source/wolfi/hello-wolfi.md index 64daf18c78..6225bf570e 100644 --- a/content/open-source/wolfi/hello-wolfi.md +++ b/content/open-source/wolfi/hello-wolfi.md @@ -94,9 +94,6 @@ docker run --privileged --rm -v "${PWD}":/work -- \ --signing-key melange.rsa --keyring-append melange.rsa.pub ``` -_If you run into issues while running melange commands, check the [melange troubleshooting guide](/open-source/melange/troubleshooting/)._ - - ### 4. Build the Composer package You can now build the Composer package with the following command on Linux operating systems: @@ -142,8 +139,6 @@ Now that all dependencies are ready, you can now run `apko build` to build the i docker run --rm -v ${PWD}:/work cgr.dev/chainguard/apko build --debug apko.yaml hello-wolfi:latest hello-wolfi.tar -k melange.rsa.pub ``` -_If you run into issues while running apko commands, check the [apko troubleshooting guide](/open-source/apko/troubleshooting/)._ - ### 7. Load the container image You can now load the generated image into Docker with the following command: diff --git a/content/open-source/wolfi/wolfi-with-dockerfiles.md b/content/open-source/wolfi/wolfi-with-dockerfiles.md index 032ef8d073..7b0534bef3 100644 --- a/content/open-source/wolfi/wolfi-with-dockerfiles.md +++ b/content/open-source/wolfi/wolfi-with-dockerfiles.md @@ -30,7 +30,7 @@ A _distroless_ image is a minimal container image that typically doesn't include There are currently two main strategies for building distroless images with Wolfi: - **With a Dockerfile:** Use `-dev` variants **or** the `wolfi-base` image from [Chainguard Images](/chainguard/chainguard-images/overview/) to build the application, and copy the artifacts to a distroless runtime image. This option is typically more accessible for people who are already used to a Dockerfile workflow. -- **With apko:** Use [apko](/open-source/apko/overview/) to build a distroless image with only the packages you need, fully customized. This option requires a steeper learning curve to get used to how apko works, but it will give you smaller images with better SBOM coverage. The [Getting Started with apko](/open-source/apko/getting-started-with-apko/) tutorial explains how that works in practice. +- **With apko:** Use [apko](https://github.com/chainguard-dev/apko) to build a distroless image with only the packages you need, fully customized. This option requires a steeper learning curve to get used to how apko works, but it will give you smaller images with better SBOM coverage. The [wolfi-base](https://github.com/chainguard-images/images/tree/main/images/wolfi-base) image, which we'll be using in this tutorial, is not distroless, because it includes `apk-tools` and `bash`. It can still be used to build a final distroless image, when combined with a distroless runtime in a [Docker multi-stage build](https://docs.docker.com/build/building/multi-stage/). @@ -220,6 +220,6 @@ And you'll notice that the `:distroless` version is significantly smaller, becau ## Final Considerations -If your build requires dependencies that are not yet available on Wolfi, you can build your own apks using [melange](/open-source/melange/overview/). Check the [Getting started with melange](/open-source/melange/tutorials/getting-started-with-melange/) guide for more details on how to go about that. +If your build requires dependencies that are not yet available on Wolfi, you can build your own apks using [melange](https://github.com/chainguard-dev/melange). Check also our public [Chainguard Images](/chainguard/chainguard-images/reference/) for application environments including `-dev` variants that can be used as builders for your specific application runtime. diff --git a/content/software-security/what-are-containers/index.md b/content/software-security/what-are-containers/index.md index bf872aab82..843ef53517 100644 --- a/content/software-security/what-are-containers/index.md +++ b/content/software-security/what-are-containers/index.md @@ -31,7 +31,7 @@ In order to build a container for your application, you will need to start with To start creating a container image, you must first select a *base image*. A base image is a foundational image that can be built upon through the addition of image *layers*. Typically, base images come pre-bundled with a specific Linux distribution. Every distribution differs in its size, dependencies, and functionality, making certain distributions better suited for certain images over others. -After selecting a base image, there are a few different ways you can introduce tailored functionality (such as your application-specific code or dependencies) to the image. Many developers today use [Docker](https://www.docker.com/), a tool used to deploy containerized applications, which ingests a [*Dockerfile*](https://docs.docker.com/engine/reference/builder/), a machine-readable configuration document containing the instructions to assemble an image with multiple layers. Aside from Dockerfiles, you can use tools such as [apko](/open-source/apko/overview/) and [ko](https://github.com/ko-build/ko) to build images, though they produce images using a single-layer construction method. +After selecting a base image, there are a few different ways you can introduce tailored functionality (such as your application-specific code or dependencies) to the image. Many developers today use [Docker](https://www.docker.com/), a tool used to deploy containerized applications, which ingests a [*Dockerfile*](https://docs.docker.com/engine/reference/builder/), a machine-readable configuration document containing the instructions to assemble an image with multiple layers. Aside from Dockerfiles, you can use tools such as [apko](https://github.com/chainguard-dev/apko) and [ko](https://github.com/ko-build/ko) to build images, though they produce images using a single-layer construction method. For example, say you want to build a container to run your Python application. You can start your container image with a Python base image, such as a [Wolfi-based image](/open-source/wolfi/wolfi-with-dockerfiles/). Then, you can add your application and its relevant dependencies to the image through the layers in a Dockerfile. The resultant image is now ready to be deployed with your application bundled inside. diff --git a/layouts/shortcodes/blurb/images-advanced.html b/layouts/shortcodes/blurb/images-advanced.html index 5b4c9f5a8d..2ae457d59b 100644 --- a/layouts/shortcodes/blurb/images-advanced.html +++ b/layouts/shortcodes/blurb/images-advanced.html @@ -8,4 +8,4 @@ Check the "Using the wolfi-base Image" section of our images quickstart guide for more information.

-

If the packages you need are not available, you can build your own apks using melange. Please refer to this guide for more information.

+

If the packages you need are not available, you can build your own apks using melange. Please refer to this guide for more information.

diff --git a/nginx.conf b/nginx.conf index ac4e9a8d8c..62dfe7c3c6 100644 --- a/nginx.conf +++ b/nginx.conf @@ -30,7 +30,8 @@ http { "~^/chainguard/chainctl/chainctl-docs/(index.html|index.xml)?$" /chainguard/chainctl/; "~^/chainguard/chainguard-enforce/chainguard-enforce-kubernetes/(index.html|index.xml)?$" /chainguard/chainguard-enforce/enforce-overview/; "~^/chainguard/chainguard-enforce/chainguard-enforce-kubernetes/chainguard-enforce-policy-examples(.+)?$" /chainguard/chainguard-enforce/policies/chainguard-enforce-policy-examples$1; - "~^/open-source/melange/getting-started-with-melange(.+)?$" /open-source/melange/tutorials/getting-started-with-melange/; + "~^/open-source/build-tools/apko" https://github.com/chainguard-dev/apko; + "~^/open-source/build-tools/melange" https://github.com/chainguard-dev/melange; "~^/chainguard/chainguard-enforce/sboms/sboms-and-attestations/(.+)?$" /open-source/sbom/sboms-and-attestations/; "~^/chainguard/chainguard-images/images-compared/(.+)?$" /chainguard/chainguard-images/vuln-comparison/; "~^/software-security/secure-software-development/considerations-for-image-updates/(.+)?$" /chainguard/chainguard-images/considerations-for-image-updates/;