Commit graph

202 commits

Author SHA1 Message Date
Tom Gundersen
fc838a8e20 stages: add test stage
Adds a new systemd unit to the image that will be pulled in by default,
run a given command, forward the output to a virtio serial port and
shutdown the machine.

We add a sample that uses this to verify that systemd conciders the
machine successfully booted. A simple way to run this test from the
commandline is to use
  `$ socat UNIX-LISTEN:qemu.sock -`
to listen for either `running` for success or `degraded` or
`maintenance` for failure.

The image should then be booted using something like
  `$ qemu-kvm -m 1024 -nographic -monitor none -serial none -chardev socket,path=qemu.sock,id=char0 -device virtio-serial -device virtserialport,chardev=char0,id=test0 -snapshot  base.qcow2`

Signed-off-by: Tom Gundersen <teg@jklm.no>
2019-08-29 10:25:15 +02:00
Tom Gundersen
a914627c89 stages: add debug shell
This gives shell access into the image on a given tty. Useful for
testing and debugging, while minimally affecting the image.

Note that this must never be used in production, as it allows root
access without a password.

For instance this could be used to verify that an image was fully
booted:

```
[teg@teg-x270 osbuild]$ qemu-kvm -m 1024 -nographic -serial mon:stdio -snapshot  base.qcow2
sh-5.0# systemctl is-system-running --wait
running
```

Signed-off-by: Tom Gundersen <teg@jklm.no>
2019-08-27 23:32:04 +03:00
Tom Gundersen
53fe311bcd assembler/qcow2: copy the tree into the target image
We used to let mkfs.ext4 initialize the filesystem for us, but it
turns out that the metadata attributes of the root directory were
not being initialized from the source tree. In particular, this
meant that the SELinu labels were left as unconfined_t, rather
than root_t, which would not allow us to boot in enforcing mode.

An alternative approach might be to fixup the root inode manually,
while still doing the rest using mkfs.ext4, but let's leave that
for the future if it turns out to be worth it.

Signed-off-by: Tom Gundersen <teg@jklm.no>
2019-08-26 09:25:42 +03:00
Tom Gundersen
5854ceea42 stages/grub2: make booting in ro/rw mode configurable
Move the decision whether the root fs should be mounted ro or rw
into the pipeline configuration.

Update the pipelines accordingly.

Signed-off-by: Tom Gundersen <teg@jklm.no>
2019-08-26 09:25:42 +03:00
Tom Gundersen
17d562e75f stages/fstab: add a stage to specify the fstab to be installed
This will allow us to boot in 'ro' mode, and remount later on.

Signed-off-by: Tom Gundersen <teg@jklm.no>
2019-08-26 09:25:42 +03:00
Tom Gundersen
8398be54a4 samples/base: install the same set of packages as anaconda would do
This makes comparison simpler.

Signed-off-by: Tom Gundersen <teg@jklm.no>
2019-08-26 09:25:42 +03:00
Tom Gundersen
9af32f1aae stages/dnf: make install_weak_deps optional
Default to True, which is what dnf defaults to, but allow it to be
overridden in the pipeline. Whether this option should be used should
be a distro policy, but for now we just want it to get images compatible
with the official fedora ones.

Signed-off-by: Tom Gundersen <teg@jklm.no>
2019-08-26 09:25:42 +03:00
Tom Gundersen
b348d858b8 stagse/dnf: don't make verbosity configurable
We don't want non-functional configuration in the pipelne, we want to
restrict ourselves to options that changes the final image.

Signed-off-by: Tom Gundersen <teg@jklm.no>
2019-08-26 09:25:42 +03:00
Tom Gundersen
679b79c5e5 osbuild: split package into separate files
Import modules between files using the syntax `from . import foobar`,
renaming what used to be `FooBar` to `foobar.FooBar` when moved to a
separate file.

In __init__.py only import what is meant to be public API.

Signed-off-by: Tom Gundersen <teg@jklm.no>
2019-08-21 09:56:50 +04:00
Lars Karlitski
f54fbe2912 stages/fix-bls: add workaround for grub2-mkrelpath
grub2-mkrelpath uses /proc/self/mountinfo to find the source of the file
system it is installed to. This breaks in a container.

