diff --git a/osbuild.spec b/osbuild.spec index 7757aa33..f4d0dff0 100644 --- a/osbuild.spec +++ b/osbuild.spec @@ -74,20 +74,23 @@ make man %py3_install mkdir -p %{buildroot}%{pkgdir}/stages -install -p -m 0755 $(find stages -type f) %{buildroot}%{pkgdir}/stages/ +install -p -m 0755 $(find stages/* -not -path "*/osbuild") %{buildroot}%{pkgdir}/stages/ +ln -s ../osbuild %{buildroot}%{pkgdir}/stages/osbuild mkdir -p %{buildroot}%{pkgdir}/assemblers -install -p -m 0755 $(find assemblers -type f) %{buildroot}%{pkgdir}/assemblers/ +install -p -m 0755 $(find assemblers/* -not -path "*/osbuild") %{buildroot}%{pkgdir}/assemblers/ +ln -s ../osbuild %{buildroot}%{pkgdir}/assemblers/osbuild mkdir -p %{buildroot}%{pkgdir}/runners -install -p -m 0755 $(find runners -type f -or -type l) %{buildroot}%{pkgdir}/runners +install -p -m 0755 $(find runners/* -not -path "*/osbuild") %{buildroot}%{pkgdir}/runners +ln -s ../osbuild %{buildroot}%{pkgdir}/runners/osbuild mkdir -p %{buildroot}%{pkgdir}/sources -install -p -m 0755 $(find sources -type f) %{buildroot}%{pkgdir}/sources +install -p -m 0755 $(find sources/* -not -path "*/osbuild") %{buildroot}%{pkgdir}/sources +ln -s ../osbuild %{buildroot}%{pkgdir}/sources/osbuild -# mount points for bind mounting the osbuild library -mkdir -p %{buildroot}%{pkgdir}/stages/osbuild -mkdir -p %{buildroot}%{pkgdir}/assemblers/osbuild +# mount point for bind mounting the osbuild library +mkdir -p %{buildroot}%{pkgdir}/osbuild # documentation mkdir -p %{buildroot}%{_mandir}/man1 diff --git a/osbuild/buildroot.py b/osbuild/buildroot.py index 03e8e09e..43b5bd45 100644 --- a/osbuild/buildroot.py +++ b/osbuild/buildroot.py @@ -1,4 +1,6 @@ +import importlib +import importlib.util import os import platform import shutil @@ -17,7 +19,7 @@ class BuildRoot: self.api = tempfile.mkdtemp(prefix="osbuild-api-", dir=path) self.var = tempfile.mkdtemp(prefix="osbuild-var-", dir=var) self.mounts = [] - self.libdir = libdir or "/usr/lib/osbuild" + self.libdir = libdir self.runner = runner self.mount_root(root) @@ -76,6 +78,8 @@ class BuildRoot: Its arguments mean the same as those for subprocess.run(). """ + nspawn_ro_binds = [] + # pylint suggests to epxlicitly pass `check` to subprocess.run() check = kwargs.pop("check", False) @@ -86,6 +90,30 @@ class BuildRoot: # wants to be able create devices nodes, so allow that loopback_allow += "m" + # make osbuild API-calls accessible to the container + nspawn_ro_binds.append(f"{self.api}:/run/osbuild/api") + + # We want to execute our stages and other scripts in the container. So + # far, we do not install osbuild as a package in the container, but + # provide it from the outside. Therefore, we need to provide `libdir` + # via bind-mount. Furthermore, a system-installed `libdir` has the + # python packages separate in `site-packages`, so we need to bind-mount + # them as well. + # In the future, we want to work towards mandating an osbuild package to + # be installed in the container, so the build is self-contained and does + # not take scripts from the host. However, this requires osbuild + # packaged for those containers. Furthermore, we want to keep supporting + # the current import-model for testing and development. + if self.libdir is not None: + # caller-specified `libdir` must be self-contained + nspawn_ro_binds.append(f"{self.libdir}:/run/osbuild/lib") + else: + # system `libdir` requires importing the python module + nspawn_ro_binds.append(f"/usr/lib/osbuild:/run/osbuild/lib") + modorigin = importlib.util.find_spec('osbuild').origin + modpath = os.path.dirname(modorigin) + nspawn_ro_binds.append(f"{modpath}:/run/osbuild/lib/osbuild") + return subprocess.run([ "systemd-nspawn", "--quiet", @@ -94,9 +122,9 @@ class BuildRoot: "--link-journal=no", f"--property=DeviceAllow=block-loop {loopback_allow}", f"--directory={self.root}", - f"--bind-ro={self.libdir}:/run/osbuild/lib", + *[f"--bind-ro={b}" for b in nspawn_ro_binds], *[f"--bind={b}" for b in (binds or [])], - *[f"--bind-ro={b}" for b in [f"{self.api}:/run/osbuild/api"] + (readonly_binds or [])], + *[f"--bind-ro={b}" for b in (readonly_binds or [])], f"/run/osbuild/lib/runners/{self.runner}" ] + argv, check=check, **kwargs) diff --git a/osbuild/pipeline.py b/osbuild/pipeline.py index ee6dd361..72109cd6 100644 --- a/osbuild/pipeline.py +++ b/osbuild/pipeline.py @@ -1,7 +1,5 @@ import hashlib -import importlib -import importlib.util import json import os import subprocess @@ -89,12 +87,6 @@ class Stage: sources_dir = f"{libdir}/sources" if libdir else "/usr/lib/osbuild/sources" ro_binds = [f"{sources_output}:/run/osbuild/sources"] - if not libdir: - osbuild_module_path = os.path.dirname(importlib.util.find_spec('osbuild').origin) - # This is a temporary workaround, once we have a common way to include osbuild in the - # buildroot we should remove this because it includes code from the host in the buildroot thus - # violating our effort of reproducibility. - ro_binds.append(f"{osbuild_module_path}:/run/osbuild/lib/stages/osbuild") with API(f"{build_root.api}/osbuild", args, interactive) as api, \ sources.SourcesServer(f"{build_root.api}/sources", @@ -151,13 +143,8 @@ class Assembler: binds.append(f"{output_dir}:/run/osbuild/output") args["output_dir"] = "/run/osbuild/output" - osbuild_module_path = os.path.dirname(importlib.util.find_spec('osbuild').origin) ro_binds = [f"{tree}:/run/osbuild/tree"] - if not libdir: - # This is a temporary workaround, once we have a common way to include osbuild in the - # buildroot we should remove this because it includes code from the host in the buildroot thus - # violating our effort of reproducibility. - ro_binds.append(f"{osbuild_module_path}:/run/osbuild/lib/assemblers/osbuild") + with remoteloop.LoopServer(f"{build_root.api}/remoteloop"), \ API(f"{build_root.api}/osbuild", args, interactive) as api: r = build_root.run( diff --git a/runners/osbuild b/runners/osbuild new file mode 120000 index 00000000..d41e248d --- /dev/null +++ b/runners/osbuild @@ -0,0 +1 @@ +../osbuild \ No newline at end of file diff --git a/sources/osbuild b/sources/osbuild new file mode 120000 index 00000000..d41e248d --- /dev/null +++ b/sources/osbuild @@ -0,0 +1 @@ +../osbuild \ No newline at end of file