@rules_distroless//apt:apt.bzl
apt.install macro
This documentation provides an overview of the convenience apt.install
repository macro to create Debian repositories with packages "installed" in
them and available to use in Bazel.
Functions & Macros
apt.installRepository macro to create Debian repositories.
[!WARNING]
THIS IS A LEGACY MACRO. Use it only if you are still usingWORKSPACE.
Otherwise please use theaptmodule extension.
Here's an example to create a Debian repo with apt.install:
# WORKSPACE load("@rules_distroless//apt:apt.bzl", "apt") apt.install( name = "bullseye", # lock = "//examples/apt:bullseye.lock.json", manifest = "//examples/apt:bullseye.yaml", ) load("@bullseye//:packages.bzl", "bullseye_packages") bullseye_packages()
Note that, for the initial setup (or if we want to run without a lock) the
lockfile attribute can be omitted. All you need is a YAML
manifest:
version: 1 sources: - channel: bullseye main url: https://snapshot-cloudflare.debian.org/archive/debian/20240210T223313Z archs: - amd64 packages: - perl
apt.install will parse the manifest and will fetch and install the
packages for the given architectures in the Bazel repo @<NAME>.
Each <PACKAGE>/<ARCH> has two targets that match the usual structure of a
Debian package: data and control.
You can use the package like so: @<REPO>//<PACKAGE>/<ARCH>:<TARGET>.
E.g. for the previous example, you could use @bullseye//perl/amd64:data.
Lockfiles
As mentioned, the macro can be used without a lock because the lock will be
generated internally on-demand. However, this comes with the cost of
performing a new package resolution on repository cache misses.
The lockfile can be generated by running bazel run @bullseye//:lock. This
will generate a .lock.json file of the same name and in the same path as
the YAML manifest file.
If you explicitly want to run without a lock and avoid the warning messages
set the nolock argument to True.
Best Practice: use snapshot archive URLs
While we strongly encourage users to check in the generated lockfile, it's
not always possible because Debian repositories are rolling by default.
Therefore, a lockfile generated today might not work later if the upstream
repository removes or publishes a new version of a package.
To avoid this problems and increase the reproducibility it's recommended to
avoid using normal Debian mirrors and use snapshot archives instead.
Snapshot archives provide a way to access Debian package mirrors at a point
in time. Basically, it's a "wayback machine" that allows access to (almost)
all past and current packages based on dates and version numbers.
Debian has had snapshot archives for 10+
years. Ubuntu
began providing a similar service recently and has packages available since
March 1st 2023.
To use this services simply use a snapshot URL in the manifest. Here's two
examples showing how to do this for Debian and Ubuntu:
For more infomation, please check https://snapshot.debian.org and/or
https://snapshot.ubuntu.com.
Parameters
*name | name of the repository |
*manifest | label to a |
lock | label to a Default: None |
nolock | bool, set to True if you explicitly want to run without a lock Default: False |
package_template | (EXPERIMENTAL!) a template file for generated BUILD Default: None |
resolve_transitive | whether dependencies of dependencies should be Default: True |
@rules_distroless//apt:defs.bzl
EXPERIMENTAL! Public API
Rules
dpkg_statusTODO: docs
| Attribute | Type | Description |
|---|---|---|
*name | name | A unique name for this target. |
*controls | list of labels |
@rules_distroless//apt:extensions.bzl
apt extensions
Module Extensions
aptTag Classes
installModule extension to create Debian repositories.
Create Debian repositories with packages "installed" in them and available
to use in Bazel.
Here's an example how to create a Debian repo:
apt = use_extension("@rules_distroless//apt:extensions.bzl", "apt") apt.install( name = "bullseye", lock = "//examples/apt:bullseye.lock.json", manifest = "//examples/apt:bullseye.yaml", ) use_repo(apt, "bullseye")
Note that, for the initial setup (or if we want to run without a lock) the
lockfile attribute can be omitted. All you need is a YAML
manifest:
version: 1 sources: - channel: bullseye main url: https://snapshot-cloudflare.debian.org/archive/debian/20240210T223313Z archs: - amd64 packages: - perl
apt.install will parse the manifest and will fetch and install the packages
for the given architectures in the Bazel repo @<NAME>.
Each <PACKAGE>/<ARCH> has two targets that match the usual structure of a
Debian package: data and control.
You can use the package like so: @<REPO>//<PACKAGE>/<ARCH>:<TARGET>.
E.g. for the previous example, you could use @bullseye//perl/amd64:data.
Lockfiles
As mentioned, the macro can be used without a lock because the lock will be
generated internally on-demand. However, this comes with the cost of
performing a new package resolution on repository cache misses.
The lockfile can be generated by running bazel run @bullseye//:lock. This
will generate a .lock.json file of the same name and in the same path as
the YAML manifest file.
If you explicitly want to run without a lock and avoid the warning messages
set the nolock argument to True.
Best Practice: use snapshot archive URLs
While we strongly encourage users to check in the generated lockfile, it's
not always possible because Debian repositories are rolling by default.
Therefore, a lockfile generated today might not work later if the upstream
repository removes or publishes a new version of a package.
To avoid this problems and increase the reproducibility it's recommended to
avoid using normal Debian mirrors and use snapshot archives instead.
Snapshot archives provide a way to access Debian package mirrors at a point
in time. Basically, it's a "wayback machine" that allows access to (almost)
all past and current packages based on dates and version numbers.
Debian has had snapshot archives for 10+
years. Ubuntu
began providing a similar service recently and has packages available since
March 1st 2023.
To use this services simply use a snapshot URL in the manifest. Here's two
examples showing how to do this for Debian and Ubuntu:
For more infomation, please check https://snapshot.debian.org and/or
https://snapshot.ubuntu.com.
| Attribute | Type | Description |
|---|---|---|
*name | name | Name of the generated repository |
*manifest | label | The file used to generate the lock file |
lock | label | The lock file to use for the index. Default: None |
nolock | boolean | If you explicitly want to run without a lock, set it to Default: False |
package_template | label | (EXPERIMENTAL!) a template file for generated BUILD files. Default: None |
resolve_transitive | boolean | Whether dependencies of dependencies should be resolved and added to the lockfile. Default: True |
mergedusr | boolean | Whether packges should be normalized following mergedusr conventions. Default: False |
@rules_distroless//distroless:defs.bzl
Public API re-exports
Functions & Macros
os_releaseCreate an Operating System Identification file from a key, value dictionary.
https://www.freedesktop.org/software/systemd/man/latest/os-release.html
Parameters
*name | name of the target |
*content | a key, value dictionary that will be serialized into See https://www.freedesktop.org/software/systemd/man/latest/os-release.html#Options for well known keys. |
path | where to put the file in the result archive. default: Default: "/usr/lib/os-release" |
mode | mode for the entry Default: "0555" |
time | time for the entry Default: "0" |
kwargs | other named arguments to expanded targets. see common rule attributes. |
groupCreate a group file from array of dicts.
https://www.ibm.com/docs/en/aix/7.2?topic=files-etcgroup-file#group_security__a21597b8__title__1
Parameters
*name | name of the target |
*entries | an array of dicts which will be serialized into single group file. |
time | time for the entry Default: "0.0" |
mode | mode for the entry Default: "0644" |
kwargs | other named arguments to expanded targets. see common rule attributes. |
passwdCreate a passwd file from array of dicts.
https://www.ibm.com/docs/en/aix/7.3?topic=passwords-using-etcpasswd-file
Parameters
*name | name of the target |
*entries | an array of dicts which will be serialized into single passwd file. An example; |
mode | mode for the entry Default: "0644" |
time | time for the entry Default: "0.0" |
kwargs | other named arguments to expanded targets. see common rule attributes. |
homeCreate home directories with specific uid and gids.
Parameters
*name | name of the target |
*dirs | array of home directory dicts. |
kwargs | other named arguments to that is passed to tar. see common rule attributes. |
Rules
cacertsCreate a ca-certificates.crt bundle from Common CA certificates.
When provided with the ca-certificates Debian package it will create a bundle
of all common CA certificates at /usr/share/ca-certificates and bundle them into
a ca-certificates.crt file at /etc/ssl/certs/ca-certificates.crt
An example of this would be
# MODULE.bazel http_archive = use_repo_rule("@bazel_tools//tools/build_defs/repo:http.bzl", "http_archive") http_archive( name = "ca-certificates", type = ".deb", sha256 = "b2d488ad4d8d8adb3ba319fc9cb2cf9909fc42cb82ad239a26c570a2e749c389", urls = ["https://snapshot.debian.org/archive/debian/20231106T210201Z/pool/main/c/ca-certificates/ca-certificates_20210119_all.deb"], build_file_content = "exports_files(["data.tar.xz"])" ) # BUILD.bazel load("@rules_distroless//distroless:defs.bzl", "cacerts") cacerts( name = "example", package = "@ca-certificates//:data.tar.xz", )
To use the generated certificate bundle for SSL, you must set SSL_CERT_FILE in the
environment. You can set it on the oci image like so:
oci_image( name = "my-image", env = { "SSL_CERT_FILE": "/etc/ssl/certs/ca-certificates.crt", } )
localeCreate a locale archive from a Debian package.
An example of this would be
# MODULE.bazel http_archive = use_repo_rule("@bazel_tools//tools/build_defs/repo:http.bzl", "http_archive") http_archive( name = "libc-bin", build_file_content = 'exports_files(["data.tar.xz"])', sha256 = "8b048ab5c7e9f5b7444655541230e689631fd9855c384e8c4a802586d9bbc65a", urls = ["https://snapshot.debian.org/archive/debian-security/20231106T230332Z/pool/updates/main/g/glibc/libc-bin_2.31-13+deb11u7_amd64.deb"], ) # BUILD.bazel load("@rules_distroless//distroless:defs.bzl", "locale") locale( name = "example", package = "@libc-bin//:data.tar.xz" )
java_keystoreCreate a java keystore (database) of cryptographic keys, X.509 certificate chains, and trusted certificates.
Currently only public X.509 are supported as part of the PUBLIC API contract.
| Attribute | Type | Description |
|---|---|---|
*name | name | A unique name for this target. |
*certificates | list of labels | |
mode | string | mode for the entries Default: "0755" |
time | string | time for the entries Default: "0.0" |
flattenFlatten multiple archives into single archive.
| Attribute | Type | Description |
|---|---|---|
*name | name | A unique name for this target. |
*tars | list of labels | List of tars to flatten |
deduplicate | boolean | EXPERIMENTAL: We may change or remove it without a notice. Remove duplicate entries from the archives after flattening. Default: False |
compress | string | Compress the archive file with a supported algorithm. Default: "" |
@rules_distroless//distroless/tests:asserts.bzl
Make shorter assertions
Functions & Macros
assert_tar_mtreeAssert that an mtree representation of a tarball matches an expected value.
Parameters
*name | name of this assertion |
*actual | label for a tarball |
*expected | expected mtree |
assert_tar_listingAssert that the listed contents of a tarball match an expected value. This is useful when checking for duplicated paths.
Parameters
*name | name of this assertion |
*actual | label for a tarball |
*expected | expected listing |
assert_jks_listingParameters
*name | |
*actual | |
*expected |