Add org.osbuild.fix-bls which goes through /boot/loader/entries and
fixes paths by removing anything before /boot.
2019-08-15 09:43:28 +03:00
Lars Karlitski
29c396584f stages/dnf: use nspawn's vfs tree
dracut stumbled over the one we set up (errors about not being able to
access /dev/kmsg). Use the one that systemd-nspawn sets up instead.
2019-08-14 13:49:27 +02:00
Tom Gundersen
9741087e92 Stage/init: fix the order of arguments
Make the order of argumnets in line with how it is used (and also
how it is conceptionally closer to the pipeline json document).

This makes no practical difference as the two arguments were both
just used for computing the hash.

Signed-off-by: Tom Gundersen <teg@jklm.no>
2019-08-13 17:13:13 +02:00
Tom Gundersen
6d7cd1b93c Pipeline: drop the base concept
Each pipeline is now self-contained without references to another.
However, as the final stage in a pipeline is saved to the content
store, we are able to reuse it if one pipeline is the prefix of
another, as described in the previous commit. This makes the
concept of a base redundant.

The ObjectStore must take a directory as argument, never None, so
the conditional assertion for this in Pipeline.run() is ok to
remove.

Signed-off-by: Tom Gundersen <teg@jklm.no>
2019-08-13 17:13:13 +02:00
Tom Gundersen
67da9e0cca Pipeline: reuse existing trees if they exist in the object store
Don't do this only for the base, but for any prefix of the current
pipeline.

Note that if two pipelines share a prefix, but one is not the prefix
of another, no sharing is possible. Only a proper prefix can be
reused by another pipeline, as only the result of the last pipeline
is saved to the object store (this restriction could be changed in
the future).

Signed-off-by: Tom Gundersen <teg@jklm.no>
2019-08-13 17:13:13 +02:00
Tom Gundersen
0a9223b6f2 Pipeline: drop the build setter
Take this as an argumnet to __init__ in the same way that `base`
is.

This avoids us having to deal with the case of someone setting a
stage before the build, which does not work as the stage id will
be wrong.

Signed-off-by: Tom Gundersen <teg@jklm.no>
2019-08-13 17:13:13 +02:00
Martin Sehnoutka
ea68bb0c26 Test refactoring
The testing script is getting too big and not very well organized. In
this commit a new module `integration_tests` is introduced that contains
parts of the original testing script split into multiple files. The
content should be the same, the only difference is that now you can run
the tests by invoking `python3 -m test`.
2019-08-13 15:14:58 +02:00
Martin Sehnoutka
c27cdd5928 introduce hostname stage
this stage will set /etc/hostname in the image. it uses
systemd-firstboot to perform the change
2019-08-13 13:24:36 +02:00
Lars Karlitski
4c91a23e98 stages/org.osbuild.users: manage users
This stage allows to add or modify users. For now, this includes all
fields available in passwd, setting auxiliary groups, and setting an ssh
key.

Based on a patch by Martin Sehnoutka <msehnout@redhat.com>.
2019-08-12 13:45:30 +02:00
Lars Karlitski
a394e975c1 stages/dnf: supress error from completion module
Disable the module. There's no need to update the completion databse in
the container.
2019-08-12 13:07:11 +02:00
Lars Karlitski
68832d2aaf osbuild: check for right errno from os.rename()
Renaming a directory over an existing one is only an error if the
existing one is not empty, in which case ENOEMPTY is thrown.

Tested with:

    >>> os.mkdir("foo")
    >>> os.mkdir("bar")
    >>> os.rename("foo", "bar")
    # no error

    >>> open("foo/a", "w").write("a")
    1
    >>> try: os.rename("bar", "foo")
    ... except OSError as e: e.errno == errno.ENOTEMPTY
    ...
    True
