From patchwork Tue Jun 18 22:08:49 2024 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Richard Sent X-Patchwork-Id: 65479 Return-Path: X-Original-To: patchwork@mira.cbaines.net Delivered-To: patchwork@mira.cbaines.net Received: by mira.cbaines.net (Postfix, from userid 113) id 3369527BBED; Tue, 18 Jun 2024 23:10:38 +0100 (BST) X-Spam-Checker-Version: SpamAssassin 3.4.6 (2021-04-09) on mira.cbaines.net X-Spam-Level: X-Spam-Status: No, score=-2.7 required=5.0 tests=BAYES_00,DKIM_INVALID, DKIM_SIGNED,MAILING_LIST_MULTI,SPF_HELO_PASS,URIBL_BLOCKED autolearn=ham autolearn_force=no version=3.4.6 Received: from lists.gnu.org (lists.gnu.org [209.51.188.17]) by mira.cbaines.net (Postfix) with ESMTPS id 0E5BE27BBEA for ; Tue, 18 Jun 2024 23:10:27 +0100 (BST) Received: from localhost ([::1] helo=lists1p.gnu.org) by lists.gnu.org with esmtp (Exim 4.90_1) (envelope-from ) id 1sJh1f-0005iD-II; Tue, 18 Jun 2024 18:10:03 -0400 Received: from eggs.gnu.org ([2001:470:142:3::10]) by lists.gnu.org with esmtps (TLS1.2:ECDHE_RSA_AES_256_GCM_SHA384:256) (Exim 4.90_1) (envelope-from ) id 1sJh1d-0005h2-4e for guix-patches@gnu.org; Tue, 18 Jun 2024 18:10:01 -0400 Received: from debbugs.gnu.org ([2001:470:142:5::43]) by eggs.gnu.org with esmtps (TLS1.2:ECDHE_RSA_AES_128_GCM_SHA256:128) (Exim 4.90_1) (envelope-from ) id 1sJh1c-0003Bs-St; Tue, 18 Jun 2024 18:10:00 -0400 Received: from Debian-debbugs by debbugs.gnu.org with local (Exim 4.84_2) (envelope-from ) id 1sJh1f-00034o-JI; Tue, 18 Jun 2024 18:10:03 -0400 X-Loop: help-debbugs@gnu.org Subject: [bug#71639] [PATCH WIP 2/5] services: backup: Add password-command support to restic-service Resent-From: Richard Sent Original-Sender: "Debbugs-submit" Resent-CC: pelzflorian@pelzflorian.de, ludo@gnu.org, matt@excalamus.com, maxim.cournoyer@gmail.com, guix-patches@gnu.org Resent-Date: Tue, 18 Jun 2024 22:10:03 +0000 Resent-Message-ID: Resent-Sender: help-debbugs@gnu.org X-GNU-PR-Message: followup 71639 X-GNU-PR-Package: guix-patches X-GNU-PR-Keywords: patch To: 71639@debbugs.gnu.org Cc: ludo@gnu.org, Richard Sent , goodoldpaul@autistici.org, Florian Pelz , Ludovic =?utf-8?q?Court=C3=A8s?= , Matthew Trzcinski , Maxim Cournoyer X-Debbugs-Original-Xcc: Florian Pelz , Ludovic =?utf-8?q?Court=C3=A8s?= , Matthew Trzcinski , Maxim Cournoyer Received: via spool by 71639-submit@debbugs.gnu.org id=B71639.171874857211692 (code B ref 71639); Tue, 18 Jun 2024 22:10:03 +0000 Received: (at 71639) by debbugs.gnu.org; 18 Jun 2024 22:09:32 +0000 Received: from localhost ([127.0.0.1]:53635 helo=debbugs.gnu.org) by debbugs.gnu.org with esmtp (Exim 4.84_2) (envelope-from ) id 1sJh19-00032Q-VW for submit@debbugs.gnu.org; Tue, 18 Jun 2024 18:09:32 -0400 Received: from mail-108-mta96.mxroute.com ([136.175.108.96]:35687) by debbugs.gnu.org with esmtp (Exim 4.84_2) (envelope-from ) id 1sJh17-000325-NN for 71639@debbugs.gnu.org; Tue, 18 Jun 2024 18:09:30 -0400 Received: from filter006.mxroute.com ([136.175.111.3] filter006.mxroute.com) (Authenticated sender: mN4UYu2MZsgR) by mail-108-mta96.mxroute.com (ZoneMTA) with ESMTPSA id 1902d65c5af00017a3.002 for <71639@debbugs.gnu.org> (version=TLSv1.3 cipher=TLS_AES_256_GCM_SHA384); Tue, 18 Jun 2024 22:09:22 +0000 X-Zone-Loop: a6785a6d9facb99f9f55f23f5b5a0967bfa001671860 X-Originating-IP: [136.175.111.3] DKIM-Signature: v=1; a=rsa-sha256; q=dns/txt; c=relaxed/relaxed; d=freakingpenguin.com; s=x; h=Content-Transfer-Encoding:MIME-Version: References:In-Reply-To:Message-ID:Date:Subject:Cc:To:From:Sender:Reply-To: Content-Type:Content-ID:Content-Description:Resent-Date:Resent-From: Resent-Sender:Resent-To:Resent-Cc:Resent-Message-ID:List-Id:List-Help: List-Unsubscribe:List-Subscribe:List-Post:List-Owner:List-Archive; bh=GRgk0YcfdnOlUM8vrZVXJwP2dkp9Z6VwaR5wZrbFuEI=; b=HW7eneh+kLX+dCqaomvyOr+SH9 LuOm19xVZUWxPIp1dJjUqFhYxHH/Qgpgefp3+0xsXWJGQ/io8DcWL7h9nNtTNP47dX3mWWN6Gl6rN /3RJaul5Dj8WU3ftYrpCBqZxhnlXHPKH8J4esc7oLDis5zfhkf4zSbZ68tBR7tUx9sqRwHDiT2VBI PuEJXzgYWKR/sWfAnSrG1Uo8lvWrw4KHKGZcM/M8CIXQp+z34mE2KmdTi2wn8D4Q11p0xHEFn3Kd7 lKJhNch1Eakcsx1p6v0Qk3d+s5wsxMsFWOBVGFX/Czxq01stNfhl1M40yEilobDtOlNf929TvZ5Oy RMFJYwfw==; From: Richard Sent Date: Tue, 18 Jun 2024 18:08:49 -0400 Message-ID: <388adecd6bae7d959392b862f1ccc234c0c24a6d.1718747513.git.richard@freakingpenguin.com> In-Reply-To: References: MIME-Version: 1.0 X-Authenticated-Id: richard@freakingpenguin.com X-BeenThere: debbugs-submit@debbugs.gnu.org X-Mailman-Version: 2.1.18 Precedence: list X-BeenThere: guix-patches@gnu.org List-Id: List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Errors-To: guix-patches-bounces+patchwork=mira.cbaines.net@gnu.org Sender: guix-patches-bounces+patchwork=mira.cbaines.net@gnu.org X-getmail-retrieved-from-mailbox: Patches * gnu/services/backup.scm (restic-backup-job): Add password-command. (verify-restic-backup-job-configuration): Create. (restic-backup-job-program): Set either RESTIC_PASSWORD or RESTIC_PASSWORD_COMMAND depending on what is configured. * doc/guix.texi (Miscellaneous Services): Document it. Change-Id: Ice9cf85d1ee4485a2737f515c63c969918219df0 --- doc/guix.texi | 7 +++++++ gnu/services/backup.scm | 42 ++++++++++++++++++++++++++++++++++++----- 2 files changed, 44 insertions(+), 5 deletions(-) diff --git a/doc/guix.texi b/doc/guix.texi index 63c9cbd1a7..f22d679023 100644 --- a/doc/guix.texi +++ b/doc/guix.texi @@ -41344,6 +41344,13 @@ Miscellaneous Services that will be used to set the @env{RESTIC_PASSWORD} environment variable for the current job. +@item @code{password-command} (type: file-like) +String path or file-like object representing the executable file that +prints password to stdout. If a file-like object is used, it is placed +in the store globally executable and in plain text. The executable +should be designed such that it does not compromise the password if an +unauthorized user runs it. + @item @code{schedule} (type: gexp-or-string) A string or a gexp that will be passed as time specification in the mcron job specification (@pxref{Syntax, mcron job specifications,, diff --git a/gnu/services/backup.scm b/gnu/services/backup.scm index eeef11eae7..2471d0ea7b 100644 --- a/gnu/services/backup.scm +++ b/gnu/services/backup.scm @@ -66,6 +66,9 @@ (define (lowerable? value) (define list-of-lowerables? (list-of lowerable?)) +(define-maybe/no-serialization string) +(define-maybe/no-serialization file-like) + (define-configuration/no-serialization restic-backup-job (restic (package restic) @@ -80,10 +83,16 @@ (define-configuration/no-serialization restic-backup-job (string) "The restic repository target of this job.") (password-file - (string) + (maybe-string) "Name of the password file, readable by the configured @code{user}, that will be used to set the @code{RESTIC_PASSWORD} environment variable for the current job.") + (password-command + (maybe-file-like) + "Name of the password command that, when run, returns the password over +stdin. Due to the nature of the store this command will be globally executable +and should have external protections to ensure other users cannot retrieve the +password. This overrides password-file.") (schedule (gexp-or-string) "A string or a gexp that will be passed as time specification in the mcron @@ -104,6 +113,14 @@ (define-configuration/no-serialization restic-backup-job "A list of values that are lowered to strings. These will be passed as command-line arguments to the current job @command{restic backup} invokation.")) +(define (verify-restic-backup-job-configuration config) + (unless (or (maybe-value-set? (restic-backup-job-password-file config)) + (maybe-value-set? (restic-backup-job-password-command config))) + (error "either password-file or password-command must be configured.")) + (when (and (maybe-value-set? (restic-backup-job-password-file config)) + (maybe-value-set? (restic-backup-job-password-command config))) + (error "password-file and password-command can not be configured simultaneously."))) + (define list-of-restic-backup-jobs? (list-of restic-backup-job?)) @@ -113,12 +130,22 @@ (define-configuration/no-serialization restic-backup-configuration "The list of backup jobs for the current system.")) (define (restic-backup-job-program config) + (define (maybe-value-or-false maybe) + (if (maybe-value-set? maybe) + maybe + #f)) + + ;; TODO: Find a place to also verify restic-backup-configuration. Mainly that jobs >=1 + (verify-restic-backup-job-configuration config) + (let ((restic (file-append (restic-backup-job-restic config) "/bin/restic")) (repository (restic-backup-job-repository config)) (password-file - (restic-backup-job-password-file config)) + (maybe-value-or-false (restic-backup-job-password-file config))) + (password-command + (maybe-value-or-false (restic-backup-job-password-command config))) (files (restic-backup-job-files config)) (extra-flags @@ -134,9 +161,14 @@ (define (restic-backup-job-program config) #~(begin (use-modules (ice-9 popen) (ice-9 rdelim)) - (setenv "RESTIC_PASSWORD" - (with-input-from-file #$password-file read-line)) - + (or (and=> #$password-file (lambda (x) + (setenv "RESTIC_PASSWORD" + (with-input-from-file x read-line)))) + (and=> #$password-command (lambda (x) + (setenv "RESTIC_PASSWORD_COMMAND" x))) + ;; Have a backup error message in case + ;; verify-restic-backup-job-configuration is messed with + (error "Neither password-file or password-command set")) (when #$init? ;; Check if the repository exists. See ;; https://github.com/restic/restic/issues/1690 and