if f"{prefix}_SCOPE" not in extrelease:
f.write(
f"{prefix}_SCOPE="
- f"{context.config.environment.get(f'{prefix}_SCOPE', 'initrd system portable')}\n"
+ f"{context.config.finalize_environment().get(f'{prefix}_SCOPE', 'initrd system portable')}\n"
)
if "ARCHITECTURE" not in extrelease:
with complete_step(f"Running configure script {script}…"):
result = run(
["/work/configure"],
- env=env | config.environment,
+ env=env | config.finalize_environment(),
sandbox=config.sandbox(
options=[
"--dir", "/work/src",
with complete_step(f"Running sync script {script}…"):
run(
["/work/sync", "final"],
- env=env | config.environment,
+ env=env | config.finalize_environment(),
stdin=sys.stdin,
sandbox=config.sandbox(
network=True,
network: bool,
) -> Iterator[list[PathString]]:
options = ["--dir", "/work/src", "--chdir", "/work/src", *options]
- suppress_chown = parse_boolean(context.config.environment.get("MKOSI_CHROOT_SUPPRESS_CHOWN", "0"))
+ suppress_chown = parse_boolean(
+ context.config.finalize_environment().get("MKOSI_CHROOT_SUPPRESS_CHOWN", "0")
+ )
helpers = {
"mkosi-chroot": [
if context.config.profiles:
env["PROFILES"] = " ".join(context.config.profiles)
- env |= context.config.environment
+ env |= context.config.finalize_environment()
with (
mount_build_overlay(context) if build else contextlib.nullcontext(),
CHROOT_BUILDDIR="/work/build",
)
- env |= context.config.environment
+ env |= context.config.finalize_environment()
with (
mount_build_overlay(context, volatile=True),
if context.config.build_dir is not None:
env |= dict(BUILDDIR="/work/build")
- env |= context.config.environment
+ env |= context.config.finalize_environment()
with (
finalize_source_mounts(
if context.config.build_dir is not None:
env |= dict(BUILDDIR="/work/build")
- env |= context.config.environment
+ env |= context.config.finalize_environment()
with (
finalize_source_mounts(
with complete_step(f"Running post-output script {script}…"):
run(
["/work/postoutput"],
- env=env | context.config.environment,
+ env=env | context.config.finalize_environment(),
sandbox=context.sandbox(
# postoutput scripts should run as (fake) root so that file ownership is
# always recorded as if owned by root.
else subprocess.DEVNULL
),
stdout=stdout,
- env=context.config.environment,
+ env=context.config.finalize_environment(),
sandbox=context.sandbox(
options=[*opt, *options],
devices=context.config.secure_boot_key_source.type != KeySourceType.file,
workdir(context.staging / context.config.output_checksum),
]
- home = Path(context.config.environment.get("GNUPGHOME", INVOKING_USER.home() / ".gnupg"))
+ home = Path(context.config.finalize_environment().get("GNUPGHOME", INVOKING_USER.home() / ".gnupg"))
if not home.exists():
die(f"GPG home {home} not found")
):
run(
[context.config.openpgp_tool, "sign", "/signing-key.pgp"],
- env=context.config.environment,
+ env=context.config.finalize_environment(),
stdin=i,
stdout=o,
sandbox=context.sandbox(
workdir(fname),
],
stdin=sys.stdin,
- env=config.environment,
+ env=config.finalize_environment(),
sandbox=config.sandbox(
network=True,
devices=True,
cmdline,
stdin=sys.stdin,
stdout=sys.stdout,
- env=os.environ | config.environment,
+ env=os.environ | config.finalize_environment(),
log=False,
sandbox=config.sandbox(
devices=True,
[tool_path, "--root" if output.is_dir() else "--image", output, *args.cmdline],
stdin=sys.stdin,
stdout=sys.stdout,
- env=os.environ | config.environment,
+ env=os.environ | config.finalize_environment(),
log=False,
sandbox=config.sandbox(
network=True,
with complete_step(f"Running clean script {script}…"):
run(
["/work/clean"],
- env=env | config.environment,
+ env=env | config.finalize_environment(),
sandbox=config.sandbox(
tools=False,
options=[
return run(
cmdline,
stdout=stdout,
- env={**config.environment, **env},
+ env={**config.finalize_environment(), **env},
sandbox=config.sandbox(options=options, devices=devices),
)
cmd,
stdin=(sys.stdin if key_source.type != KeySourceType.file else subprocess.DEVNULL),
stdout=stdout,
- env={**config.environment, **env},
+ env={**config.finalize_environment(), **env},
sandbox=config.sandbox(
options=opt,
devices=(
if context.config.secure_boot_key_source.type != KeySourceType.file
else subprocess.DEVNULL
),
- env=context.config.environment,
+ env=context.config.finalize_environment(),
sandbox=context.sandbox(
options=options,
devices=context.config.secure_boot_key_source.type != KeySourceType.file,
cmd,
stdin=sys.stdin,
stdout=sys.stdout,
- env=os.environ | config.environment,
+ env=os.environ | config.finalize_environment(),
log=False,
sandbox=config.sandbox(
devices=True,
image: Optional[str]
+ def finalize_environment(self) -> dict[str, str]:
+ env = {
+ "SYSTEMD_TMPFILES_FORCE_SUBVOL": "0",
+ "SYSTEMD_ASK_PASSWORD_KEYRING_TIMEOUT_SEC": "infinity",
+ "SYSTEMD_ASK_PASSWORD_KEYRING_TYPE": "session",
+ "TERM": finalize_term(),
+ }
+
+ if self.image is not None:
+ env["SUBIMAGE"] = self.image
+ if self.image_id is not None:
+ env["IMAGE_ID"] = self.image_id
+ if self.image_version is not None:
+ env["IMAGE_VERSION"] = self.image_version
+ if self.source_date_epoch is not None:
+ env["SOURCE_DATE_EPOCH"] = str(self.source_date_epoch)
+ if self.proxy_url is not None:
+ for e in ("http_proxy", "https_proxy"):
+ env[e] = self.proxy_url
+ env[e.upper()] = self.proxy_url
+ if self.proxy_exclude:
+ env["no_proxy"] = ",".join(self.proxy_exclude)
+ env["NO_PROXY"] = ",".join(self.proxy_exclude)
+ if self.proxy_peer_certificate:
+ env["GIT_PROXY_SSL_CAINFO"] = "/proxy.cacert"
+ if self.proxy_client_certificate:
+ env["GIT_PROXY_SSL_CERT"] = "/proxy.clientcert"
+ if self.proxy_client_key:
+ env["GIT_PROXY_SSL_KEY"] = "/proxy.clientkey"
+ if dnf := os.getenv("MKOSI_DNF"):
+ env["MKOSI_DNF"] = dnf
+ if gnupghome := os.getenv("GNUPGHOME"):
+ env["GNUPGHOME"] = gnupghome
+
+ env |= dict(
+ parse_environment(line)
+ for f in self.environment_files
+ for line in f.read_text().strip().splitlines()
+ )
+ env |= self.environment
+
+ return env
+
def name(self) -> str:
return self.image or self.image_id or "default"
return term if sys.stderr.isatty() else "dumb"
-def load_environment(args: argparse.Namespace) -> dict[str, str]:
- env = {
- "SYSTEMD_TMPFILES_FORCE_SUBVOL": "0",
- "SYSTEMD_ASK_PASSWORD_KEYRING_TIMEOUT_SEC": "infinity",
- "SYSTEMD_ASK_PASSWORD_KEYRING_TYPE": "session",
- "TERM": finalize_term(),
- }
-
- if args.image is not None:
- env["SUBIMAGE"] = args.image
- if args.image_id is not None:
- env["IMAGE_ID"] = args.image_id
- if args.image_version is not None:
- env["IMAGE_VERSION"] = args.image_version
- if args.source_date_epoch is not None:
- env["SOURCE_DATE_EPOCH"] = str(args.source_date_epoch)
- if args.proxy_url is not None:
- for e in ("http_proxy", "https_proxy"):
- env[e] = args.proxy_url
- env[e.upper()] = args.proxy_url
- if args.proxy_exclude:
- env["no_proxy"] = ",".join(args.proxy_exclude)
- env["NO_PROXY"] = ",".join(args.proxy_exclude)
- if args.proxy_peer_certificate:
- env["GIT_PROXY_SSL_CAINFO"] = "/proxy.cacert"
- if args.proxy_client_certificate:
- env["GIT_PROXY_SSL_CERT"] = "/proxy.clientcert"
- if args.proxy_client_key:
- env["GIT_PROXY_SSL_KEY"] = "/proxy.clientkey"
- if dnf := os.getenv("MKOSI_DNF"):
- env["MKOSI_DNF"] = dnf
- if gnupghome := os.getenv("GNUPGHOME"):
- env["GNUPGHOME"] = gnupghome
-
- env |= dict(
- parse_environment(line)
- for f in args.environment_files
- for line in f.read_text().strip().splitlines()
- )
- env |= args.environment
-
- return env
-
-
def load_args(args: argparse.Namespace) -> Args:
if args.cmdline and not args.verb.supports_cmdline():
die(f"Arguments after verb are not supported for {args.verb}.")
):
config.build_dir /= f"{config.distribution}~{config.release}~{config.architecture}"
- config.environment = load_environment(config)
-
return Config.from_namespace(config)
# For EPEL we make the assumption that epel is mirrored in the parent directory of the mirror
# URL and path we were given. Since this doesn't work for all scenarios, we also allow
# overriding the mirror via an environment variable.
- url = context.config.environment.get("EPEL_MIRROR", join_mirror(mirror, "../fedora"))
+ url = context.config.finalize_environment().get(
+ "EPEL_MIRROR", join_mirror(mirror, "../fedora")
+ )
yield RpmRepository(
repo,
f"baseurl={url}/{dir}/$releasever/Everything/$basearch",
"SYSTEMD_IN_CHROOT": "1",
}
- if "SYSTEMD_HWDB_UPDATE_BYPASS" not in context.config.environment:
+ if "SYSTEMD_HWDB_UPDATE_BYPASS" not in context.config.finalize_environment():
env["SYSTEMD_HWDB_UPDATE_BYPASS"] = "1"
if (
- "KERNEL_INSTALL_BYPASS" not in context.config.environment
+ "KERNEL_INSTALL_BYPASS" not in context.config.finalize_environment()
and context.config.bootable != ConfigFeature.disabled
):
env["KERNEL_INSTALL_BYPASS"] = "1"
"DEBCONF_INTERACTIVE_SEEN": "true",
}
- if "INITRD" not in context.config.environment and context.config.bootable != ConfigFeature.disabled:
+ if (
+ "INITRD" not in context.config.finalize_environment()
+ and context.config.bootable != ConfigFeature.disabled
+ ):
env["INITRD"] = "No"
return super().finalize_environment(context) | env
@classmethod
def executable(cls, config: Config) -> str:
# Allow the user to override autodetection with an environment variable
- dnf = config.environment.get("MKOSI_DNF")
+ dnf = config.finalize_environment().get("MKOSI_DNF")
return Path(dnf or config.find_binary("dnf5") or "dnf").name
@classmethod
with tempfile.NamedTemporaryFile(dir="/var/tmp", prefix="mkosi-scratch-") as scratch:
scratch.truncate(1024**4)
fs = config.distribution.filesystem()
- extra = config.environment.get(f"SYSTEMD_REPART_MKFS_OPTIONS_{fs.upper()}", "")
+ extra = config.finalize_environment().get(f"SYSTEMD_REPART_MKFS_OPTIONS_{fs.upper()}", "")
run(
[f"mkfs.{fs}", "-L", "scratch", "-q", *extra.split(), workdir(Path(scratch.name))],
sandbox=config.sandbox(options=["--bind", scratch.name, workdir(Path(scratch.name))]),
services = json.loads(
run(
["busctl", "list", "--json=pretty"],
- env=os.environ | config.environment,
+ env=os.environ | config.finalize_environment(),
sandbox=config.sandbox(relaxed=True),
stdout=subprocess.PIPE,
).stdout.strip()
}
),
],
- env=os.environ | config.environment,
+ env=os.environ | config.finalize_environment(),
sandbox=config.sandbox(relaxed=True),
stdin=sys.stdin,
# Prevent varlinkctl's empty '{}' response from showing up in the terminal.
str(pid),
fname if fname.is_dir() else "",
], # fmt: skip
- env=os.environ | config.environment,
+ env=os.environ | config.finalize_environment(),
sandbox=config.sandbox(relaxed=True),
stdin=sys.stdin,
stdout=sys.stdout,
stdout=stdout,
stderr=stderr,
pass_fds=qemu_device_fds.values(),
- env=os.environ | config.environment,
+ env=os.environ | config.finalize_environment(),
sandbox=config.sandbox(
network=True,
devices=True,
cmd,
stdin=sys.stdin,
stdout=sys.stdout,
- env=os.environ | config.environment | {"SHELL": "/bin/bash"},
+ env=os.environ | config.finalize_environment() | {"SHELL": "/bin/bash"},
log=False,
sandbox=config.sandbox(
network=True,
cmd,
stdin=sys.stdin,
stdout=sys.stdout,
- env=os.environ | config.environment,
+ env=os.environ | config.finalize_environment(),
log=False,
sandbox=config.sandbox(
devices=True,
cmdline,
stdin=sys.stdin,
stdout=sys.stdout,
- env=env | config.environment,
+ env=env | config.finalize_environment(),
log=False,
sandbox=config.sandbox(
network=True,
}
# Only check values for keys from expected, as config.environment contains other items as well
- assert {k: config.environment[k] for k in expected.keys()} == expected
+ assert {k: config.finalize_environment()[k] for k in expected.keys()} == expected
assert config.environment_files == [Path.cwd() / "mkosi.env", Path.cwd() / "other.env"]