2019-08-12 13:06:18 +02:00
Lars Karlitski
054fea3d83 osbuild: add description() methods
We already allow loading from a description. This adds the opposite
direction to export Pipelines, Stages, and Assemblers.
2019-08-07 10:01:17 +02:00
Lars Karlitski
ec671ddc04 .gitignore: add additional directories to ignore
Also split into list of global patterns and full paths.
2019-08-07 10:01:17 +02:00
msehnout
dc1466eeca
introduce firewall stage (#61)
as described in lorax documentation, we need to support raw
ports/protocols and services as defined by firewalld:
https://weldr.io/lorax/lorax-composer.html#customizations-firewall
2019-08-07 09:34:22 +02:00
Tom Gundersen
9371eb9eaa ObjectStore/get_tree: make sure to clean up the context manager
Even if the yield raises an exception, we must always unmount to
clean up.

Signed-off-by: Tom Gundersen <teg@jklm.no>
2019-08-02 01:05:47 +02:00
Tom Gundersen
dcc9384ba8 Pipeline: add support for a build pipeline
The build pipeline, is a sub-pipeline used to generate the build
tree to use rather than the current root directory. This can be
nested arbitrarily deep, but ultimately we will fall back to the
current logic when no build property is found.

Just like the tree after the last stage of a regular pipeline ends
up in the object store, so does currently each build tree (as the
build sub-pipeline really is just a regular pipeline in its own
right). We may want to avoid both these instances of the implicit
storing semantics, and rather make it something the caller opts-in
to. However, for now that is left as a future optimization.

Signed-off-by: Tom Gundersen <teg@jklm.no>
2019-08-02 00:57:28 +02:00
Tom Gundersen
3669978577 osbuild-run: remove any /etc/nsswitch.conf
On some hosts, systemd-tmpfiles will generate an nsswitch.conf
configuring DNS to be done via systemd-resolved, but this will
require the container to be booted and resolved to be running.

In other cases, a proper fall-back is configured, so this is not
a problem, but on some hosts this means DNS does not work.

Conversely, the default behavior with no nsswitch.conf at all
works just fine, always using nss-dns.

Let's simply delete the file if it is there, and rely on the
default.

Signed-off-by: Tom Gundersen <teg@jklm.no>
2019-08-02 00:57:28 +02:00
Tom Gundersen
7c7fcecd47 ObjectStore: add an object store class
This also changes the structure of the object store, though the
basic idea is the same.

The object store contains a directory of objects, which are content
addressable filesystem trees. Currently we only ever use their
content-hash internally, but the idea for this is basically Lars
Karlitski and Kay Sievers' `treesum()`. We may exopse this in the
future.

Moreover, it contains a directory of refs, which are symlinks named
by the stage id they correspond to (as before), pointing to an object
generated from that stage-id.

The ObjectStore exposes three method:
`has_tree()`: This checks if the content store contains the given tree.
If so, we can rely on the tree remaining there.
`get_tree()`: This is meant to be used with a `with` block and yields
the path to a read-only instance of the tree with the given id. If the
tree_id is passed in as None, an empty directory is given instead.
`new_tree()`: This is meant to be used with a `with` block and yields
the path to a directory in which the tree by the given id should be
created. If a base_id is passed in, the tree is initialized with the
tree with the given id. Only when the block is exited successfully
is the tree written to the content store, referenced by the id in
question.

Use this in Pipeline.run() to avoid regenerating trees unneccessarily.
In order to trigger a regeneration, the content store must currently
be manually flushed.

Update the travis test to run the noop pipeline twice, verifying that
the stage is only run the first time.

Signed-off-by: Tom Gundersen <teg@jklm.no>
2019-08-01 22:39:52 +02:00
Tom Gundersen
5eaa553563 BuildRoot: require the root directory to be passed in
Rather than hard-coding this to /, let the caller provide the
directory path to use.

In the past, we needed to give special treatment to /, as it had
to be bind-mounted before being used by nspawn, to work around a
check they had, refusing to use the host root in the container.

We no longer pass the directory directly to nspawn, but rather
mount the subdirs we want ourselves, so that no longer applies.

The callers pass in /, so the behavior is unchanged.

Signed-off-by: Tom Gundersen <teg@jklm.no>
2019-08-01 22:39:52 +02:00
Martin Sehnoutka
834823f131 detect version in makefile, change name of produced tarballs 2019-08-01 16:17:11 +02:00
Martin Sehnoutka
3bbe17073d download sources from github as <name>-<version>.tar.gz
packit produces tarballs with this name, so it is easier to download
them from github like this
2019-08-01 16:17:11 +02:00
Martin Sehnoutka
97abdbed39 enable copr builds triggered in pull-requests
packit provide us with possibility to automatically build RPM package
for each PR, this configuration change enable the feature
2019-08-01 16:17:11 +02:00
Martin Sehnoutka
28e33c07ce introduce support for user-defined kernel options 2019-08-01 14:59:37 +02:00
Martin Sehnoutka
a095eb01c3 add packit config
packit is a service for continous delivery into Fedora repositories. It
should help us synchronize upstream repository on Github with downstream
repository on src.fedoraproject.org.
2019-07-31 17:38:03 +02:00
Tom Gundersen
faaa5ffa10 travis: test rpm generation
Signed-off-by: Tom Gundersen <teg@jklm.no>
2019-07-31 01:34:31 +02:00
Tom Gundersen
ef31294505 travis: only install relevant dependencies for each job
This speeds up the simple tests considerably.

Signed-off-by: Tom Gundersen <teg@jklm.no>
2019-07-31 01:34:31 +02:00
Tom Gundersen
8b659ae638 travis: add a test for a yum-based pipeline
Travis uses Ubuntu, which does not ship dnf, so introduce a yum
stage that allows us to test actual generation of trees on Travis.

We use this to generate a tree containing the tools necessary to
create abritrary Fedora-based build images in the future. We base
this on Fedora 27, as that is the last version that is installable
using yum rather than dnf.

In the future, once we support pipelines with nested build-images,
rather than just using the host OS as the build image, this will
allow us to bootstrap arbitrary pipelines on Travis.

Signed-off-by: Tom Gundersen <teg@jklm.no>
2019-07-31 01:34:31 +02:00
Tom Gundersen
fa7a5b985e travis: add an osbuild test
Actually test the tools. This simply runs a noop stage followed by
a noop assembler.

Signed-off-by: Tom Gundersen <teg@jklm.no>
2019-07-31 01:34:31 +02:00
Tom Gundersen
659ce42c83 BuildRoot: don't use nspawn's --volatile mode
We want the same functionality, but we now impleent it ourselves.

In addition to bind-mounting in /usr into the target container
(which is all nspawn does), we also add /bin, /sbin, /lib and
/lib64, if they exist and are not symlinks (presuambly into
/usr).

This means we can work on distros who have not implemented the
usr-move, like Ubuntu Bionic (used by Travis).

Signed-off-by: Tom Gundersen <teg@jklm.no>
2019-07-31 01:34:31 +02:00
Tom Gundersen
52e2374bb6 travis: run osbuild-run through pylint
This was most likely an oversight.

Signed-off-by: Tom Gundersen <teg@jklm.no>
2019-07-31 01:34:31 +02:00
Tom Gundersen
fd72ed80ba osbuild-run: generate SSL certificates also on Debian-based systems
Call update-ca-certificates if the binary is found, generating SSL
certificates in /etc in i similar way on Debian-based systems as
is being done on RedHat-based ones.

Signed-off-by: Tom Gundersen <teg@jklm.no>
2019-07-31 01:34:31 +02:00
Tom Gundersen
d08aed8f12 osbuild-run: make update-ca-trust optional
This is a RHism, that is not available on Debian-based systems.
Do not make it a hard reqirement, as pipelines may be able to
function just fine without it.

In a follow-up commit we will also check for the Debian-based
equivalent.

Signed-off-by: Tom Gundersen <teg@jklm.no>
2019-07-31 01:34:31 +02:00
Tom Gundersen
9fa827ab04 osbuild-run: refactor into functions
Prepare for follow-up patches adding more functionality.

Signed-off-by: Tom Gundersen <teg@jklm.no>
2019-07-31 01:34:31 +02:00
Martin Sehnoutka
0cf93934eb unify messages about files to be removed 2019-07-29 20:13:36 +02:00
Martin Sehnoutka
1ca4d8e6bb introduce keymap stage 2019-07-29 12:39:38 +02:00
Lars Karlitski
2e0981f1ab qcow2: remove partition_table_id
It's not necessary to specify it.
2019-07-29 12:39:10 +02:00
Martin Sehnoutka
593c6de385 add timezone stage 2019-07-29 12:05:42 +02:00
Martin Sehnoutka
693cd4e6b0 drop Darwin support, noone uses it anymore 2019-07-29 12:05:42 +02:00
Martin Sehnoutka
0812baa352 update url in the specfile 2019-07-29 09:41:28 +02:00
Lars Karlitski
4ebdc33e5e samples: fix base ids
I broke them with the io.weldr → org.osbuild move.
2019-07-28 21:27:26 +02:00
Tom Gundersen
4cb424acf7 travis: move to bionic
Let's always use the latest available Ubuntu release for our CI, we
are interested in potentially building old images, and using old
images as bulid images, but having an old distro as host is not
necessarily an aim. If we want to test with a greater diversity of
distros (which we do), we should do that in VM's, this should just
be for the simple/quick case.

Also restructure a bit to allow for more (named) tests.

Signed-off-by: Tom Gundersen <teg@jklm.no>
2019-07-27 11:49:04 +02:00