store: Add #:cut? parameter to 'topologically-sorted'.

* guix/store.scm (topologically-sorted): Add #:cut? and honor it.
* tests/store.scm ("topologically-sorted, one item, cutting"): New
test.
This commit is contained in:
Ludovic Courtès 2019-12-12 12:55:42 +01:00
parent 22a9dc1b79
commit 947c4a1689
No known key found for this signature in database
GPG key ID: 090B11993D9AEBB5
2 changed files with 27 additions and 13 deletions

View file

@ -1378,9 +1378,10 @@ SEED."
its references, recursively)." its references, recursively)."
(fold-path store cons '() paths)) (fold-path store cons '() paths))
(define (topologically-sorted store paths) (define* (topologically-sorted store paths #:key (cut? (const #f)))
"Return a list containing PATHS and all their references sorted in "Return a list containing PATHS and all their references sorted in
topological order." topological order. Skip store items that match CUT? as well as their
dependencies."
(define (traverse) (define (traverse)
;; Do a simple depth-first traversal of all of PATHS. ;; Do a simple depth-first traversal of all of PATHS.
(let loop ((paths paths) (let loop ((paths paths)
@ -1394,17 +1395,20 @@ topological order."
(match paths (match paths
((head tail ...) ((head tail ...)
(if (visited? head) (cond ((visited? head)
(loop tail visited result) (loop tail visited result))
(call-with-values ((cut? head)
(lambda () (loop tail visited result))
(loop (references store head) (else
(visit head) (call-with-values
result)) (lambda ()
(lambda (visited result) (loop (references store head)
(loop tail (visit head)
visited result))
(cons head result)))))) (lambda (visited result)
(loop tail
visited
(cons head result)))))))
(() (()
(values visited result))))) (values visited result)))))

View file

@ -388,6 +388,16 @@
(s (topologically-sorted %store (list d)))) (s (topologically-sorted %store (list d))))
(equal? s (list a b c d)))) (equal? s (list a b c d))))
(test-assert "topologically-sorted, one item, cutting"
(let* ((a (add-text-to-store %store "a" "a"))
(b (add-text-to-store %store "b" "b" (list a)))
(c (add-text-to-store %store "c" "c" (list b)))
(d (add-text-to-store %store "d" "d" (list c)))
(s (topologically-sorted %store (list d)
#:cut?
(cut string-suffix? "-b" <>))))
(equal? s (list c d))))
(test-assert "topologically-sorted, several items" (test-assert "topologically-sorted, several items"
(let* ((a (add-text-to-store %store "a" "a")) (let* ((a (add-text-to-store %store "a" "a"))
(b (add-text-to-store %store "b" "b" (list a))) (b (add-text-to-store %store "b" "b" (list a)))