Kiwi For Customizing Your Distro
About me
-
That longhaired linux guy.
What’s Kiwi?
-
"OS Image and Appliance Builder"
-
Linux distribution customizer
For these values of "distribution":
SUSE, SLES, RHEL, CentOS.
What kind of images?
-
VM disks: VMWare, KVM, VBox, LVM, Xen.
-
Docker! (recently added feature)
-
EC2 image, S3- or EBS-backed
-
OEM preload installations
-
PXE network install servers
-
Root over NFS, NBD, AoE
-
-
ISOs: bootable DVDs/CDs, memory sticks
-
Live systems and installers together
The build process
What you provide: an XML file, some shell scripts, overlay tree, tarballs.
Two steps: prepare, create.

The build process
Prepare step
-
Everything will be installed into one common directory, the "root" (chrooted)
-
Copies over files from overlay tree - e.g. your replacements for files in /etc, /home/…
-
Copies over archives (tarballs)
-
Runs your config.sh
Create step
-
Runs your images.sh
-
Builds the final image from the result.
config.xml
From the top…
<?xml version="1.0" encoding="utf-8"?>
<image schemaversion="6.1" name="wordpress-openSUSE-13.1" displayname="Wordpress">
<description type="system">
<author>Chris Riddoch</author>
<contact>riddochc@gmail.com</contact>
<specification>Wordpress VM</specification>
</description>
...
</image>
config.xml, inside <image>
<preferences>
<type checkprebuilt="true" boot="vmxboot/suse-13.1"
fsnocheck='true' image="vmx" filesystem="ext3" format="qcow2" bootloader="grub2">
<size unit="G" additive="true">1</size>
<machine arch="x86_64" memory="1024" guestOS="suse-64">
<vmdisk id="0" controller="ide"/>
<vmnic interface="0" driver="e1000" mode="bridged"/>
</machine>
</type>
config.xml, the <type> tag
- image="lxc"
-
linux container
- image="ext2|ext3|ext4|btrfs|squashfs|reiserfs|xfs"
-
a filesystem
- image="tbz"
-
just make a tarball from it
- image="cpio"
-
an initrd boot image.
- image="iso"
-
a live system for CD/DVD. flags=clic|seed|overlay|compressed
- image="oem"
-
virtual disk suitable for preload setting. lvm=… is useful here.
- image="pxe"
-
network boot image creation, pxedeploy=… goes with it.
- image="split"
-
divided across more than one image. e.g., separate homedir vm disk.
- image="vmx"
-
virtual disk. format=vmdk|qcow2|…, vga= for framebuffer, <machine> child element
config.xml, more of the <type> tag.
config.xml, moving on to the rest of <preferences>
<preferences>
...
<version>0.0.2</version>
<packagemanager>zypper</packagemanager>
<locale>en_US</locale>
<keytable>dvorak.map.gz</keytable>
<timezone>US/Mountain</timezone>
<hwclock>utc</hwclock>
<rpm-check-signatures>true</rpm-check-signatures>
<rpm-excludedocs>false</rpm-excludedocs>
<rpm-force>false</rpm-force>
</preferences>
config.xml, users
<users group="root">
<!-- changeme -->
<user name="root" home="/root" shell="/bin/bash" password="JQnXXR4jv21oU"/>
</users>
<users group="users">
<!-- changeme -->
<user name="webdev" home="/home/webdev" shell="/bin/zsh" password="bW9OlN0deb4cc"/>
</users>
config.xml: repository references
<repository type='rpm-md'>
<source path="http://software.syntacticsugar.org/opensuse/13.1/update/"/>
<!-- <source path='http://download.opensuse.org/update/13.1/'/> -->
</repository>
<repository type='yast2'>
<source path="http://software.syntacticsugar.org/opensuse/13.1/oss/"/>
<!-- <source path='http://download.opensuse.org/distribution/13.1/repo/oss/'/> -->
</repository>
config.xml: package selection
<packages type="image" patternType="onlyRequired">
<package name="aaa_base"/>
<package name="patterns-openSUSE-base"/>
...
<package name='apache2'/>
<package name='mariadb'/>
<package name="php5-fpm"/>
<package name="php5-zlib"/>
</packages>
config.xml: packages when?
<packages type="bootstrap">
<package name="filesystem"/>
<package name="glibc-locale"/>
<package name="module-init-tools"/>
</packages>
<packages type="delete">
<package name="wallpaper-branding-basedonopensuse"/>
</packages>
And finally…
</image>
That was the hard part
Remember, you can generate XML. Also, a brief plug for Suse Studio, http://susestudio.com/

You can also export from suse studio and build locally.
Stepping back
The first part of the build process, the "prepare" step:
-
Everything will be installed into one common directory, the "root" (chrooted)
-
Copies over files from overlay tree - e.g. your replacements for files in /etc, /home/…
-
Copies over archives (tarballs)
-
Runs your config.sh
Running the prepare
-
Overlay tree is in ./root (the default)
-
Chrooted tree to go in ./wordpress-root
kiwi --prepare . --root wordpress-root
Oh, wait, config.sh
The last step of the prepare phase.
The primary intended use of this script is to complete system configuration such as service activation. For detailed description pre-defined configuration functions consult the kiwi::config.sh(1) man page."
The second part: create.
-
Runs your images.sh
-
Builds the final image from the result.
At the beginning of the image creation process the optional images.sh script is executed at the top level of the unpacked image directory. Unlike the config.sh script, the images.sh script does not have a target use case. The script is most often used to remove files that are no needed in the final image.
Okay, finally!
A demo!
Reminder to self:
-
ifup tap0, br0, dnsmasq, firewall
-
show and explain these files:
-
My little makefile
-
config.sh
-
images.sh
-
root/studio/firstboot.sh
-
root/etc/apache2/default-server.conf
-
Just scratching the surface!
Could be combined with puppet, chef, salt, ansible, cfengine, etc. etc.
Notes on my setup
-
Local mirror of SUSE packages makes all the difference
-
Local git server, for VMs to download stuff.
-
dnsmasq so VMs are identified by mac address, provided IPs by dhcp
-
VM uses tap0, to virtual bridge br0, masqueraded to outside.
Thanks!
Any questions?