packages: 'package-input-rewriting/spec' ignores hidden packages.

The primary motivation is to support things like:

  guix build guix --with-input=guile=guile-next

without triggering a rebuild of (@@ (gnu packages commencement)
guile-final) and similar things.

It is also consistent with package name resolution on the command line:
a package that cannot be named cannot be replaced.

* guix/packages.scm (package-input-rewriting/spec)[rewrite]: When P is
hidden, return it as-is.
* tests/packages.scm ("package-input-rewriting/spec, hidden package"):
New test.
* doc/guix.texi (Defining Package Variants): Update.
(Package Transformation Options): Update '--with-input' example.
This commit is contained in:
Ludovic Courtès 2023-03-08 12:53:20 +01:00
parent 5dd0d7f99f
commit eee95b5a87
No known key found for this signature in database
GPG key ID: 090B11993D9AEBB5
3 changed files with 36 additions and 12 deletions

View file

@ -8331,10 +8331,13 @@ be replaced by name rather than by identity.
@deffn {Scheme Procedure} package-input-rewriting/spec @var{replacements} [#:deep? #t] @deffn {Scheme Procedure} package-input-rewriting/spec @var{replacements} [#:deep? #t]
Return a procedure that, given a package, applies the given Return a procedure that, given a package, applies the given
@var{replacements} to all the package graph, including implicit inputs @var{replacements} to all the package graph, including implicit inputs
unless @var{deep?} is false. @var{replacements} is a list of unless @var{deep?} is false.
spec/procedures pair; each spec is a package specification such as
@code{"gcc"} or @code{"guile@@2"}, and each procedure takes a matching @var{replacements} is a list of spec/procedures pair; each spec is a
package and returns a replacement for that package. package specification such as @code{"gcc"} or @code{"guile@@2"}, and
each procedure takes a matching package and returns a replacement for
that package. Matching packages that have the @code{hidden?} property
set are not replaced.
@end deffn @end deffn
The example above could be rewritten this way: The example above could be rewritten this way:
@ -12664,18 +12667,18 @@ or @code{guile@@1.8}.
For instance, the following command builds Guix, but replaces its For instance, the following command builds Guix, but replaces its
dependency on the current stable version of Guile with a dependency on dependency on the current stable version of Guile with a dependency on
the legacy version of Guile, @code{guile@@2.0}: the legacy version of Guile, @code{guile@@2.2}:
@example @example
guix build --with-input=guile=guile@@2.0 guix guix build --with-input=guile=guile@@2.2 guix
@end example @end example
This is a recursive, deep replacement. So in this example, both This is a recursive, deep replacement. So in this example, both
@code{guix} and its dependency @code{guile-json} (which also depends on @code{guix} and its dependency @code{guile-json} (which also depends on
@code{guile}) get rebuilt against @code{guile@@2.0}. @code{guile}) get rebuilt against @code{guile@@2.2}.
This is implemented using the @code{package-input-rewriting} Scheme This is implemented using the @code{package-input-rewriting/spec} Scheme
procedure (@pxref{Defining Packages, @code{package-input-rewriting}}). procedure (@pxref{Defining Packages, @code{package-input-rewriting/spec}}).
@item --with-graft=@var{package}=@var{replacement} @item --with-graft=@var{package}=@var{replacement}
This is similar to @option{--with-input} but with an important difference: This is similar to @option{--with-input} but with an important difference:

View file

@ -1533,9 +1533,11 @@ (define (cut? p)
(define* (package-input-rewriting/spec replacements #:key (deep? #t)) (define* (package-input-rewriting/spec replacements #:key (deep? #t))
"Return a procedure that, given a package, applies the given REPLACEMENTS to "Return a procedure that, given a package, applies the given REPLACEMENTS to
all the package graph, including implicit inputs unless DEEP? is false. all the package graph, including implicit inputs unless DEEP? is false.
REPLACEMENTS is a list of spec/procedures pair; each spec is a package REPLACEMENTS is a list of spec/procedures pair; each spec is a package
specification such as \"gcc\" or \"guile@2\", and each procedure takes a specification such as \"gcc\" or \"guile@2\", and each procedure takes a
matching package and returns a replacement for that package." matching package and returns a replacement for that package. Matching
packages that have the 'hidden?' property set are not replaced."
(define table (define table
(fold (lambda (replacement table) (fold (lambda (replacement table)
(match replacement (match replacement
@ -1563,7 +1565,8 @@ (define replacement-property
(gensym " package-replacement")) (gensym " package-replacement"))
(define (rewrite p) (define (rewrite p)
(if (assq-ref (package-properties p) replacement-property) (if (or (assq-ref (package-properties p) replacement-property)
(hidden-package? p))
p p
(match (find-replacement p) (match (find-replacement p)
(#f p) (#f p)

View file

@ -1,5 +1,5 @@
;;; GNU Guix --- Functional package management for GNU ;;; GNU Guix --- Functional package management for GNU
;;; Copyright © 2012-2022 Ludovic Courtès <ludo@gnu.org> ;;; Copyright © 2012-2023 Ludovic Courtès <ludo@gnu.org>
;;; Copyright © 2018 Jan (janneke) Nieuwenhuizen <janneke@gnu.org> ;;; Copyright © 2018 Jan (janneke) Nieuwenhuizen <janneke@gnu.org>
;;; Copyright © 2021 Maxim Cournoyer <maxim.cournoyer@gmail.com> ;;; Copyright © 2021 Maxim Cournoyer <maxim.cournoyer@gmail.com>
;;; Copyright © 2021 Maxime Devos <maximedevos@telenet.be> ;;; Copyright © 2021 Maxime Devos <maximedevos@telenet.be>
@ -1592,6 +1592,24 @@ (define right-system?
(match (delete-duplicates pythons eq?) (match (delete-duplicates pythons eq?)
((p) (eq? p (rewrite python)))))) ((p) (eq? p (rewrite python))))))
(test-assert "package-input-rewriting/spec, hidden package"
;; Hidden packages are not subject to rewriting.
(let* ((python (hidden-package python))
(p0 (dummy-package "chbouib"
(build-system trivial-build-system)
(inputs (list python))))
(rewrite (package-input-rewriting/spec
`(("python" . ,(const sed)))
#:deep? #t))
(p1 (rewrite p0))
(bag1 (package->bag p1))
(pythons (filter-map (match-lambda
(("python" python) python)
(_ #f))
(bag-transitive-inputs bag1))))
(match (delete-duplicates pythons eq?)
((p) (eq? p python)))))
(test-equal "package-input-rewriting/spec, graft" (test-equal "package-input-rewriting/spec, graft"
(derivation-file-name (package-derivation %store sed)) (derivation-file-name (package-derivation %store sed))