From mboxrd@z Thu Jan 1 00:00:00 1970 Received: from eggs.gnu.org ([2001:470:142:3::10]:33664) by lists.gnu.org with esmtp (Exim 4.86_2) (envelope-from ) id 1htCdi-000082-Bc for guix-patches@gnu.org; Thu, 01 Aug 2019 11:05:13 -0400 Received: from Debian-exim by eggs.gnu.org with spam-scanned (Exim 4.71) (envelope-from ) id 1htCdd-0000E3-LJ for guix-patches@gnu.org; Thu, 01 Aug 2019 11:05:07 -0400 Received: from debbugs.gnu.org ([209.51.188.43]:46061) by eggs.gnu.org with esmtps (TLS1.0:RSA_AES_128_CBC_SHA1:16) (Exim 4.71) (envelope-from ) id 1htCda-0000Az-OH for guix-patches@gnu.org; Thu, 01 Aug 2019 11:05:03 -0400 Received: from Debian-debbugs by debbugs.gnu.org with local (Exim 4.84_2) (envelope-from ) id 1htCda-0005n8-HE for guix-patches@gnu.org; Thu, 01 Aug 2019 11:05:02 -0400 Subject: [bug#36875] [PATCH] doc: Document the use of `program-file' for mcron jobs. Resent-Message-ID: From: Maxim Cournoyer References: <875znhbugu.fsf@gmail.com> <87h872t2me.fsf@elephly.net> Date: Fri, 02 Aug 2019 09:03:54 +0900 In-Reply-To: <87h872t2me.fsf@elephly.net> (Ricardo Wurmus's message of "Wed, 31 Jul 2019 21:39:37 +0200") Message-ID: <87wofwa0wl.fsf@gmail.com> MIME-Version: 1.0 Content-Type: multipart/signed; boundary="==-=-="; micalg=pgp-sha256; protocol="application/pgp-signature" List-Id: List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Errors-To: guix-patches-bounces+kyle=kyleam.com@gnu.org Sender: "Guix-patches" To: Ricardo Wurmus Cc: 36875@debbugs.gnu.org --==-=-= Content-Type: multipart/mixed; boundary="=-=-=" --=-=-= Content-Type: text/plain; charset=utf-8 Content-Transfer-Encoding: quoted-printable Hello Ricardo! Ricardo Wurmus writes: > Hi Maxim, > >> This follows up to my second post under the thread at >> (https://lists.gnu.org/archive/html/help-guix/2019-07/msg00180.html). >> >> It aims to shed some light on (more) complex mcron job Guile scripting >> with the aid of Guix features (such as program-file). > > I wonder if this can be worked around some other way, e.g. by adding > srfi-26 to the =E2=80=9Cwith-imported-modules=E2=80=9D clause. No; srfi-26 is already present in the Guile load path. `with-imported-modules' is used to import non-builtin Guile modules into the generated script load paths. In the current example, passing (srfi srfi-26) to (with-imported-modules ...) doesn't change the hash of the compiled gexps (because it is already included). > I don=E2=80=99t fully understand the problem as described in the addition= to the > manual. What does =E2=80=9Cimported syntax definitions wouldn't work cor= rectly=E2=80=9D > mean? That any macro imported with (use-modules ...) in a mcron job defined using a lambda would not be expanded correctly. > It would be useful to state that this is something to do with srfi-26. It is not just about srfi-26; but about any syntax definitions (macros) tha= t a user might want to use in a mcron script, such as `guard' from srfi-34. Consider the mcron job defined as below: =2D-8<---------------cut here---------------start------------->8--- (define %macros-in-a-mcron-lambda-job-dont-work (with-imported-modules (source-module-closure '((guix build utils))) #~(job '(next-minute (range 0 60 1)) (lambda _ (use-modules (guix build utils) (srfi srfi-34)) (guard (c ((invoke-error? c)) (format #t "Guard worked as expected.")) (invoke "false")))))) =2D-8<---------------cut here---------------end--------------->8--- Then upon running, it would fail with the following backtrace: =2D-8<---------------cut here---------------start------------->8--- Backtrace: 9 (apply-smob/1 #) In ice-9/boot-9.scm: 829:9 8 (catch _ _ # ?) In mcron/scripts/mcron.scm: 99:7 7 (_) In mcron/base.scm: 234:12 6 (_ #) In srfi/srfi-1.scm: 640:9 5 (for-each # (#< user: #(?>)) In mcron/base.scm: 186:10 4 (run-job _) In ice-9/eval.scm: 159:9 3 (_ #(#(#) ())) 182:19 2 (proc #(#(#) #)) 142:16 1 (compile-top-call _ (7 . c) ((10 (10 (13 15 . #) #)) #)) In unknown file: 0 (%resolve-variable (7 . c) #) ERROR: In procedure %resolve-variable: Unbound variable: c =2D-8<---------------cut here---------------end--------------->8--- Which I found quite puzzling, and can easily imagine other mcron users stumbling onto. The solution (to use the program-file Gexp facility) is not an obvious one, so is worth being documented, in my opinion. I've attempted to clarify the text is the revised patch (attached). > About the patch: > > - please replace tabs with spaces. Done. > - =E2=80=9CBeep the system when the battery reaches %MIN-LEVEL or less ba= ttery > percent.=E2=80=9D sounds odd. How about =E2=80=9CBeep when the battery= percentage > falls below %MIN-LEVEL.=E2=80=9D? Done (and modified the logic to match it). ) > - Can the example be simplified further? Is (setenv "LC_ALL" "C") > really needed here? It's to ensure that the output of the 'acpi' command is in English, which the script depends on (setting the locale of the system to something else could affect this, if acpi is internationalized (I don't know, but I'm protecting against it, in case)). > - instead of let* and when I=E2=80=99d probably use and-let*. Done. Reworked patch is attached. Thanks for the feedback! :-) Maxim --=-=-= Content-Type: text/x-patch Content-Disposition: attachment; filename=0001-doc-Document-the-use-of-program-file-for-mcron-jobs.patch Content-Transfer-Encoding: quoted-printable From=200fffed46b4899bf0485926399d3971a4b5e94408 Mon Sep 17 00:00:00 2001 From: Maxim Cournoyer Date: Thu, 1 Aug 2019 07:34:17 +0900 Subject: [PATCH] doc: Document the use of `program-file' for mcron jobs. * doc/guix.texi (Scheduled Job Execution): Explain why using `program-file' for an mcron job can be necessary. Add an example. =2D-- doc/guix.texi | 35 +++++++++++++++++++++++++++++++++++ 1 file changed, 35 insertions(+) diff --git a/doc/guix.texi b/doc/guix.texi index e6047a4909..dd06efa9c2 100644 =2D-- a/doc/guix.texi +++ b/doc/guix.texi @@ -12444,6 +12444,41 @@ gexps to introduce job definitions that are passed= to mcron %base-services))) @end lisp =20 +For more complex jobs defined in Scheme, it is safer to pass the job as a +script to mcron; otherwise, macros defined or imported with @code{use-modu= les} +wouldn't expand correctly, as Guile requires macros to be strictly defined= or +imported at the top level of a Guile module. This can be achieved using t= he +@code{program-file} procedure from the @code{(guix gexp)} module, as shown= in +the example below. + +@lisp +(define %battery-alert-job + ;; Beep when the battery percentage falls below %MIN-LEVEL. + #~(job + '(next-minute (range 0 60 1)) + #$(program-file + "battery-alert.scm" + (with-imported-modules (source-module-closure + '((guix build utils))) + #~(begin + (define %min-level 20) + (use-modules (guix build utils) + (ice-9 popen) + (ice-9 regex) + (ice-9 textual-ports) + (srfi srfi-2)) + (setenv "LC_ALL" "C") + (and-let* ((input-pipe (open-pipe* + OPEN_READ + #$(file-append acpi "/bin/acpi"))) + (output (get-string-all input-pipe)) + (m (string-match "Discharging, ([0-9]+)%" output)) + (level (string->number (match:substring m 1))) + ((< level %min-level))) + (format #t "warning: Battery level is low (~a%)~%" level) + (invoke #$(file-append beep "/bin/beep") "-r5"))))))) +@end lisp + @xref{Guile Syntax, mcron job specifications,, mcron, GNU@tie{}mcron}, for more information on mcron job specifications. Below is the reference of the mcron service. =2D-=20 2.21.0 --=-=-=-- --==-=-= Content-Type: application/pgp-signature; name="signature.asc" -----BEGIN PGP SIGNATURE----- iQIzBAEBCAAdFiEEJ9WGpPiQCFQyn/CfEmDkZILmNWIFAl1DfeoACgkQEmDkZILm NWJnvQ//b4qpwmEA2yGDu4VdR8Qu1WmwyoZ/nM/JlWs1BZ6wbMijVcm6xki2s1b+ SEvkC2Srj9Bp5yU+ETklrGpldE/rDQ81QkBaGWuU022pIpMM/bUdP6NOS6N8w35p TFksKnPmlxxh3qUmO1bpc+5M2yLdy2w0T4X0sy0PlQ665Nrc8XUJpCVv7srVKtPS F250Dl+XMLrM4qT3LEgs7b6BLT5lLtGo7CxTwAqoAUfJDEX5U6odp50OUZB7Jey1 e1q8TPBb9Vvcr2A1almrZrXvTk5QWAFHaUuWgexFwnG53F0ETTUtOLfhvn5KJCcL /RIelrdnensjCF2W914uxOrvZGPSYRdGr0Sx6NGaUK1dn2FrBqbQsgbgrpITT6H4 M2yb3igLYBbdEn4sqGfyOfFxGIAdDXkZQJADqqc04Goad+ANq7rOD1lpYBQDooJr tKWda3Ra3sbpaJBHniGxP3rfGiqgU7u+9cugwNd8dX26b9Hp6JLPBFP/MxkK8TkM grHUhr/JudEa1354Lk7YCzcTmtTY1GzFyQp1732syCrsJlvFR15lOan+NoPOdTnD xiK1ob4JpZJZBPraUJmKEMj5jvsUbCDy1NVlrgr7K6w8dOUX3pqklwgV+HkSeypA VrkmCuReRPGn/zXUo0qvkNhbazfdrLi7bRd7nLWxDCR5O3FYI7A= =+p0u -----END PGP SIGNATURE----- --==-=-=--