~ruther/guix-local

a7cf4eb6d99838606d8ecfa776f7e4920dfbb7f5 — Mathieu Lirzin 9 years ago 365de1e
services: Add 'cuirass-service'.

* gnu/services/cuirass.scm: New file.
* gnu/local.mk (GNU_SYSTEM_MODULES): Add it.
* doc/guix.texi (Continuous integration): New node.
3 files changed, 195 insertions(+), 0 deletions(-)

M doc/guix.texi
M gnu/local.mk
A gnu/services/cuirass.scm
M doc/guix.texi => doc/guix.texi +79 -0
@@ 7926,6 7926,7 @@ declaration.
* Kerberos Services::           Kerberos services.
* Web Services::                Web servers.
* Network File System::         NFS related services.
* Continuous Integration::      The Cuirass service.
* Miscellaneous Services::      Other services.
@end menu



@@ 11747,6 11748,84 @@ If it is @code{#f} then the daemon will use the host's fully qualified domain na
@end table
@end deftp

@node Continuous Integration
@subsubsection Continuous Integration

@cindex continuous integration
@uref{https://notabug.org/mthl/cuirass, Cuirass} is a continuous
integration tool for Guix.  It can be used both for development and for
providing substitutes to others (@pxref{Substitutes}).

The @code{(gnu services cuirass)} module provides the following service.

@deffn {Scheme Procedure} cuirass-service @
       [#:config @code{(cuirass-configuration)}]
Return a service that runs @command{cuirass}.

The @var{#:config} keyword argument specifies the configuration for
@command{cuirass}, which must be a @code{<cuirass-configuration>}
object, by default it doesn't provide any build job.  If you want to
provide your own configuration you will most likely use the
@code{cuirass-configuration} special form which returns such objects.
@end deffn

In order to add build jobs you will have to set the
@code{specifications} field.  Here is an example of a cuirass service
defining a build job based on a specification that can be found in
Cuirass source tree.

@example
(let ((spec `((#:name . "guix")
              (#:url . "git://git.savannah.gnu.org/guix.git")
              (#:load-path . ".")
              ;; Adapt to a valid absolute file name.
              (#:file . "/.../cuirass/tests/gnu-system.scm")
              (#:proc . hydra-jobs)
              (#:arguments (subset . "hello"))
              (#:branch . "master"))))
  (cuirass-service #:config (cuirass-configuration
                             (specifications (list spec)))))
@end example

While information related to build jobs are located directly in the
specifications, global settings for the @command{cuirass} process are
accessible in other @code{cuirass-configuration} fields.

@deftp {Data Type} cuirass-configuration
Data type representing the configuration of Cuirass.

@table @asis
@item @code{cache-directory} (default: @code{""})
Location of the repository cache.

@item @code{user} (default: @code{"cuirass"})
Owner of the @code{cuirass} process.

@item @code{group} (default: @code{"cuirass"})
Owner's group of the @code{cuirass} process.

@item @code{interval} (default: @code{60})
Number of seconds between the poll of the repositories followed by the
Cuirass jobs.

@item @code{database} (default: @code{"/var/run/cuirass/cuirass.db"})
Location of sqlite database which contains the build results and previously
added specifications.

@item @code{specifications} (default: @code{'()})
A list of specifications, where a specification is an association list
(@pxref{Associations Lists,,, guile, GNU Guile Reference Manual}) whose
keys are keywords (@code{#:keyword-example}) as shown in the example
above.

@item @code{use-substitutes?} (default: @code{#f})
This allows using substitutes to avoid building every dependencies of a job
from source.

@item @code{one-shot?} (default: @code{#f})
Only evaluate specifications and build derivations once.
@end table
@end deftp

@node Miscellaneous Services
@subsubsection Miscellaneous Services

M gnu/local.mk => gnu/local.mk +1 -0
@@ 402,6 402,7 @@ GNU_SYSTEM_MODULES =				\
  %D%/services/avahi.scm			\
  %D%/services/base.scm				\
  %D%/services/configuration.scm		\
  %D%/services/cuirass.scm			\
  %D%/services/cups.scm				\
  %D%/services/databases.scm			\
  %D%/services/dbus.scm				\

A gnu/services/cuirass.scm => gnu/services/cuirass.scm +115 -0
@@ 0,0 1,115 @@
;;; GNU Guix --- Functional package management for GNU
;;; Copyright © 2016 Mathieu Lirzin <mthl@gnu.org>
;;;
;;; This file is part of GNU Guix.
;;;
;;; GNU Guix is free software: you can redistribute it and/or modify
;;; it under the terms of the GNU General Public License as published by
;;; the Free Software Foundation, either version 3 of the License, or
;;; (at your option) any later version.
;;;
;;; GNU Guix is distributed in the hope that it will be useful,
;;; but WITHOUT ANY WARRANTY; without even the implied warranty of
;;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
;;; GNU General Public License for more details.
;;;
;;; You should have received a copy of the GNU General Public License
;;; along with GNU Guix.  If not, see <http://www.gnu.org/licenses/>.

(define-module (gnu services cuirass)
  #:use-module (guix gexp)
  #:use-module (guix records)
  #:use-module (gnu packages admin)
  #:autoload   (gnu packages ci) (cuirass)
  #:use-module (gnu services)
  #:use-module (gnu services base)
  #:use-module (gnu services shepherd)
  #:use-module (gnu system shadow)
  #:export (<cuirass-configuration>
            cuirass-configuration
            cuirass-configuration?

            cuirass-service-type
            cuirass-service))

;;;; Commentary:
;;;
;;; This module implements a service that to run instances of Cuirass, a
;;; continuous integration tool.
;;;
;;;; Code:

(define-record-type* <cuirass-configuration>
  cuirass-configuration make-cuirass-configuration
  cuirass-configuration?
  (cache-directory  cuirass-configuration-cache-directory ;string (dir-name)
                    (default ""))
  (user             cuirass-configuration-user ;string
                    (default "cuirass"))
  (group            cuirass-configuration-group ;string
                    (default "cuirass"))
  (interval         cuirass-configuration-interval ;integer (seconds)
                    (default 60))
  (database         cuirass-configuration-database ;string (file-name)
                    (default "/var/run/cuirass/cuirass.db"))
  (specifications   cuirass-configuration-specifications ;string (file-name)
                    (default ""))
  (use-substitutes? cuirass-configuration-use-substitutes? ;boolean
                    (default #f))
  (one-shot?        cuirass-configuration-one-shot? ;boolean
                    (default #f)))

(define (cuirass-shepherd-service config)
  "Return a <shepherd-service> for the Cuirass service with CONFIG."
  (and
   (cuirass-configuration? config)
   (let ((cache-directory  (cuirass-configuration-cache-directory config))
         (interval         (cuirass-configuration-interval config))
         (database         (cuirass-configuration-database config))
         (specifications   (cuirass-configuration-specifications config))
         (use-substitutes? (cuirass-configuration-use-substitutes? config))
         (one-shot?        (cuirass-configuration-one-shot? config)))
     (list (shepherd-service
            (documentation "Run Cuirass.")
            (provision '(cuirass))
            (requirement '(guix-daemon))
            (start #~(make-forkexec-constructor
                      (list (string-append #$cuirass "/bin/cuirass")
                            #$@(if (string=? "" cache-directory)
                                   '()
                                   (list "--cache-directory" cache-directory))
                            #$@(if (string=? "" specifications)
                                   '()
                                   (list "--specifications" specifications))
                            "--database" #$database
                            "--interval" #$(number->string interval)
                            #$@(if use-substitutes? '("--use-substitutes") '())
                            #$@(if one-shot? '("--one-shot") '()))))
            (stop #~(make-kill-destructor)))))))

(define (cuirass-account config)
  "Return the user accounts and user groups for CONFIG."
  (let ((cuirass-user  (cuirass-configuration-user config))
        (cuirass-group (cuirass-configuration-group config)))
    (list (user-group
           (name cuirass-group)
           (system? #t))
          (user-account
           (name cuirass-user)
           (group cuirass-group)
           (system? #t)
           (comment "Cuirass privilege separation user")
           (home-directory (string-append "/var/run/" cuirass-user))
           (shell #~(string-append #$shadow "/sbin/nologin"))))))

(define cuirass-service-type
  (service-type
   (name 'cuirass)
   (extensions
    (list
     (service-extension shepherd-root-service-type cuirass-shepherd-service)
     (service-extension account-service-type cuirass-account)))))

(define* (cuirass-service #:key (config (cuirass-configuration)))
  "Return a service that runs cuirass according to CONFIG."
  (service cuirass-service-type config))