Copyright © 2022 SUSE LLC and contributors. All rights reserved.
Except where otherwise noted, this document is licensed under Creative Commons Attribution-ShareAlike 4.0 International (CC-BY-SA 4.0): https://creativecommons.org/licenses/by-sa/4.0/legalcode.
For SUSE trademarks, see http://www.suse.com/company/legal/. All third-party trademarks are the property of their respective owners. Trademark symbols (®, ™ etc.) denote trademarks of SUSE and its affiliates. Asterisks (*) denote third-party trademarks.
All information found in this book has been compiled with utmost attention to detail. However, this does not guarantee complete accuracy. Neither SUSE LLC, its affiliates, the authors nor the translators shall be held liable for possible errors or the consequences thereof.
1 Understanding Keg and KIWI image descriptions #
Keg is a command-line tool that helps to create and manage image descriptions for use with the KIWI appliance builder. A KIWI image description consists of a single XML document that specifies the type, configuration and content of the image to be built. Optionally, configuration scripts and overlay archives can be added to an image description to allow for further configuration and additional content.
Because KIWI image descriptions are monolithic, maintaining a number of image descriptions that have considerable overlap with respect to content and setup can be cumbersome and error-prone. Keg alleviates that by allowing image descriptions to be broken into manageable modules. These modules can be composed in different ways within specific image definitions. The modules can inherit from parent modules, allowing for fine-tuning of specific image setups. Configuration scripts and overlay archives can also be generated in a modular fashion.
The collection of source data required for Keg to produce image
descriptions is called recipes. Keg
recipes are typically stored in a Git
repository, and Keg has support for producing changelogs
from the git commit history, but this is not a requirement. A
recipes repository provides Keg with
instructions on how an image description is composed and
the content of its components.
The basic principle of operation is that when
keg is executed, it is pointed to a directory
within the recipes repository. It reads
any YAML files in that directory and its parent directories,
merging their contents into a single dictionary. The structure of
the image definition data remains flexible, provided that the
resulting dictionary represents a valid image definition. This
allows for a lot of flexibility in the layout of a
recipes repository. The SUSE
Public Cloud Keg Recipes repository provides an example
of a highly modular layout with strong use of inheritance.
For more details on what constitutes a
recipes repository, see Section 5, “Structuring Keg recipes for image definitions” and the following sections.
2 Generating an image description with Keg #
To create an image description, Keg must be installed alongside KIWI, as the latter is used by Keg to validate the final image description. See Section 3, “Installing Keg from openSUSE or PyPI repositories” for information about how to install Keg, and KIWI Installation about how to install KIWI.
Additionally, a recipes repository is
required to provide the source data. The following example demonstrates
how to use Public Cloud keg recipes:
> git clone https://github.com/SUSE-Enceladus/keg-recipes.git > mkdir sles15-sp4-byos > keg --recipes-root keg-recipes --dest-dir sles15-sp4-byos \ cross-cloud/sles/byos/15-sp4
After the keg command completes, the
destination directory specified with
--dest-dir contains a description for a SUSE
Linux Enterprise Server 15 SP4 image for the Public
Clouds. It can be processed with KIWI to build an image. For
more details about KIWI image descriptions, see https://osinside.github.io/kiwi/image_description.html.
Recipes used to generate an image description
can be spread across multiple repositories. For that purpose, the
--recipes-root command-line argument may be
given multiple times, with each one specifying a different
recipes repository. Repositories will be
searched in the order they are specified, and for any dictionary
key, config scriptlet, or overlay archive module that exists in
multiple repositories, the one that is read last will be used.
Using multiple repositories for recipes can
be useful in some situations. For example, if some parts of the
recipes data are public and some private,
they can be kept in different repositories. It could also be
used to base recipes on an upstream
repository and only maintain additional image definitions or
modifications in a separate repository.
Keg also provides support for producing image descriptions for
use with the Open
Build Service (OBS). It can generate the
_multibuild files required by OBS
for image descriptions with multiple profiles. Keg includes
an OBS Source Service plug-in to automate
the generation process. See Section 9, “Automating image descriptions with the OBS Source Service” for details.
3 Installing Keg from openSUSE or PyPI repositories #
This section describes how to install Keg. Currently, Keg is available via the Python Package Index (PyPI) and from the openSUSE Build Service for several openSUSE distributions. It is included in openSUSE Tumbleweed.
3.1 Installing from the openSUSE Cloud:Tools repository #
Keg is available for various openSUSE distributions from the
Cloud:Tools
repository in the openSUSE Build Service. The package name
is pythonpy_version-kiwi-keg.
3.2 Installing from PyPI #
Keg can be obtained from PyPI via Python’s package manager pip:
> pip install kiwi_keg
4 Keg command-line interface syntax and options #
4.1 The keg command #
SYNOPSIS#
keg [options] <source>
DESCRIPTION#
The Keg tool helps create and manage image descriptions suitable for the KIWI appliance builder. While Keg can handle single definitions, it provides no considerable advantage in such use cases. Its strategic advantage lies in managing multiple image descriptions with significant content overlap.
Keg requires source data called recipes,
which provides all the information necessary for Keg to create
KIWI image descriptions. See Section 5, “Structuring Keg recipes for image definitions”
for more information about recipes.
The recipes used for generating SUSE Public
Cloud image descriptions can be found in the Public
Cloud Keg Recipes repository.
ARGUMENTS#
- source
Path to image source under
RECIPES_ROOT/images.
OPTIONS#
-
-r--recipes-root Root directory of keg recipes. Can be used more than once. Elements from later roots may overwrite earlier ones.
-
-d--dest-dir Destination directory for the generated description. [default:
.]-
--disable-multibuild Option to disable creation of OBS _multibuild file (for image definitions with multiple profiles). [default:
false]-
--disable-root-tar Option to disable the creation of root.tar.gz in the destination directory. If present, an overlay tree will be created instead. [default:
false]-
--dump-dict Dump the generated data dictionary to stdout instead of generating an image description. Useful for debugging.
-
-l--list-recipes List available images that can be created with the current recipes.
-
-f--force Force mode (ignore errors, overwrite files).
-
--format-yaml Format/Update the Keg written image description to the installed KIWI schema and write the resulting description in the YAML markup.
NoteCurrently, no translation of comment blocks from the Keg-generated KIWI description to the YAML markup will be performed.
-
--format-xml Format/Update the Keg-written image description to the installed KIWI schema and write the resulting description in XML markup.
NoteCurrently, only top-level header comments from the Keg-written image description will be preserved in the formatted/updated KIWI XML file. Inline comments will not be preserved.
-
-i--image-version Set image version.
-
-a Generate image description for architecture ARCH (can be used multiple times).
-
-s--write-source-info Write a file per profile containing a list of all used source locations. The files can generate a changelog from the recipes repository commit log.
-
-v--verbose Enable verbose output.
-
--version Print version.
EXAMPLE#
> git clone https://github.com/SUSE-Enceladus/keg-recipes.git > keg --recipes-root keg-recipes --dest-dir leap_description leap/jeos/15.2
4.2 The generate_recipes_changelog command #
SYNOPSIS#
generate_recipes_changelog [options] <logfile>
DESCRIPTION#
generate_recipes_changelog generates a
changelog from the git commit history of one or more
keg-recipes repositories. The input file
is a source info log that is generated by Keg when run with
source tracking enabled (-s command line
switch).
The exit status is 0 if a changelog was generated successfully, 1 in case an error occurred, or 2 if no error occurred but generated changelog is empty.
ARGUMENTS#
- logfile
A source info log file produced by Keg.
OPTIONS#
-
-o Write output to OUTPUT_FILE (
stdoutif omitted).-
-rPATH:REV Set the git revision range to REV for the repo at PATH.
NoteThis limits the applicable set of commits to the given revision spec. This can be used to select only newer changes from a previous changelog generator run. See the section called “EXAMPLE” below.
-
-f Output format,
textoryaml. [default:yaml]-
-m Format spec for commit messages (see ‘format:<string>’ in
man git-log) [default:- %s] (only used with text format).-
-t Use ROOT_TAG for YAML output (e.g. image version).
EXAMPLE#
> generate_recipes_changelog -r /path/to/repo:12345678.. -t 1.1.8 log_sources
This will produce a YAML changelog, namespaced with
1.1.8, intended as a version number, only
considering commits after hash 12345678. If
12345678 was the hash of the HEAD commit in
the checked-out branch at /PATH/TO/REPO
at the previous run of
generate_recipes_changelog on the same data
set, this would limit the changelog to only contain newer
changes. This method can be used to produce incremental change
logs.
The changelog will have the following format:
1.1.8:
- change: git message subject
date: git commit UTC timestamp
details: |-
git message body
...5 Structuring Keg recipes for image definitions #
To produce image descriptions, Keg must be provided with source
data known as keg recipes. Unlike KIWI
descriptions, keg recipes can be composed of
an arbitrary number of files, which allows for creating building
blocks for image descriptions. Keg does not mandate a specific
structure for the recipes data, but it expects specific types of
source data to be organized within a defined directory layout.
5.1 How to organize directories for image definitions and modules #
Essentially, a keg recipes repository consists of three top-level directories,
which contain different types of configuration data. Those three are:
-
Image Definitions:
images The
imagesdirectory contains all image definitions. An image definition specifies the properties and content of the image description to be generated. Include statements in the image definition allow referencing chunks of content from the data modules. Image definitions are specified in YAML format, can be modular and support data inheritance. See Section 6, “Creating image definitions” for details.- Data Modules:
data The
datadirectory contains different bits of configuration and content data that can be used to compose an image description. See Section 7, “Using data modules for modular configuration” for details on data modules. There are three different types of data modules:- Image Definition Modules
Any directory in
datathat is not file:scriptsor file:overlayfilesis considered a module, or module tree, for image definition data. Those modules can be referenced in the image definitions using_includestatements. The data is in YAML format and supports inheritance.- Image Configuration Scriptlets
Scriptlets can be used to compose optional configuration shell scripts that KIWI can run during the build process. The scriptlets are located in
data/scripts.- Overlay Files
Image descriptions may include overlay files that get copied into the target image. Keg can create overlay archives from overlay data directories. Overlay files trees are located in
>data/overlayfiles.
- Schema Templates:
schemas Keg uses Jinja2 templates to produce the headers for
config.shandimages.sh. Both are optional and Keg will write a fallback header if they are missing. Additionally, a Jinja2 template can be used to generateconfig.kiwiinstead of using the internal XML generator.
5.2 Source data format and processing #
An image description is internally represented by a data dictionary with a certain structure. This dictionary is composed by parsing source image definition and data files referenced by the image definition and merging them into a dictionary.
Image definitions and data modules are used by
referencing a directory (under images or data respectively), which may be
several layers of directories under the root directory. When
parsing those, Keg will also read any
.yaml file that is in a directory above
the referenced one, and merge all source data into one
dictionary, with the lower (i.e. more specific) layers taking
precedence over upper (i.e. more generic) ones. This
inheritance mechanism is intended to reduce data duplication.
Keg uses namespaces in the image definition to group certain bits of information (for instance, a list of packages) which can be overwritten in derived modules, allowing for the creation of specialized versions of data modules for specific use case or different image description versions.
Once everything is merged, the resulting dictionary is
validated against the image definition schema to ensure its
structure is correct and all required keys are present. If
that is the case, Keg runs the image dictionary through its
XML generator to produce a config.kiwi
file. In case the image definition contains configuration
scripts or overlay archive specifications, Keg will generate
those as well.
6 Creating image definitions #
In Keg terminology, an image definition is the data set that
instructs Keg on how to generate a KIWI XML description.
Keg reads image definitions from the images directory in the recipes root directory.
Keg considers all leaf directories in images to be image definitions.
This means by parsing any YAML file from those directories and
all YAML files in any parent directory and merging their data
into a dictionary, a complete image definition needs to be
available in the resulting dictionary. There is no specific
hierarchy required in images. Any level of subdirectories
can be used to create multiple levels of
inheritance, or simply just to group image definitions. Example
directory layout:
images/
opensuse/
defaults.yaml
leap/
content.yaml
15.2/
image.yaml
15.3/
image.yaml
This example layout defines two images: opensuse/leap/15.2 and opensuse/leap/15.3. It uses
inheritance to define a common content definition for both image
definitions and to set some opensuse specific defaults. Running
keg -d output_dir opensuse/leap/15.3 would
merge data from the files in the following order:
images/opensuse/defaults.yaml images/opensuse/leap/content.yaml images/opensuse/leap/15.3/image.yaml
All keys from the individual YAML files that are in the given tree will be merged into a dictionary that defines the image to be generated.
6.1 Image definition structure #
An image definition dictionary is composed of several parts that define different parts of the image: the actual image description, configuration scripts and overlay archives. All parts are defined under a top-level key in the dictionary. There are additional top-level keys that affect data parsing and generator selection.
The top-level keys are as follows:
6.1.1 image #
The image dictionary. This is the only mandatory top-level
key. It defines the content of the
config.kiwi file Keg should generate
and is essentially a YAML version of KIWI's image
description (typically in XML). It contains all image
configuration properties, package lists, and references to
overlay archives. There are a number of special keys that
influence how Keg constructs the dictionary and generates
the XML output. The basic structure is as follows:
image:
_attributes:
schemaversion: "SCHEMA_MAJ.SCHEMA_MIN"
name: IMAGE_NAME
displayname: IMAGE_BOOT_TITLE
description:
_attributes:
type: SYSTEM_TYPE
author: AUTHOR_NAME
contact: AUTHOR_EMAIL
preferences:
- version: VERSION_STRING
- _attributes:
profiles:
- PROFILE_NAME
...
type:
_attributes:
image: IMAGE_TYPE
kernelcmdline:
KERNEL_PARAM: KERNEL_PARAM_VALUE
...
...
size:
_attributes:
unit: SIZE_UNIT
_text: DISK_SIZE
...
users:
user:
- _attributes:
name: USER_NAME
groups: USER_GROUPS
home: USER_HOME
password: USER_PASSWORD
...
packages:
- _attributes:
type: image|bootstrap
profiles:
- PROFILE
...
archive:
_attributes:
name: ARCHIVE_FILENAME
NAMESPACE:
package:
- _attributes:
name: PACKAGE_NAME
arch: PACKAGE_ARCH
...
...
...
profiles:
profile:
- _attributes:
name: PROFILE_NAME
description: PROFILE_DESCRIPTION
...This only outlines the structure and includes some of the configuration keys that KIWI supports. See KIWI Image Description for full details.
For the purpose of generating the KIWI XML image
description, any key in the image dictionary that is not a
plain data type is converted to an XML element in the KIWI
image description, with the tag name being the key name. Any
key that starts with an _ has a special
meaning. The following keys are supported:
_attributesIf a key contains a subkey called
_attributes, it instructs the XML generator to produce an attribute for the XML element with the given key name and value as its name-value pair. If the value is not a plain data type, it is converted to a string, which allows for complex attributes to be split over different files and also for redefinition at lower levels. For example:type: _attributes: image: vmx kernelcmdline: console: ttyS0 debug: []Would generate the following XML element:
<type image="vmx" kernelcmdline="console=ttyS0 debug"/>
The empty list used as a value for
debugmeans the attribute parameter is valueless (i.e. a flag)._textIf a key contains a key called
_text, its value is considered the element’s content string._namespace_nameAny key that starts with
_namespacedoes not produce an XML element in the output. Namespaces are used to group data and allow for an inheritance and overwrite mechanism. Namespaces produce comments in the XML output that state which namespace the enclosed data was part of._map_attributeIf a key contains a key
_map_attribute, which needs to be a string type, any_attributekey under the key that is a simple list instead of the actually required mapping, is automatically converted to a mapping with the attribute key equal to_map_attributevalue. For example:packages: _map_attribute: name _namespace_some_pkgs: package: - pkg1 - pkg2Is automatically converted to:
packages: _namespace_some_pkgs: package: - _attribute: name: pkg1 - _attribute: name: pkg1 archive: - _attributes: name: archive1.tar.gzThis allows for making lists of elements that all have the same attribute (which package lists typically have) more compact and readable.
_comment_nameAny key that has a key that starts with
_commentwill have a comment above it in the XML output, reading the value of the_commentkey (needs to be a string).
6.1.2 config #
The config dictionary defines the content of the
config.sh file Keg should
generate. config.sh is a script that KIWI
runs during the image preparation step and can be used to modify
the image’s configuration. The config
dictionary structure is as follows:
config:
- profiles:
- PROFILE_NAME
...
files:
NAMESPACE:
- path: FILE
append: bool
content: string
...
...
scripts:
NAMESPACE:
- SCRIPT
...
...
services:
NAMESPACE:
- SERVICE_name
- name: SERVICE_name
enable: bool
...
...
sysconfig:
NAMESPACE:
- file: SYSCONFIG_FILE
name: SYSCONFIG_VARIABLE
value: string
...
...
...
Each list item in config produces a
section in config.sh, with the optional
profiles key defining for which image
profile that section should apply. Each item can have the
following keys (all are optional, but there has to be at
least one):
filesDefines files that should be created (or overwritten if existing) with the given
contentor havecontentappended to inconfig.sh(default onappendisfalse).scriptsDefines which scriptlets should be included.
scriptrefers to a filedata/scripts/SCRIPT.shin the recipes tree.servicesDefines which systemd services and timers should be enabled or disabled in the image. The short version (just a string) means the string is the service name and it should be enabled.
sysconfigDefines which existing sysconfig variables should be altered.
NAMESPACE defines a namespace
with the same purpose as in the image
dictionary, but config namespaces do
not have to start with _ (although this
would be allowed, too).
6.1.3 setup #
The config dictionary defines the content of the
images.sh file Keg should
generate. This script is run by KIWI during the image creation
step. Its structure is identical to
config.
See User defined scripts in the KIWI documentation for more details on user scripts.
6.1.4 archive #
The archive dictionary defines the content of overlay tar
archives that can be included in the image via the
archive sub-section of the
packages section of the
image dictionary. The structure is as
follows:
archive:
- name: archive_filename
namespace:
_include_overlays:
- overlay_module
...
...
When generating the image description, Keg will produce a
tar archive for each entry in archive
with the given file name, with its contents being composed
of all files that are in the listed overlay modules. Each
module references a directory in
data/overlayfiles.
Keg automatically compresses the archive based on the file
name extension. Supported are gz, ,
xz, or no extension for uncompressed
archive.
The archive name root.tar (regardless
of compression extension) is automatically included in all
profiles (if there are any) by KIWI. It is not necessary
to include it explicitly in the image definition.
6.2 The _include statement #
Keg supports importing parts of the image definition from
other directory trees within the recipes to allow for
modularization. For that purpose, a key in the image
dictionary may have a subkey called
_include. Its value is a list of strings,
each of which points to a directory in the
data subdirectory of the recipes root. To
process the instruction, Keg generates another dictionary from
all YAML files in the referenced directory trees (the same
mechanism as when parsing the images tree
applies). It then looks up the key in that dictionary that is
equal to the parent key of the _include
key, and replaces the _include key with its
contents. That means, if the _include
statement is below a key called packages,
only data under packages in the include
dictionary will be copied into the image definition
dictionary. This allows for having different types of
configuration data in the same directory and including them in
different places in the image definition. See Section 7, “Using data modules for modular configuration” for details on data modules.
6.3 Additional configuration directives #
There are three additional optional top-level image definition sections that affect how the image definition dictionary is composed and the image description is generated:
6.3.1 include-paths #
The include-paths key defines a list of
search paths that get appended when
_include statements are processed. This
allows for having different versions of data modules and
still sharing most of an image definition between
different versions. See Section 7, “Using data modules for modular configuration” for
details.
6.3.2 image-config-comments #
The image-config-comments element allows you
to add top-level comments to the generated KIWI file.
The format is as follows:
image-config-comments:
COMMENT_NAME: string
...
COMMENT_NAME is just a name and
is not included in the generated output. Comments can be
used to include arbitrary information in the image
description. Some comments have a special meaning for
processing image descriptions by the Open Build Service; for
instance, the OBS-Profiles directive that
is required to process multi-profile image descriptions. See
https://osinside.github.io/kiwi/working_with_images/build_in_buildservice.html
for details.
Keg generates some comments automatically. If the
image definition has multiple profiles and the
--disable-multibuild command-line
switch is not set, it will add an OBS-Profiles:
@BUILD_FLAVOR@ comment. If the image
description is generated for one or more specific
architectures via the -a command-line
option, the appropriate
OBS-ExclusiveArch comment is
added.
6.3.3 xmlfiles #
This optional section allows generating additional custom XML files. The format is as follows:
xmlfiles:
- name: FILENAME
content:
CONTENT_DICTIONARY
...
For each list item in this section, an XML file named
FILENAME will be created, with
the content being generated from the
<content_dictionary>. For this dictionary,
the same formatting rules as for the image dictionary apply,
including namespacing.
Custom XML files can be useful when generating image
descriptions for the Open Build Service, which
accepts build configuration directives via XML source files,
like the _constraints file. See
https://openbuildservice.org/help/manuals/obs-user-guide/cha.obs.build_job_constraints.html
for details.
6.3.4 schema #
Keg, starting with version 2.0.0, has an internal XML generator to produce KIWI image descriptions. Previously, a Jinja2 template was used to convert the image dictionary that Keg constructed into a KIWI image description. Using a Jinja2 template is still supported and can be configured as follows in the image definition:
schema: TEMPLATE
In this case, instead of running the XML generator, Keg
would read the file
TEMPLATE.kiwi.templ
from the schemas
directory in the recipes root directory and run it through
the Jinja2 engine.
While using a Jinja2 template would in theory allow to operate on different input data structures, the internal schema validator requires the image definition to comply with what Keg expects.
7 Using data modules for modular configuration #
Data modules are directories in the data tree. There are
three different kinds of data modules:
- Image Definition Modules
Any part of the image definition can be in a data module that is included by the
_includestatement from the main image definition.- Image Configuration Scriptlets
Configuration scriptlets are stored in
data/scripts. These scriptlets can be used to compose the image configuration or setup scripts defined by theconfigandsetupkeys in the image definition.- Overlay Files
Files that can be directly included in the image description and will be copied into the image’s file system by KIWI during the build process. Overlay files are stored under
data/overlayfiles.
7.1 Image definition modules #
Any directory under data that is not scripts or overlayfiles is considered an
image definition data module and may be included in the main
image definition using the _include
statement.
Inheritance rules apply similarly to the image definition tree, but Keg supports subversions of data modules. This can be used, for instance, to create slightly different versions of modules for use with different image versions while still sharing most of the image definition between those versions.
For this purpose, Keg supports the
include-paths directive in the image
definition. Include paths are paths that get appended to any
source path, and these paths get scanned for input files as well. See
the following image definition as an example:
include-paths:
leap15/1
leap15/2
image:
preferences:
- _include:
- base/common
packages:
- _include:
- base/common
config:
- _include:
- base/common
This tells Keg, when adding data from directory data/base/common to the image
data dictionary, to also look into subdirectories leap15/2, leap15/1, and leap15 (through
inheritance). This would lead to the following directories
being scanned:
data data/common data/common/base data/common/base/leap15 data/common/base/leap15/1 data/common/base/leap15/2
This allows, for example, to put generic configuration bits in
data/common/base, Leap
15 specific configuration in data/common/base/leap15, and
adjust the configuration for minor versions.
When merging the included dictionaries into the main
dictionary, Keg only copies the dictionary under the top-level
key that matches the key under which the
_include statement is. That means, assuming
the YAML files collected from the above trees resulted in the
following data structure:
preferences:
locale: en_US
timezone: UTC
type:
_attributes:
firmware: efi
image: vmx
packages:
_namespace_base_packages:
package:
- bash
- glibc
- kernel-default
config:
_namespace_base_services:
services:
- sshdWould result in a data structure like this:
include-paths:
leap15/1
leap15/2
image:
preferences:
locale: en_US
timezone: UTC
type:
_attributes:
firmware: efi
image: vmx
packages:
_namespace_base_packages:
package:
- bash
- glibc
- kernel-default
config:
_namespace_base_services:
services:
- sshdMerging based on the parent key allows for grouping different types of configuration data in one data module.
7.2 Image configuration scriptlets #
Configuration scriptlets are individual script snippets that can be used to generate image configuration scripts. KIWI runs those scripts at certain points in the image build process. They can be used to change the system’s configuration.
The scriptlets are located in data/scripts and are required to have a
.sh suffix. These are referenced in the scripts list of the config
or setup sections in the image definition (without the .sh suffix).
See Section 6.1.2, “config” for details on the config section.
7.3 Overlay files #
KIWI image descriptions can contain optional overlay archives, which will be
extracted into the system’s root directory before the image is created.
Overlay files are located in subdirectories in data/overlayfiles,
with each subdirectory representing an overlay files module. Any directory
structure under the module’s top directory is preserved.
Overlay files modules can be referenced in the archive section of the image
definition using the _include_overlays directive. See Section 6.1.4, “archive” for
details.
8 Generating changelogs #
Keg comes with a separate tool that can be used to produce a
changelog for a generated image description from the git commit
history of the used keg recipes tree(s). This
obviously requires these keg recipes to be
stored in Git repositories.
To produce a changelog for an image description, the
description needs to be generated with source info tracking
enabled in Keg (-s command line switch).
8.1 Source info tracking #
With source info tracking enabled, Keg will write one or more
source info files in addition to the image description in the
output directory. If the image description at hand is
single-build, a single file log_sources is
written. If it is multi-build, a file
log_sources_PROFILE is written for each
profile. This allows for generating individual changelogs for
the resulting image binaries.
The source info logs contain detailed information about which
bits from the keg-recipes tree were used to
generate the image description. The source info log files will
contain several lines of the following format:
root:/path/to/repository
range:start:end:/path/to/repository/file
/path/to/repository/file_or_dir
The first line specifies the repository location. There will
be one for each keg-recipes directory given
to Keg. Lines starting with range: specify
a part of a file in a repository. This is used to track the
source location of each key that was in the final image
dictionary. The third line format simply specifies a file or a
directory in the repository that was used in the image
description, and is used for configuration script snippets and
overlay files.
This enables the changelog generator to produce a changelog using the git commit history, selecting only commits that apply to the generated image description.
8.2 Changelog generator #
The generated source info log files, together with the
keg-recipes in the place and state they
were used to generate the image description, can be used to
generate changelogs. The Keg distribution contains the tool
generate_recipes_changelog for that
purpose. When called with a source log file as argument,
generate_recipes_changelog will use the
source information to select matching git messages and produce
a changelog in chronological order. There are parameters
to narrow down the applicable commit range and some
formatting options. Refer to Section 4.2, “The generate_recipes_changelog command” command overview for
details.
8.3 Integration in OBS source service #
The Keg distribution contains a module for integrating with the Open Build Service, an implementation of a so-called OBS Source Service. It supports automatic changelog generation. See Section 9, “Automating image descriptions with the OBS Source Service” for details.
9 Automating image descriptions with the OBS Source Service #
The OBS Source Service for Keg provides a
mechanism to produce kiwi image descriptions
for use with the Open
Build Service in an automated fashion. The OBS
Source Service, named
compose_kiwi_description, checks out any
given keg-recipes repositories, runs
keg to produce the specified image
description, and optionally produces changelog files and stores
the HEAD commit hashed of the keg-recipes
repositories to be used for the next source service run.
To set up an OBS package as a Keg source service package, simply
create a file named _service in your package
directory. The contents of the file should look like the
following:
<services>
<service name="compose_kiwi_description">
<param name="git-recipes">https://github.com/SUSE-Enceladus/keg-recipes.git</param>
<param name="git-branch">released</param>
<param name="image-source">cross-cloud/sles/byos/15-sp3</param>
</service>
</services>
In this example, the released branch of the
public keg-recipes repository for SUSE Linux
Enterprise images hosted on GitHub is used as the source, and the
selected image source is
cross-cloud/sles/byos/15-sp3. Running the
source service will produce a description for a SUSE Linux
Enterprise Server 15 SP3 BYOS image for several cloud service
provider frameworks.
The parameters git-recipes and git-branch may be used multiple times if
the image description should be composed from more than one
repository.
There are a few additional optional parameters:
arch(string)Set the build target architecture. Can be used multiple times.
image-version(string)Set image version. If no version is given, the version number of the existing image description will be used with the patch level increased by one.
version-bump(true|false)Whether the patch version number should be incremented. Ignored if
--image-versionis set. If set tofalseand--image-versionis not set, the image version defined in the recipes will be used. If no image version is defined, image description generation will fail. Default istrue.update-changelogs(true|false)Whether
changes.yamlfiles should be updated. Default istrue.update-revisions(true|false)Whether
_keg_revisions(used for storing current commit IDs) should be updated. Default istrue.force(true|false)If true, refresh the image description even if there are no new commits. Default is
false.
The system on which the source service is running needs to have Keg
and obs-service-keg installed. Refer to the
Using
Source Services section of the OBS manual for details
on how to run the source service and which operating modes are
available.