guix-home-manager/home/ssh.scm

ssh.scm

1
;;; Guix Home Manager.
2
;;;
3
;;; Copyright © 2019 Julien Lepiller <julien@lepiller.eu>
4
;;;
5
;;; This program is free software: you can redistribute it and/or modify
6
;;; it under the terms of the GNU General Public License as published by
7
;;; the Free Software Foundation, either version 3 of the License, or
8
;;; (at your option) any later version.
9
;;;
10
;;; This program is distributed in the hope that it will be useful,
11
;;; but WITHOUT ANY WARRANTY; without even the implied warranty of
12
;;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
13
;;; GNU General Public License for more details.
14
;;;
15
;;; You should have received a copy of the GNU General Public License
16
;;; along with this program.  If not, see <http://www.gnu.org/licenses/>.
17
18
(define-module (home ssh)
19
  #:use-module (guix build utils)
20
  #:use-module (guix gexp)
21
  #:use-module (guix records)
22
  #:use-module (gnu packages lxde)
23
  #:use-module (ice-9 match)
24
  #:use-module (home)
25
  #:export (ssh-configuration
26
            ssh-configuration-authorized-keys
27
            ssh-configuration-known-hosts
28
            ssh-configuration-hosts
29
            ssh-configuration-default-host
30
31
            ssh-host-configuration
32
            ssh-host-configuration-host-name
33
            ssh-host-configuration-identity-file
34
            ssh-host-configuration-name
35
            ssh-host-configuration-port
36
            ssh-host-configuration-user
37
38
            ssh-known-host-configuration
39
            ssh-known-host-configuration-names
40
            ssh-known-host-configuration-algo
41
            ssh-known-host-configuration-key
42
43
            ssh-home-type))
44
45
(define-record-type* <ssh-host-configuration>
46
  ssh-host-configuration make-ssh-host-configuration
47
  ssh-host-configuration?
48
  (host-name     ssh-host-configuration-host-name
49
                 (default "*"))
50
  (identity-file ssh-host-configuration-identity-file
51
                 (default #f))
52
  (name          ssh-host-configuration-name
53
                 (default "*"))
54
  (port          ssh-host-configuration-port
55
                 (default #f))
56
  (user          ssh-host-configuration-user
57
                 (default #f)))
58
59
(define (ssh-host config)
60
  (match config
61
    (($ <ssh-host-configuration> host-name identity-file name port user)
62
     (string-append "Host " name "\n"
63
                    "  HostName " host-name "\n"
64
                    (if identity-file
65
                        (string-append "  IdentityFile " identity-file "\n")
66
                        "")
67
                    (if port
68
                        (string-append "  Port " port "\n")
69
                        "")
70
                    (if user
71
                        (string-append "  User " user "\n")
72
                        "")))))
73
74
(define (default-ssh config)
75
  (match config
76
    (($ <ssh-host-configuration> host-name identity-file name port user)
77
     (string-append
78
       (if identity-file
79
           (string-append "IdentityFile " identity-file "\n")
80
           "")
81
       (if port
82
           (string-append "Port " port "\n")
83
           "")
84
       (if user
85
           (string-append "User " user "\n")
86
           "")))))
87
88
(define (generate-ssh-hosts lst)
89
  (string-join (map ssh-host lst) "\n\n"))
90
91
(define (generate-ssh-config hosts default-host)
92
  (string-append (generate-ssh-hosts hosts)
93
                 "\n\n"
94
                 (default-ssh default-host)))
95
96
(define-record-type* <ssh-known-host-configuration>
97
  ssh-known-host-configuration make-ssh-known-host-configuration
98
  ssh-known-host-configuration?
99
  (names ssh-known-host-configuration-names)
100
  (algo  ssh-known-host-configuration-algo
101
         (default "ecdsa-sha2-nistp256"))
102
  (key   ssh-known-host-configuration-key))
103
104
105
(define (known-host config)
106
  (match config
107
    (($ <ssh-known-host-configuration> names algo key)
108
     (string-append
109
       (match names
110
         ((name) name)
111
         ((n1 ns ...)
112
          (string-join names ",")))
113
       " " algo " " key))))
114
115
(define-record-type* <ssh-configuration>
116
  ssh-configuration make-ssh-configuration
117
  ssh-configuration?
118
  (authorized-keys ssh-configuration-authorized-keys
119
                   (default '()))
120
  (known-hosts     ssh-configuration-known-hosts
121
                   (default '()))
122
  (hosts           ssh-configuration-hosts
123
                   (default '()))
124
  (default-host    ssh-configuration-default-host
125
                   (default #f)))
126
127
(define (generate-ssh-authorized-keys lst)
128
  (string-join lst "\n"))
129
130
(define (generate-ssh-known-hosts lst)
131
  (string-join (map known-host lst) "\n"))
132
133
(define ssh-home-type
134
  (home-type
135
    (name 'ssh)
136
    (extensions
137
      (list
138
        (home-extension
139
          (target root-home-type)
140
          (compute (lambda (config)
141
                     (match config
142
                       (($ <ssh-configuration> authorized-keys known-hosts hosts default-host)
143
                        (let ((config (plain-file "config" (generate-ssh-config hosts default-host)))
144
                              (known-hosts (plain-file "known_hosts"
145
                                                       (generate-ssh-known-hosts known-hosts)))
146
                              (authorized-keys (plain-file "authorized_keys"
147
                                                           (generate-ssh-authorized-keys authorized-keys))))
148
                     `((".ssh/authorized_keys" ,authorized-keys) (".ssh/known_hosts" ,known-hosts)
149
                       (".ssh/config" ,config))))))))))))
150