diff options
Diffstat (limited to 'guix/channels.scm')
-rw-r--r-- | guix/channels.scm | 178 |
1 files changed, 123 insertions, 55 deletions
diff --git a/guix/channels.scm b/guix/channels.scm index 0c84eed477..05226e766b 100644 --- a/guix/channels.scm +++ b/guix/channels.scm @@ -1,5 +1,5 @@ ;;; GNU Guix --- Functional package management for GNU -;;; Copyright © 2018, 2019, 2020 Ludovic Courtès <ludo@gnu.org> +;;; Copyright © 2018, 2019, 2020, 2021 Ludovic Courtès <ludo@gnu.org> ;;; Copyright © 2018 Ricardo Wurmus <rekado@elephly.net> ;;; Copyright © 2019 Jan (janneke) Nieuwenhuizen <janneke@gnu.org> ;;; @@ -47,6 +47,7 @@ #:use-module (srfi srfi-26) #:use-module (srfi srfi-34) #:use-module (srfi srfi-35) + #:autoload (guix describe) (current-channels) ;XXX: circular dep #:autoload (guix self) (whole-package make-config.scm) #:autoload (guix inferior) (gexp->derivation-in-inferior) ;FIXME: circular dep #:autoload (guix quirks) (%quirks %patches applicable-patch? apply-patch) @@ -91,6 +92,9 @@ ensure-forward-channel-update profile-channels + manifest-entry-channel + sexp->channel + channel->code channel-news-entry? channel-news-entry-commit @@ -341,6 +345,18 @@ commits)...~%") (progress-reporter/bar (length commits))) + (define authentic-commits + ;; Consider the currently-used commit of CHANNEL as authentic so + ;; authentication can skip it and all its closure. + (match (find (lambda (candidate) + (eq? (channel-name candidate) (channel-name channel))) + (current-channels)) + (#f '()) + (channel + (if (channel-commit channel) + (list (channel-commit channel)) + '())))) + ;; XXX: Too bad we need to re-open CHECKOUT. (with-repository checkout repository (authenticate-repository repository @@ -351,6 +367,7 @@ commits)...~%") #:keyring-reference (string-append keyring-reference-prefix keyring-reference) + #:authentic-commits authentic-commits #:make-reporter make-reporter #:cache-key cache-key))) @@ -623,16 +640,23 @@ that unconditionally resumes the continuation." (values (run-with-store store mvalue) store)))) -(define* (build-from-source name source - #:key core verbose? commit - (dependencies '())) - "Return a derivation to build Guix from SOURCE, using the self-build script -contained therein; use COMMIT as the version string. When CORE is true, build -package modules under SOURCE using CORE, an instance of Guix." +(define* (build-from-source instance + #:key core verbose? (dependencies '())) + "Return a derivation to build Guix from INSTANCE, using the self-build +script contained therein. When CORE is true, build package modules under +SOURCE using CORE, an instance of Guix." + (define name + (symbol->string + (channel-name (channel-instance-channel instance)))) + (define source + (channel-instance-checkout instance)) + (define commit + (channel-instance-commit instance)) + ;; Running the self-build script makes it easier to update the build ;; procedure: the self-build script of the Guix-to-be-installed contains the ;; right dependencies, build procedure, etc., which the Guix-in-use may not - ;; be know. + ;; know. (define script (string-append source "/" %self-build-file)) @@ -658,7 +682,9 @@ package modules under SOURCE using CORE, an instance of Guix." ;; cause us to redo half of the BUILD computation several times just ;; to realize it gives the same result. (with-trivial-build-handler - (build source #:verbose? verbose? #:version commit + (build source + #:verbose? verbose? #:version commit + #:channel-metadata (channel-instance->sexp instance) #:pull-version %pull-version)))) ;; Build a set of modules that extend Guix using the standard method. @@ -669,10 +695,7 @@ package modules under SOURCE using CORE, an instance of Guix." "Return, as a monadic value, the derivation for INSTANCE, a channel instance. DEPENDENCIES is a list of extensions providing Guile modules that INSTANCE depends on." - (build-from-source (symbol->string - (channel-name (channel-instance-channel instance))) - (channel-instance-checkout instance) - #:commit (channel-instance-commit instance) + (build-from-source instance #:core core #:dependencies dependencies)) @@ -802,13 +825,36 @@ derivation." (derivation-input-derivation input)))) (derivation-inputs drv)))) +(define (channel-instance->sexp instance) + "Return an sexp representation of INSTANCE, a channel instance." + (let* ((commit (channel-instance-commit instance)) + (channel (channel-instance-channel instance)) + (intro (channel-introduction channel))) + `(repository + (version 0) + (url ,(channel-url channel)) + (branch ,(channel-branch channel)) + (commit ,commit) + (name ,(channel-name channel)) + ,@(if intro + `((introduction + (channel-introduction + (version 0) + (commit + ,(channel-introduction-first-signed-commit + intro)) + (signer + ,(openpgp-format-fingerprint + (channel-introduction-first-commit-signer + intro)))))) + '())))) + (define (channel-instances->manifest instances) "Return a profile manifest with entries for all of INSTANCES, a list of channel instances." (define (instance->entry instance drv) - (let* ((commit (channel-instance-commit instance)) - (channel (channel-instance-channel instance)) - (intro (channel-introduction channel))) + (let ((commit (channel-instance-commit instance)) + (channel (channel-instance-channel instance))) (manifest-entry (name (symbol->string (channel-name channel))) (version (string-take commit 7)) @@ -819,23 +865,7 @@ channel instances." drv) drv)) (properties - `((source (repository - (version 0) - (url ,(channel-url channel)) - (branch ,(channel-branch channel)) - (commit ,commit) - ,@(if intro - `((introduction - (channel-introduction - (version 0) - (commit - ,(channel-introduction-first-signed-commit - intro)) - (signer - ,(openpgp-format-fingerprint - (channel-introduction-first-commit-signer - intro)))))) - '())))))))) + `((source ,(channel-instance->sexp instance))))))) (mlet* %store-monad ((derivations (channel-instance-derivations instances)) (entries -> (map instance->entry instances derivations))) @@ -900,35 +930,73 @@ to 'latest-channel-instances'." validate-pull))) (channel-instances->derivation instances))) +(define* (sexp->channel sexp #:optional (name 'channel)) + "Read SEXP, a provenance sexp as created by 'channel-instance->sexp'; use +NAME as the channel name if SEXP does not specify it. Return #f if the sexp +does not have the expected structure." + (match sexp + (('repository ('version 0) + ('url url) + ('branch branch) + ('commit commit) + rest ...) + ;; Historically channel sexps did not include the channel name. It's OK + ;; for channels created by 'channel-instances->manifest' because the + ;; entry name is the channel name, but it was missing for entries created + ;; by 'manifest-entry-with-provenance'. + (channel (name (match (assq 'name rest) + (#f name) + (('name name) name))) + (url url) + (commit commit) + (introduction + (match (assq 'introduction rest) + (#f #f) + (('introduction intro) + (sexp->channel-introduction intro)))))) + + (_ #f))) + +(define (manifest-entry-channel entry) + "Return the channel ENTRY corresponds to, or #f if that information is +missing or unreadable. ENTRY must be an entry created by +'channel-instances->manifest', with the 'source' property." + (let ((name (string->symbol (manifest-entry-name entry)))) + (match (assq-ref (manifest-entry-properties entry) 'source) + ((sexp) + (sexp->channel sexp name)) + (_ + ;; No channel information for this manifest entry. + ;; XXX: Pre-0.15.0 Guix did not provide that information, + ;; but there's not much we can do in that case. + #f)))) + (define (profile-channels profile) "Return the list of channels corresponding to entries in PROFILE. If PROFILE is not a profile created by 'guix pull', return the empty list." - (filter-map (lambda (entry) - (match (assq 'source (manifest-entry-properties entry)) - (('source ('repository ('version 0) - ('url url) - ('branch branch) - ('commit commit) - rest ...)) - (channel (name (string->symbol - (manifest-entry-name entry))) - (url url) - (commit commit) - (introduction - (match (assq 'introduction rest) - (#f #f) - (('introduction intro) - (sexp->channel-introduction intro)))))) - - ;; No channel information for this manifest entry. - ;; XXX: Pre-0.15.0 Guix did not provide that information, - ;; but there's not much we can do in that case. - (_ #f))) - + (filter-map manifest-entry-channel ;; Show most recently installed packages last. (reverse (manifest-entries (profile-manifest profile))))) +(define* (channel->code channel #:key (include-introduction? #t)) + "Return code (an sexp) to build CHANNEL. When INCLUDE-INTRODUCTION? is +true, include its introduction, if any." + (let ((intro (and include-introduction? + (channel-introduction channel)))) + `(channel + (name ',(channel-name channel)) + (url ,(channel-url channel)) + (commit ,(channel-commit channel)) + ,@(if intro + `((introduction (make-channel-introduction + ,(channel-introduction-first-signed-commit intro) + (openpgp-fingerprint + ,(openpgp-format-fingerprint + (channel-introduction-first-commit-signer + intro)))))) + '())))) + ;;; ;;; News. |