From e8ac9c3c3aee52866c8c48dc0aacccb27fc88d5a Mon Sep 17 00:00:00 2001 From: Maxim Cournoyer Date: Tue, 28 Apr 2026 11:18:58 +0900 Subject: services: Add forgejo-service-type. * gnu/services/forgejo.scm: New file. * gnu/tests/forgejo.scm: Likewise. * doc/guix.texi (Forge Services): Document it. Change-Id: I2c4e7b570d137b8d2fb7c02a29cb9aaf5366b9e1 --- doc/guix.texi | 319 ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 319 insertions(+) (limited to 'doc') diff --git a/doc/guix.texi b/doc/guix.texi index f5efd34024e..4d28f7c4aab 100644 --- a/doc/guix.texi +++ b/doc/guix.texi @@ -429,6 +429,7 @@ Services * Desktop Services:: D-Bus and desktop services. * Sound Services:: ALSA and Pulseaudio services. * File Search Services:: Tools to search for files. +* Forge Services:: Hosting your own software forge. * Database Services:: SQL databases, key-value stores, etc. * Mail Services:: IMAP, POP3, SMTP, and all that. * Messaging Services:: Messaging services. @@ -20358,6 +20359,7 @@ declaration. * Desktop Services:: D-Bus and desktop services. * Sound Services:: ALSA and Pulseaudio services. * File Search Services:: Tools to search for files. +* Forge Services:: Hosting your own software forge. * Database Services:: SQL databases, key-value stores, etc. * Mail Services:: IMAP, POP3, SMTP, and all that. * Messaging Services:: Messaging services. @@ -28758,6 +28760,323 @@ G-exp denoting the channels to use when updating the database @end table @end deftp +@node Forge Services +@subsection Forge Services + +Forges are applications designed to ease collaboration on software +development. Their usual features include an issue tracker, code +versioning and a system to request and conduct change reviews. + +@cindex software forge, self-hosting +@cindex forgejo, software forge +@subsubheading Forgejo + +This is the service for running Forgejo (@url{https://forgejo.org/}). +It is provided via the @code{(gnu services forgejo)} module. + +@defvar forgejo-service-type +The service type for the Forgejo source forge. It takes a +@code{forgejo-configuration} object as a value, documented below. In +its simplest form, a Forgejo service can be defined as just: + +@lisp +(service forgejo-service-type) +@end lisp + +Here's a slightly more involved service configuration, intended as a +secure, private software forge that is able to send notification emails. + +@lisp +(service forgejo-service-type + (forgejo-configuration + (offline-mode? #t) + (require-signin-to-view? #t) + (http-address "10.1.1.1") ;exposed via wireguard + (ssh-address "10.1.1.1") + (mailer? #t) + (mail-from "some-email@@example.com") + (smtp-address "smtp.example.com") + (smtp-user "some-email@@example.com") + (smtp-password-file "/etc/forgejo/smtp_secret") + (mail-notification? #t))) +@end lisp +@end defvar + +Below is the documentation for the @code{forgejo-configuration} record: + +@c %start of fragment + +@deftp {Data Type} forgejo-configuration +Available @code{forgejo-configuration} fields are: + +@table @asis +@item @code{forgejo} (default: @code{forgejo}) (type: file-like) +The forgejo package. + +@item @code{work-directory} (default: @code{"/var/lib/forgejo"}) (type: string) +The directory where Forgejo keeps its state, including its database when +using @code{"sqlite3"} as the @code{database-type}. + +@item @code{shepherd-provision} (default: @code{(forgejo)}) (type: list-of-symbols) +The name(s) of the service. + +@item @code{configuration-wizard?} (default: @code{#f}) (type: boolean) +Whether to use the initial configuration page (wizard) to setup Forgejo. +Setting this to @code{#t} means that none of the declarative +configuration values will be honored. The Forgejo-generated +configuration file will be kept under @file{custom/conf/app.ini}, +relative to the value of the @code{work-directory}. + +@item @code{user} (default: @code{"forgejo"}) (type: string) +The name of the user under which Forgejo will be executed. + +@item @code{group} (default: @code{"forgejo"}) (type: string) +The name of the group under which Forgejo will be executed. + +@item @code{custom-configuration-file} (type: maybe-file-like) +File-like object to provide a complete Forgejo configuration file as an +escape hatch, overriding every other fields of this configuration. + +@item @code{application-name} (default: @code{"Forgejo"}) (type: string) +The application name that shows in every page title. + +@item @code{application-slogan} (default: @code{""}) (type: string) +Slogan to show near the application name in every page title. + +@item @code{run-mode} (default: @code{"prod"}) (type: run-mode) +The run mode to use; either @code{"dev"} or @code{"prod"}. + +@item @code{domain} (default: @code{"localhost"}) (type: string) +The domain name or host address of the server. + +@item @code{offline-mode?} (default: @code{#f}) (type: boolean) +Set to @code{#t} to run Forgejo in offline mode, meaning it won't reach +out to any external services such as Gravatar, CDNs, etc. and serve +everything locally instead. + +@item @code{port} (default: @code{3000}) (type: unprivileged-port) +The port Forgejo will listen on. The port should be an unprivileged +port; to serve Forgejo on a privileged port like @code{80}, configure a +reverse proxy. It is ignored when using a Unix-domain socket. + +@item @code{protocol} (default: @code{"http"}) (type: protocol) +Listen protocol. Either @code{http}, @code{https}, @code{fcgi}, +@code{"http+unix"} or @code{"fcgi+unix"}. @samp{+unix} means @emph{via} +a Unix-domain socket, in which case @code{http-address} must be the file +name of the socket to use. + +@item @code{root-url} (type: maybe-string) +Overwrite the automatically generated public URL, which implicitly +defaults to @samp{@var{protocol}://@var{domain}:@var{port}}, which is +necessary using a reverse proxy. + +@item @code{http-address} (default: @code{"0.0.0.0"}) (type: string) +The address to listen to. It can be an absolute file name when using a +Unix-domain socket, for example @file{/run/forgejo.sock}, or a file name +relative to the @code{work-directory}, for example @file{forgejo.sock}. + +@item @code{ssh-address} (default: @code{"0.0.0.0"}) (type: string) +The IP address to listen on for the SSH server. + +@item @code{lfs?} (default: @code{#t}) (type: boolean) +Whether to enable Git LFS support. + +@item @code{lfs-secret-file} (default: @code{"/etc/forgejo/lfs_jwt_secret"}) (type: string) +The file name of the LFS JWT (JSON Web Token) secret, necessary for +proper Git LFS operation, which can be generated with @samp{forgejo +generate secret JWT_SECRET}. Automatically generated the first time +Forgejo runs if it does not yet exist. + +@item @code{mail-notification?} (default: @code{#f}) (type: boolean) +Whether to enable email notifications. + +@item @code{acme?} (default: @code{#f}) (type: boolean) +Whether to enable @acronym{ACME,Automatic Certificate Management +Environment}, to automatically provision TLS certificates, which can be +useful if you use the @code{https} or @code{https+unix} protocols. + +@item @code{tls-cert-file} (default: @code{"https/cert.pem"}) (type: string) +File name of a TLS certificate file. Ignored if @code{acme?} is +enabled. A relative file name is located under +@file{@var{work-directory}/custom}. + +@item @code{tls-key-file} (default: @code{"https/key.pem"}) (type: string) +File name of a TLS key. Ignored if @code{acme?} is enabled. A relative +file name is located under @file{@var{work-directory}/custom}. + +@item @code{ssh-port} (default: @code{22}) (type: port-or-false) +The SSH port Forgejo will use; if you already run an OpenSSH as the SSH +server, specify the port used by the SSH daemon. Otherwise, you need to +use an unprivileged port (greater or equal to 1024) which Forgejo will +use with its built-in SSH server. Set to @code{#f} to disable SSH +support. + +@item @code{actions?} (default: @code{#t}) (type: boolean) +Whether to enable actions capabilities. + +@item @code{default-actions-url} (default: @code{"https://code.forgejo.org"}) (type: string) +The default address to fetch action plugins from. + +@item @code{internal-token-file} (default: @code{"/etc/forgejo/internal_token"}) (type: string) +The file name of the internal token used to validate communication +within Forgejo, which can be generated with @samp{forgejo generate +secret INTERNAL_TOKEN} + +@item @code{secret-key-file} (default: @code{"/etc/forgejo/secret_key"}) (type: string) +The file name containing the global secret key used for encrypting data +like 2FA secrets; it is thus very important to back it up somewhere safe +to avoid losing access to encrypted data. + +@item @code{oauth2-jwt-secret-file} (default: @code{"/etc/forgejo/oauth2_jwt_secret"}) (type: string) +The file name of the OAuth2 JWT secret, which Forgejo expects to exist. + +@item @code{mail-notification-on-new-user-signin?} (default: @code{#f}) (type: boolean) +Whether to notify administrators by email when a new user signs in for +the first time. + +@item @code{mailer?} (default: @code{#f}) (type: boolean) +Whether to enable the mail server integration, used for sending email +notifications for example. + +@item @code{mail-from} (default: @code{""}) (type: string) +The FROM email address used for sent emails, per the RFC 5322 +specification. This can be for example just an email address, or +something like @samp{"Name" }. This field +@emph{must} be specified if @code{mailer?} is set to @code{#t}. + +@item @code{mail-subject-prefix} (default: @code{""}) (type: string) +The prefix displayed before the subject in emails. + +@item @code{mail-protocol} (default: @code{""}) (type: mail-protocol) +The mail server protocol. One of @code{"smtp"}, @code{"smtps"}, +@code{"smtp+starttls"}, @code{"smtp+unix"}, @code{"sendmail"}, +@code{"dummy"} or @code{""}. The empty string defaults means the +protocol is inferred from the value of the @code{smtp-port} value, +meaning its effective implicit value is @code{"smtps"}. @code{"dummy"} +causes emails to be sent to the log, useful for testing. When +@code{"sendmail"} is used, it is expected to be fully and correctly +externally configured, with the other @samp{smtp-} prefixed options of +this configuration ignored. + +@item @code{smtp-address} (default: @code{""}) (type: string) +The mail server address, for example @code{"smtp.example.com"} or an +absolute file name, if using @code{"smtp+unix"} for the +@code{mail-protocol}. + +@item @code{smtp-port} (default: @code{465}) (type: port) +The mail server port. This field affects the implicit value of the +@code{mail-protocol}. + +@item @code{smtp-user} (default: @code{""}) (type: string) +The SMTP server user name, if required + +@item @code{smtp-password-file} (default: @code{""}) (type: string) +An absolute file name containing the password of the SMTP server. + +@item @code{mail-plain-text?} (default: @code{#f}) (type: boolean) +Send emails only in plain text, without HTML alternative. + +@item @code{sendmail-command} (default: @code{"sendmail"}) (type: string) +The file name of the @command{sendmail} command to use, which can be +either an absolute file name or a command name to be looked from +@env{"PATH"}. + +@item @code{sendmail-options} (default: @code{()}) (type: list-of-strings) +Optional options to pass to the @command{sendmail} command. If your +@code{sendmail} program, like that of Postfix, interprets options, you +should provide @code{"--"} as the first option. + +@item @code{sendmail-timeout} (default: @code{"5m"}) (type: string) +The timeout for Sendmail, provided as a +@uref{https://pkg.go.dev/time#ParseDuration,Go @code{time.Duration} +string}, for example @code{"300ms"}, @code{"1.5h"} or @code{"2h45m"}. + +@item @code{sendmail-convert-crlf?} (default: @code{#t}) (type: boolean) +Whether to convert @samp{\r\n} to @samp{\n} for Sendmail. + +@item @code{log-level} (default: @code{"info"}) (type: log-level) +The log level to use. Either @code{"trace"}, @code{"debug"}, +@code{"info"}, @code{"warn"}, @code{"error"} or @code{"none"}. + +@item @code{openid-signin?} (default: @code{#t}) (type: boolean) +Whether to allow signing in using OpenID. + +@item @code{disable-registration?} (default: @code{#f}) (type: boolean) +Disallow registration, only allowing administrators to create accounts. + +@item @code{confirm-mail-on-registration?} (default: @code{#f}) (type: boolean) +Whether to require email confirmation when new users register. + +@item @code{require-signin-to-view?} (default: @code{#f}) (type: boolean) +Whether users must sign in before they can view the explore pages. + +@item @code{default-keep-email-private?} (default: @code{#f}) (type: boolean) +Whether by default a user email is displayed on their profile. + +@item @code{user-push-to-create?} (default: @code{#f}) (type: boolean) +Allow users to push local repositories to Forgejo and have them +automatically created for a user. + +@item @code{organization-push-to-create?} (default: @code{#f}) (type: boolean) +Allow users to push local repositories to Forgejo and have them +automatically created for an organization. + +@item @code{default-push-to-create-private?} (default: @code{#t}) (type: boolean) +Whether to make newly created repositories private by default when they +were created via push. + +@item @code{default-merge-style} (default: @code{"merge"}) (type: merge-style) +The default merge style to use. Either @code{"merge"}, @code{"rebase"}, +@code{"rebase-merge"}, @code{"squash"} or @code{"fast-forward-only"}. + +@item @code{default-trust-model} (default: @code{"committer"}) (type: trust-model) +The default trust model for repositories. Either @code{"collaborator"}, +@code{"committer"} or @code{"collaboratorcommitter"} + +@item @code{metrics?} (default: @code{#f}) (type: boolean) +Whether to enable the metrics endpoint. + +@item @code{metrics-token} (default: @code{""}) (type: string) +A secret to use, if authorization to the metrics endpoint is desired. + +@item @code{database-type} (default: @code{"sqlite3"}) (type: database-type) +The database type to use. Either @code{"sqlite3"}, @code{"mysql"} or +@code{"postgres"}. The sqlite3 type is the simplest to use, but a +full-fledged database like PostgreSQL may scale better for multiple +users. If you change this, make sure to adjust the other +@samp{database-*} values accordingly. Also note that currently, the +PostgreSQL and MySQL databases must be manually created: refer to the +official Forgejo documentation for +@uref{https://forgejo.org/docs/latest/admin/installation/database-preparation,database +preparation}. + +@item @code{database-host} (default: @code{"/var/run/postgresql"}) (type: string) +This is the @samp{@var{host}:@var{port}} tuple for remote database +MySQL/PostgreSQL hosts, or a local Unix-domain socket file. If using +MySQL, this should be adjusted to @file{/run/mysqld/mysqld.sock} + +@item @code{database-name} (default: @code{"forgejo"}) (type: string) +The MySQL/PostgreSQL database name to use. + +@item @code{database-user} (default: @code{"forgejo"}) (type: string) +The MySQL/PostgreSQL database user to use. + +@item @code{database-password-file} (type: maybe-string) +A file name containing the password to access the MySQL/PostgreSQL +database, for example @file{"/etc/forgejo/db_passwd"}. + +@item @code{database-tls?} (default: @code{#f}) (type: ssl-mode) +Whether the connection to a MySQL/PostgreSQL database should use TLS. +Set to @code{#t} to enable TLS with full verification or to +@code{'skip-verify} to enable TLS without verification. + +@end table + +@end deftp + + +@c %end of fragment + @node Database Services @subsection Database Services -- cgit v1.2.3