From mboxrd@z Thu Jan 1 00:00:00 1970 From: ludo@gnu.org (Ludovic =?utf-8?Q?Court=C3=A8s?=) Subject: Reporting module errors Date: Tue, 07 Nov 2017 23:47:35 +0100 Message-ID: <87zi7xwvso.fsf_-_@gnu.org> References: <868tfjw4is.fsf@gmail.com> <20171106221621.GA2534@jasmine.lan> <86o9oex34v.fsf@gmail.com> <779b1b6f2043e03a2f911981142e7740@lepiller.eu> <777f3534955ec61a520ff5f9b7054673@lepiller.eu> <86tvy6tbz5.fsf@gmail.com> <86efpat6z6.fsf@gmail.com> Mime-Version: 1.0 Content-Type: multipart/mixed; boundary="=-=-=" Return-path: Received: from eggs.gnu.org ([2001:4830:134:3::10]:40680) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1eCCel-0001RT-SZ for guix-devel@gnu.org; Tue, 07 Nov 2017 17:47:45 -0500 Received: from Debian-exim by eggs.gnu.org with spam-scanned (Exim 4.71) (envelope-from ) id 1eCCeh-0007jY-Re for guix-devel@gnu.org; Tue, 07 Nov 2017 17:47:43 -0500 Received: from hera.aquilenet.fr ([141.255.128.1]:49597) by eggs.gnu.org with esmtps (TLS1.0:DHE_RSA_AES_256_CBC_SHA1:32) (Exim 4.71) (envelope-from ) id 1eCCeh-0007iq-FO for guix-devel@gnu.org; Tue, 07 Nov 2017 17:47:39 -0500 In-Reply-To: (julien lepiller's message of "Tue, 07 Nov 2017 17:25:33 +0100") List-Id: "Development of GNU Guix and the GNU System distribution." List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Errors-To: guix-devel-bounces+gcggd-guix-devel=m.gmane.org@gnu.org Sender: "Guix-devel" To: julien lepiller Cc: guix-devel@gnu.org --=-=-= Content-Type: text/plain; charset=utf-8 Content-Transfer-Encoding: quoted-printable Hello! You=E2=80=99re too fast! :-) julien lepiller skribis: > +(define (import-error type module syntax) > + (define package-hint > + (string-append > + "Hint: You may use `guix package --show=3Dfoo | grep location` to = search\n" > + "Hint: for foo's location.\n" > + "Hint: If you get the line \"location: gnu/packages/bar.scm:174:2\= ",\n" > + "Hint: you want to add bar in use-package-modules.")) > + (define service-hint > + (string-append > + "Hint: You may use `guix system search foo` to search for foo's lo= cation.\n" > + "Hint: If you get the line \"location: gnu/services/bar.scm:188:2\= ",\n" > + "Hint: you want to add bar in use-service-modules.")) > + (error (string-append > + type " module \"" module "\" does not exist.\n" > + "Check the \"" syntax "\" line in your configuration.\n" > + (if (equal? type "Package") > + package-hint > + (if (equal? type "Service") > + service-hint > + ""))))) > + > (define-syntax-rule (use-package-modules module ...) > - (use-modules (gnu packages module) ...)) > + (begin > + (catch #t (lambda () (use-modules (gnu packages module))) > + (lambda _ > + (import-error "Package" (symbol->string 'module) "use-packa= ge-modules"))) > + ...)) That=E2=80=99s a great suggestion! I=E2=80=99d propose a variant of it, see below. With this, one gets a mess= age like: /tmp/config.scm:6:0: module (gnu packages foobar) could not be found where line 6 is: (use-package-modules foobar) How does that sound? It lacks the hints that you were proposing, which isn=E2=80=99t great, but I think we=E2=80=99d need to provide a homogeneous and internationalized API = in (guix ui) if we are to display hints. But overall I like the idea of providing hints somehow. Perhaps we could simply introduce another condition type for hints as a first step, similar to =E2=80=98&message=E2=80=99? Speaking of hints, we should have something that suggests a module name based on the Levenshtein distance with available modules. :-) Thanks, Ludo=E2=80=99. --=-=-= Content-Type: text/x-patch; charset=utf-8 Content-Disposition: inline Content-Transfer-Encoding: quoted-printable diff --git a/gnu.scm b/gnu.scm index 913ce6160..6dde968f1 100644 --- a/gnu.scm +++ b/gnu.scm @@ -1,5 +1,5 @@ ;;; GNU Guix --- Functional package management for GNU -;;; Copyright =C2=A9 2014, 2015, 2016 Ludovic Court=C3=A8s +;;; Copyright =C2=A9 2014, 2015, 2016, 2017 Ludovic Court=C3=A8s ;;; Copyright =C2=A9 2015 Joshua S. Grant ;;; Copyright =C2=A9 2017 Mathieu Othacehe ;;; @@ -19,6 +19,10 @@ ;;; along with GNU Guix. If not, see . =20 (define-module (gnu) + #:use-module (guix utils) + #:use-module (srfi srfi-34) + #:use-module (srfi srfi-35) + #:use-module (ice-9 match) #:export (use-package-modules use-service-modules use-system-modules)) @@ -52,13 +56,46 @@ (module-use! i (resolve-interface m)))) %public-modules))) =20 +(define (%try-use-modules modules location) + "Attempt to load all of MODULES. Report errors as coming from LOCATION,= a +source property alist." + (define (location->string loc) + (match loc + (#f "") + (($ file line column) + (format #f "~a:~a:~a: " file line column)))) + + (for-each (lambda (module) + (catch 'misc-error + (lambda () + (process-use-modules `((,module)))) + (lambda _ + (raise (condition + (&message + ;; TODO: Suggest a module with a similar name. + (message + (let-syntax ((G_ (syntax-rules () + ((_ str) str)))) + (format #f + (G_ "module ~a could not be found~%") + module)))) + (&error-location + (location location))))))) + modules)) + +(define-syntax-rule (try-use-modules modules ...) + (eval-when (expand load eval) + (%try-use-modules '(modules ...) + (source-properties->location + (current-source-location))))) + (define-syntax-rule (use-package-modules module ...) - (use-modules (gnu packages module) ...)) + (try-use-modules (gnu packages module) ...)) =20 (define-syntax-rule (use-service-modules module ...) - (use-modules (gnu services module) ...)) + (try-use-modules (gnu services module) ...)) =20 (define-syntax-rule (use-system-modules module ...) - (use-modules (gnu system module) ...)) + (try-use-modules (gnu system module) ...)) =20 ;;; gnu.scm ends here diff --git a/guix/ui.scm b/guix/ui.scm index 3c8734a7d..cd3a44fb4 100644 --- a/guix/ui.scm +++ b/guix/ui.scm @@ -272,9 +272,15 @@ ARGS is the list of arguments received by the 'throw' = handler." (location->string loc) message))) (('srfi-34 obj) (if (message-condition? obj) - (report-error (G_ "~a~%") - (gettext (condition-message obj) - %gettext-domain)) + (if (error-location? obj) + (format (current-error-port) + (G_ "~a: ~a~%") + (location->string (error-location obj)) + (gettext (condition-message obj) + %gettext-domain)) + (report-error (G_ "~a~%") + (gettext (condition-message obj) + %gettext-domain))) (report-error (G_ "exception thrown: ~s~%") obj))) ((error args ...) (report-error (G_ "failed to load '~a':~%") file) @@ -538,6 +544,11 @@ interpreted." directories:~{ ~a~}~%") (file-search-error-file-name c) (file-search-error-search-path c))) + ((and (error-location? c) (message-condition? c)) + (format (current-error-port) + (G_ "~a: ~a~%") + (location->string (error-location c)) + (gettext (condition-message c) %gettext-domain))) ((message-condition? c) ;; Normally '&message' error conditions have an i18n'd messag= e. (leave (G_ "~a~%") diff --git a/guix/utils.scm b/guix/utils.scm index eb1ec29b3..e25e2299e 100644 --- a/guix/utils.scm +++ b/guix/utils.scm @@ -28,6 +28,7 @@ #:use-module (srfi srfi-9) #:use-module (srfi srfi-11) #:use-module (srfi srfi-26) + #:use-module (srfi srfi-35) #:use-module (srfi srfi-39) #:use-module (ice-9 binary-ports) #:autoload (rnrs io ports) (make-custom-binary-input-port) @@ -60,6 +61,10 @@ source-properties->location location->source-properties =20 + &error-location + error-location? + error-location + nix-system->gnu-triplet gnu-triplet->nix-system %current-system @@ -750,6 +755,10 @@ a location object." (column . ,(location-column loc)) (filename . ,(location-file loc)))) =20 +(define-condition-type &error-location &error + error-location? + (location error-location)) ; + ;;; Local Variables: ;;; eval: (put 'call-with-progress-reporter 'scheme-indent-function 1) ;;; End: diff --git a/po/guix/POTFILES.in b/po/guix/POTFILES.in index e3f767cc6..6510b99e8 100644 --- a/po/guix/POTFILES.in +++ b/po/guix/POTFILES.in @@ -1,5 +1,6 @@ # List of source files which contain translatable strings. # This should be source files of the various tools, and not package module= s. +gnu.scm gnu/packages.scm gnu/services.scm gnu/system.scm --=-=-=--