gnu: gnome-settings-daemon: Add dependency on NetworkManager.
[jackhill/guix/guix.git] / gnu / services / databases.scm
CommitLineData
105369a4
DT
1;;; GNU Guix --- Functional package management for GNU
2;;; Copyright © 2015 David Thompson <davet@gnu.org>
9b1cee97 3;;; Copyright © 2015, 2016 Ludovic Courtès <ludo@gnu.org>
8823ed4e 4;;; Copyright © 2016 Leo Famulari <leo@famulari.name>
105369a4
DT
5;;;
6;;; This file is part of GNU Guix.
7;;;
8;;; GNU Guix is free software; you can redistribute it and/or modify it
9;;; under the terms of the GNU General Public License as published by
10;;; the Free Software Foundation; either version 3 of the License, or (at
11;;; your option) any later version.
12;;;
13;;; GNU Guix is distributed in the hope that it will be useful, but
14;;; WITHOUT ANY WARRANTY; without even the implied warranty of
15;;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
16;;; GNU General Public License for more details.
17;;;
18;;; You should have received a copy of the GNU General Public License
19;;; along with GNU Guix. If not, see <http://www.gnu.org/licenses/>.
20
21(define-module (gnu services databases)
22 #:use-module (gnu services)
0190c1c0 23 #:use-module (gnu services shepherd)
105369a4
DT
24 #:use-module (gnu system shadow)
25 #:use-module (gnu packages admin)
26 #:use-module (gnu packages databases)
27 #:use-module (guix records)
105369a4 28 #:use-module (guix gexp)
0adfe95a 29 #:use-module (ice-9 match)
24e96431
30 #:export (postgresql-configuration
31 postgresql-configuration?
32 postgresql-service
33 postgresql-service-type
34
6575183b 35 mysql-service
24e96431
36 mysql-service-type
37 mysql-configuration
38 mysql-configuration?))
105369a4
DT
39
40;;; Commentary:
41;;;
42;;; Database services.
43;;;
44;;; Code:
45
0adfe95a
LC
46(define-record-type* <postgresql-configuration>
47 postgresql-configuration make-postgresql-configuration
48 postgresql-configuration?
49 (postgresql postgresql-configuration-postgresql ;<package>
50 (default postgresql))
51 (config-file postgresql-configuration-file)
52 (data-directory postgresql-configuration-data-directory))
53
105369a4 54(define %default-postgres-hba
be1c2c54
LC
55 (plain-file "pg_hba.conf"
56 "
105369a4
DT
57local all all trust
58host all all 127.0.0.1/32 trust
59host all all ::1/128 trust"))
60
61(define %default-postgres-ident
be1c2c54 62 (plain-file "pg_ident.conf"
105369a4
DT
63 "# MAPNAME SYSTEM-USERNAME PG-USERNAME"))
64
65(define %default-postgres-config
be1c2c54 66 (mixed-text-file "postgresql.conf"
9b1cee97 67 "log_destination = 'syslog'\n"
be1c2c54 68 "hba_file = '" %default-postgres-hba "'\n"
8823ed4e 69 "ident_file = '" %default-postgres-ident "'\n"))
105369a4 70
0adfe95a
LC
71(define %postgresql-accounts
72 (list (user-group (name "postgres") (system? #t))
73 (user-account
74 (name "postgres")
75 (group "postgres")
76 (system? #t)
77 (comment "PostgreSQL server user")
78 (home-directory "/var/empty")
9e41130b 79 (shell (file-append shadow "/sbin/nologin")))))
0adfe95a
LC
80
81(define postgresql-activation
82 (match-lambda
83 (($ <postgresql-configuration> postgresql config-file data-directory)
84 #~(begin
85 (use-modules (guix build utils)
86 (ice-9 match))
87
88 (let ((user (getpwnam "postgres"))
89 (initdb (string-append #$postgresql "/bin/initdb")))
90 ;; Create db state directory.
91 (mkdir-p #$data-directory)
92 (chown #$data-directory (passwd:uid user) (passwd:gid user))
93
94 ;; Drop privileges and init state directory in a new
95 ;; process. Wait for it to finish before proceeding.
96 (match (primitive-fork)
97 (0
98 ;; Exit with a non-zero status code if an exception is thrown.
99 (dynamic-wind
100 (const #t)
101 (lambda ()
102 (setgid (passwd:gid user))
103 (setuid (passwd:uid user))
104 (primitive-exit (system* initdb "-D" #$data-directory)))
105 (lambda ()
106 (primitive-exit 1))))
107 (pid (waitpid pid))))))))
108
d4053c71 109(define postgresql-shepherd-service
0adfe95a
LC
110 (match-lambda
111 (($ <postgresql-configuration> postgresql config-file data-directory)
112 (let ((start-script
113 ;; Wrapper script that switches to the 'postgres' user before
114 ;; launching daemon.
115 (program-file "start-postgres"
116 #~(let ((user (getpwnam "postgres"))
117 (postgres (string-append #$postgresql
118 "/bin/postgres")))
119 (setgid (passwd:gid user))
120 (setuid (passwd:uid user))
121 (system* postgres
122 (string-append "--config-file="
123 #$config-file)
124 "-D" #$data-directory)))))
d4053c71 125 (list (shepherd-service
0adfe95a
LC
126 (provision '(postgres))
127 (documentation "Run the PostgreSQL daemon.")
9b1cee97 128 (requirement '(user-processes loopback syslogd))
0adfe95a
LC
129 (start #~(make-forkexec-constructor #$start-script))
130 (stop #~(make-kill-destructor))))))))
131
132(define postgresql-service-type
133 (service-type (name 'postgresql)
134 (extensions
d4053c71
AK
135 (list (service-extension shepherd-root-service-type
136 postgresql-shepherd-service)
0adfe95a
LC
137 (service-extension activation-service-type
138 postgresql-activation)
139 (service-extension account-service-type
140 (const %postgresql-accounts))))))
141
105369a4
DT
142(define* (postgresql-service #:key (postgresql postgresql)
143 (config-file %default-postgres-config)
144 (data-directory "/var/lib/postgresql/data"))
145 "Return a service that runs @var{postgresql}, the PostgreSQL database server.
146
147The PostgreSQL daemon loads its runtime configuration from @var{config-file}
148and stores the database cluster in @var{data-directory}."
0adfe95a
LC
149 (service postgresql-service-type
150 (postgresql-configuration
151 (postgresql postgresql)
152 (config-file config-file)
153 (data-directory data-directory))))
6575183b
SB
154
155\f
156;;;
157;;; MySQL.
158;;;
159
160(define-record-type* <mysql-configuration>
161 mysql-configuration make-mysql-configuration
162 mysql-configuration?
4b41febf
CB
163 (mysql mysql-configuration-mysql (default mariadb))
164 (port mysql-configuration-port (default 3306)))
6575183b
SB
165
166(define %mysql-accounts
167 (list (user-group
168 (name "mysql")
169 (system? #t))
170 (user-account
171 (name "mysql")
172 (group "mysql")
173 (system? #t)
174 (home-directory "/var/empty")
9e41130b 175 (shell (file-append shadow "/sbin/nologin")))))
6575183b
SB
176
177(define mysql-configuration-file
178 (match-lambda
4b41febf
CB
179 (($ <mysql-configuration> mysql port)
180 (mixed-text-file "my.cnf" "[mysqld]
6575183b
SB
181datadir=/var/lib/mysql
182socket=/run/mysqld/mysqld.sock
4b41febf 183port=" (number->string port) "
6575183b
SB
184"))))
185
186(define (%mysql-activation config)
187 "Return an activation gexp for the MySQL or MariaDB database server."
188 (let ((mysql (mysql-configuration-mysql config))
189 (my.cnf (mysql-configuration-file config)))
190 #~(begin
191 (use-modules (ice-9 popen)
192 (guix build utils))
193 (let* ((mysqld (string-append #$mysql "/bin/mysqld"))
194 (user (getpwnam "mysql"))
195 (uid (passwd:uid user))
196 (gid (passwd:gid user))
197 (datadir "/var/lib/mysql")
198 (rundir "/run/mysqld"))
199 (mkdir-p datadir)
200 (chown datadir uid gid)
201 (mkdir-p rundir)
202 (chown rundir uid gid)
203 ;; Initialize the database when it doesn't exist.
204 (when (not (file-exists? (string-append datadir "/mysql")))
205 (if (string-prefix? "mysql-" (strip-store-file-name #$mysql))
206 ;; For MySQL.
207 (system* mysqld
208 (string-append "--defaults-file=" #$my.cnf)
209 "--initialize"
210 "--user=mysql")
211 ;; For MariaDB.
212 ;; XXX: The 'mysql_install_db' script doesn't work directly
213 ;; due to missing 'mkdir' in PATH.
214 (let ((p (open-pipe* OPEN_WRITE mysqld
215 (string-append
216 "--defaults-file=" #$my.cnf)
217 "--bootstrap"
218 "--user=mysql")))
219 ;; Create the system database, as does by 'mysql_install_db'.
220 (display "create database mysql;\n" p)
221 (display "use mysql;\n" p)
222 (for-each
223 (lambda (sql)
224 (call-with-input-file
225 (string-append #$mysql "/share/mysql/" sql)
226 (lambda (in) (dump-port in p))))
227 '("mysql_system_tables.sql"
228 "mysql_performance_tables.sql"
229 "mysql_system_tables_data.sql"
230 "fill_help_tables.sql"))
231 ;; Remove the anonymous user and disable root access from
232 ;; remote machines, as does by 'mysql_secure_installation'.
233 (display "
234DELETE FROM user WHERE User='';
235DELETE FROM user WHERE User='root' AND
236 Host NOT IN ('localhost', '127.0.0.1', '::1');
237FLUSH PRIVILEGES;
238" p)
239 (close-pipe p))))))))
240
241(define (mysql-shepherd-service config)
242 (list (shepherd-service
243 (provision '(mysql))
244 (documentation "Run the MySQL server.")
245 (start (let ((mysql (mysql-configuration-mysql config))
246 (my.cnf (mysql-configuration-file config)))
247 #~(make-forkexec-constructor
248 (list (string-append #$mysql "/bin/mysqld")
249 (string-append "--defaults-file=" #$my.cnf))
250 #:user "mysql" #:group "mysql")))
251 (stop #~(make-kill-destructor)))))
252
253(define mysql-service-type
254 (service-type
255 (name 'mysql)
256 (extensions
257 (list (service-extension account-service-type
258 (const %mysql-accounts))
259 (service-extension activation-service-type
260 %mysql-activation)
261 (service-extension shepherd-root-service-type
262 mysql-shepherd-service)))))
263
264(define* (mysql-service #:key (config (mysql-configuration)))
265 "Return a service that runs @command{mysqld}, the MySQL or MariaDB
266database server.
267
268The optional @var{config} argument specifies the configuration for
269@command{mysqld}, which should be a @code{<mysql-configuration>} object."
270 (service mysql-service-type config))