rpmmd/dnf-json: support chain dependency solving
Add a new `rpmmdImpl` method `chainDepsolve`, which is able to depsolve multiple chained package sets as separate DNF transactions layered on top of each other. This new method allows to depsolve the `blueprint` package set on top of the base image package set (usually called `packages`). Introduce a helper function `chainPackageSets` for constructing arguments to the `chainDepsolve` method based on the provided arguments: - slice of package set names to chain as transactions - map of package sets - slice of system repositories used by all package sets - map of package-set-specific repositories Extend `dnf-json` with a new command `chain-depsolve` allowing to depsolve multiple transaction in a row, layered on top of each other. Add unit tests where appropriate.
This commit is contained in:
parent
0f0b2072d5
commit
d48da99a12
3 changed files with 611 additions and 0 deletions
57
dnf-json
57
dnf-json
|
|
@ -247,6 +247,59 @@ class Solver():
|
|||
"dependencies": dependencies
|
||||
}
|
||||
|
||||
def chain_depsolve(self, transactions):
|
||||
last_transaction = []
|
||||
|
||||
for idx, transaction in enumerate(transactions):
|
||||
self.base.reset(goal=True)
|
||||
self.base.sack.reset_excludes()
|
||||
|
||||
# don't install weak-deps for transactions after the 1st transaction
|
||||
if idx > 0:
|
||||
self.base.conf.install_weak_deps=False
|
||||
|
||||
# set the packages from the last transaction as installed
|
||||
for installed_pkg in last_transaction:
|
||||
self.base.package_install(installed_pkg, strict=True)
|
||||
|
||||
# depsolve the current transaction
|
||||
self.base.install_specs(
|
||||
transaction.get("package-specs"),
|
||||
transaction.get("exclude-specs"),
|
||||
reponame=[str(id) for id in transaction.get("repos")])
|
||||
self.base.resolve()
|
||||
|
||||
# store the current transaction result
|
||||
last_transaction.clear()
|
||||
for tsi in self.base.transaction:
|
||||
# Avoid using the install_set() helper, as it does not guarantee
|
||||
# a stable order
|
||||
if tsi.action not in dnf.transaction.FORWARD_ACTIONS:
|
||||
continue
|
||||
last_transaction.append(tsi.pkg)
|
||||
|
||||
dependencies = []
|
||||
for package in last_transaction:
|
||||
dependencies.append({
|
||||
"name": package.name,
|
||||
"epoch": package.epoch,
|
||||
"version": package.version,
|
||||
"release": package.release,
|
||||
"arch": package.arch,
|
||||
"repo_id": package.repoid,
|
||||
"path": package.relativepath,
|
||||
"remote_location": package.remote_location(),
|
||||
"checksum": (
|
||||
f"{hawkey.chksum_name(package.chksum[0])}:"
|
||||
f"{package.chksum[1].hex()}"
|
||||
)
|
||||
})
|
||||
|
||||
return {
|
||||
"checksums": self._repo_checksums(),
|
||||
"dependencies": dependencies
|
||||
}
|
||||
|
||||
|
||||
class DnfJsonRequestHandler(BaseHTTPRequestHandler):
|
||||
"""
|
||||
|
|
@ -354,6 +407,10 @@ class DnfJsonRequestHandler(BaseHTTPRequestHandler):
|
|||
)
|
||||
)
|
||||
log.info("depsolve success")
|
||||
elif command == "chain-depsolve":
|
||||
self.response_success(
|
||||
solver.chain_depsolve(arguments["transactions"])
|
||||
)
|
||||
|
||||
except dnf.exceptions.MarkingErrors as e:
|
||||
log.info("error install_specs")
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue