---
tags: rfc
---
> TODO:
> - [ ] Add app developer use cases
> - [ ] Upgrade
> - [ ] Mixins
# Extending Images UX
The definition of an extended image is that of which an execution occurs within the running of a container to produce mutation to said image.
```
+-----+
| |
| e |
| x |
| t |
| e |
| n |
+----------------+ | s | +-----------------------+
| | | i | | |
| some/image | +--> | o | +--> | some/extended-image |
| | | n | | |
+----------------+ | | +-----------------------+
| f |
| u |
| n |
| c |
| |
+-----+
```
Within the context of builders, it makes sense to provide this functionality to the following images:
- builder image
- run image
_We exclude build image because the builder is based (and therefor) effectively the build image but there is no technical limitation as to why they should be excluded._
An image can be extended if it adheres to the contract defined in [RFC #TBD](https://github.com/buildpacks/rfcs/blob/app-image-ext/text/0000-app-image-extensions.md#specification).
## Operators
The use cases this tries to solve are the following:
* As an operator, I want to produce a builder image that has package X installed from the OS.
* As an operator, I want to produce a run image that has package X installed from the OS.
* As an operator, I want to add OS packages to an existing builder image.
* As an operator, I want to add OS packages to an existing run image.
### `pack extend`: Extending any image
```shell
pack extend <image-name> [image-name, ...] --config extend.toml
```
where `extend.toml` is:
```toml
[extend]
image = "<image-name>"
[extend.metadata]
# arbitrary metadadata understood by the image being extended
```
The resulting image will contain the following information in a label `io.buildpacks.extend.metadata`. If the label exists on the image being extended it will be merged.
#### Example: Extenting run image
```shell
pack extend some/extended-run gcr.io/some/extended-run --config extend.toml
```
where `extend.toml` is:
```toml
[extend]
image = "some/run"
[extend.metadata]
packages = ["imagemagick"]
```
### `pack extend-builder`: Extending an existing builder
This case is more focused to extending all images associated with a builder. This includes the builder image and run image(s).
```shell
pack extend-builder \
# name of image to save as
# (required) *out*
<image-name> \
# configuration
# (required) *in*
--extension-config <extend-builder.toml> \
# name to save run image as
# (required if `run` image is to be extended) *out*
--run-image <image-name> \
# name to save a run image mirror as
# (optional) *out*
--run-image-mirror <image-name>
```
`extend-builder.toml`:
```toml
[extend]
image = "<image-name>"
[extend.metadata]
# metadata provided to `run` and `build` images
[extend.metadata.run]
# metadata provided only to `run` images
[extend.metadata.build]
# metadata provided only to `build` images
```
#### Example: Extending a builder while saving only builder image
```shell
pack extend-builder some/extended-builder --extension-config extend.toml
```
where `extend.toml` is:
```toml
[extend]
image = "some/builder"
[extend.metadata.build]
packages = ["git"]
```
#### Example: Extending a builder while saving all images
```shell
pack extend-builder some/extended-builder \
--run-image some/extended-run \
--run-image-mirror gcr.io/some/extended-run \
--config extend.toml
```
where `extend.toml` is:
```toml
[extend]
image = "some/builder"
[extend.metadata.run]
packages = ["imagemagick"]
[extend.metadata.build]
packages = ["build-essentials", "imagemagick"]
```
### Creating an extended builder
> Technically, leveraging the `pack extend` command instead of a new command could achieve the same thing without adding complexity to `create-builder`.
Adds configuration section and flags as defined in [`extend-builder`](#pack-extend-builder-Extending-an-existing-builder) to `pack create-builder`.
```shell
pack create-builder some/extended-builder \
--run-image some/extended-run \
--run-image-mirror gcr.io/some/extended-run \
--config builder.toml
```
`builder.toml`:
```toml
[[buildpacks]]
# buildpacks to include in builder
[[order]]
[[order.group]]
# execution order of buildpacks
[stack]
id = "<stack-id>"
run-image = "<image-name>"
build-image = "<image-name>"
[extend]
[extend.metadata]
# metadata provided to `run` and `build` images
[extend.metadata.run]
# metadata provided only to `run` images
[extend.metadata.build]
# metadata provided only to `build` images
```