M pmb/config/__init__.py => pmb/config/__init__.py +3 -3
@@ 696,9 696,9 @@ apkbuild_package_attributes = {
"install": {"array": True},
"triggers": {"array": True},
- # UI meta-packages can specify apps in "_pmb_recommends" to be explicitly
- # installed by default, and not implicitly as dependency of the UI meta-
- # package ("depends"). This makes these apps uninstallable, without
+ # Packages can specify soft dependencies in "_pmb_recommends" to be
+ # explicitly installed by default, and not implicitly as a hard dependency
+ # of the package ("depends"). This makes these apps uninstallable, without
# removing the meta-package. (#1933). To disable this feature, use:
# "pmbootstrap install --no-recommends".
"_pmb_recommends": {"array": True},
M pmb/install/_install.py => pmb/install/_install.py +41 -2
@@ 1054,6 1054,44 @@ def get_selected_providers(args, packages):
return providers
+def get_recommends(args, packages):
+ """
+ Look through the specified packages and collect additional packages
+ specified under _pmb_recommends in them. This is recursive, so it will
+ dive into packages that are listed under recommends to collect any
+ packages they might also have listed under their own _pmb_recommends.
+
+ If running with pmbootstrap install --no-recommends, this function
+ returns an empty list.
+
+ :returns: list of pkgnames, e.g. ["chatty", "gnome-contacts"] """
+ ret = []
+ if not args.install_recommends:
+ return ret
+
+ for package in packages:
+ # Note that this ignores packages that don't exist. This means they
+ # aren't in pmaports. This is fine, with the assumption that
+ # installation will fail later in some other method if they truly don't
+ # exist in any repo.
+ apkbuild = pmb.helpers.pmaports.get(args, package, must_exist=False)
+ if not apkbuild:
+ continue
+ if package in apkbuild["subpackages"]:
+ # Just focus on the subpackage
+ apkbuild = apkbuild["subpackages"][package]
+ recommends = apkbuild["_pmb_recommends"]
+ if recommends:
+ logging.debug(f"{package}: install _pmb_recommends:"
+ f" {', '.join(recommends)}")
+ ret += recommends
+ # Call recursively in case recommends have pmb_recommends of their
+ # own.
+ ret += get_recommends(args, recommends)
+
+ return ret
+
+
def create_device_rootfs(args, step, steps):
# List all packages to be installed (including the ones specified by --add)
# and upgrade the installed packages/apkindexes
@@ 1082,8 1120,6 @@ def create_device_rootfs(args, step, steps):
if args.ui.lower() != "none":
if args.ui_extras:
install_packages += ["postmarketos-ui-" + args.ui + "-extras"]
- if args.install_recommends:
- install_packages += pmb.install.ui.get_recommends(args)
if args.extra_packages.lower() != "none":
install_packages += args.extra_packages.split(",")
if args.add:
@@ 1112,6 1148,9 @@ def create_device_rootfs(args, step, steps):
pmb.helpers.repo.update(args, args.deviceinfo["arch"])
+ # Install uninstallable "dependencies" by default
+ install_packages += get_recommends(args, install_packages)
+
# Explicitly call build on the install packages, to re-build them or any
# dependency, in case the version increased
if args.build_pkgs_on_install:
M pmb/install/ui.py => pmb/install/ui.py +0 -30
@@ 5,36 5,6 @@ import logging
import pmb.helpers.pmaports
-def get_recommends(args):
- """ Get all packages listed in _pmb_recommends of the UI and UI-extras
- package, unless running with pmbootstrap install --no-recommends.
-
- :returns: list of pkgnames, e.g. ["chatty", "gnome-contacts"] """
- ret = []
- if not args.install_recommends or args.ui == "none":
- return ret
-
- # UI package
- meta = f"postmarketos-ui-{args.ui}"
- apkbuild = pmb.helpers.pmaports.get(args, meta)
- recommends = apkbuild["_pmb_recommends"]
- if recommends:
- logging.debug(f"{meta}: install _pmb_recommends:"
- f" {', '.join(recommends)}")
- ret += recommends
-
- # UI-extras subpackage
- meta_extras = f"{meta}-extras"
- if args.ui_extras and meta_extras in apkbuild["subpackages"]:
- recommends = apkbuild["subpackages"][meta_extras]["_pmb_recommends"]
- if recommends:
- logging.debug(f"{meta_extras}: install _pmb_recommends:"
- f" {', '.join(recommends)}")
- ret += recommends
-
- return ret
-
-
def get_groups(args):
""" Get all groups to which the user additionally must be added.
The list of groups are listed in _pmb_groups of the UI and