···27272828As per [RFC 0072](https://github.com/NixOS/rfcs/pull/72), all new documentation content should be written in [CommonMark](https://commonmark.org/) Markdown dialect.
29293030-Additional syntax extensions are available, though not all extensions can be used in NixOS option documentation. The following extensions are currently used:
3030+Additional syntax extensions are available, all of which can be used in NixOS option documentation. The following extensions are currently used:
31313232- []{#ssec-contributing-markup-anchors}
3333 Explicitly defined **anchors** on headings, to allow linking to sections. These should be always used, to ensure the anchors can be linked even when the heading text changes, and to prevent conflicts between [automatically assigned identifiers](https://github.com/jgm/commonmark-hs/blob/master/commonmark-extensions/test/auto_identifiers.md).
···3737 ```markdown
3838 ## Syntax {#sec-contributing-markup}
3939 ```
4040+4141+ ::: {.note}
4242+ NixOS option documentation does not support headings in general.
4343+ :::
40444145- []{#ssec-contributing-markup-anchors-inline}
4246 **Inline anchors**, which allow linking arbitrary place in the text (e.g. individual list items, sentences…).
···67716872 This syntax is taken from [MyST](https://myst-parser.readthedocs.io/en/latest/syntax/syntax.html#roles-an-in-line-extension-point). Though, the feature originates from [reStructuredText](https://www.sphinx-doc.org/en/master/usage/restructuredtext/roles.html#role-manpage) with slightly different syntax.
69737070- ::: {.note}
7171- Inline roles are available for option documentation.
7272- :::
7373-7474- []{#ssec-contributing-markup-admonitions}
7575 **Admonitions**, set off from the text to bring attention to something.
7676···9595 - [`note`](https://tdg.docbook.org/tdg/5.0/note.html)
9696 - [`tip`](https://tdg.docbook.org/tdg/5.0/tip.html)
9797 - [`warning`](https://tdg.docbook.org/tdg/5.0/warning.html)
9898-9999- ::: {.note}
100100- Admonitions are available for option documentation.
101101- :::
1029810399- []{#ssec-contributing-markup-definition-lists}
104100 [**Definition lists**](https://github.com/jgm/commonmark-hs/blob/master/commonmark-extensions/test/definition_lists.md), for defining a group of terms:
···23232424 meta = {
2525 maintainers = with lib.maintainers; [ ericsagnes ];
2626- doc = ./default.xml;
2626+ doc = ./default.md;
2727 buildDocsInSandbox = true;
2828 };
2929}
···31313232- `maintainers` contains a list of the module maintainers.
33333434-- `doc` points to a valid DocBook file containing the module
3434+- `doc` points to a valid [Nixpkgs-flavored CommonMark](
3535+ https://nixos.org/manual/nixpkgs/unstable/#sec-contributing-markup
3636+ ) file containing the module
3537 documentation. Its contents is automatically added to
3638 [](#ch-configuration). Changes to a module documentation have to
3739 be checked to not break building the NixOS manual:
38403941 ```ShellSession
4042 $ nix-build nixos/release.nix -A manual.x86_64-linux
4141- ```
4242-4343- This file should *not* usually be written by hand. Instead it is preferred
4444- to write documentation using CommonMark and converting it to CommonMark
4545- using pandoc. The simplest documentation can be converted using just
4646-4747- ```ShellSession
4848- $ pandoc doc.md -t docbook --top-level-division=chapter -f markdown+smart > doc.xml
4949- ```
5050-5151- More elaborate documentation may wish to add one or more of the pandoc
5252- filters used to build the remainder of the manual, for example the GNOME
5353- desktop uses
5454-5555- ```ShellSession
5656- $ pandoc gnome.md -t docbook --top-level-division=chapter \
5757- --extract-media=media -f markdown+smart \
5858- --lua-filter ../../../../../doc/build-aux/pandoc-filters/myst-reader/roles.lua \
5959- --lua-filter ../../../../../doc/build-aux/pandoc-filters/docbook-writer/rst-roles.lua \
6060- > gnome.xml
6143 ```
62446345- `buildDocsInSandbox` indicates whether the option documentation for the
···28282929 meta = {
3030 maintainers = with lib.maintainers; [ ericsagnes ];
3131- doc = ./default.xml;
3131+ doc = ./default.md;
3232 buildDocsInSandbox = true;
3333 };
3434}
···4242 </listitem>
4343 <listitem>
4444 <para>
4545- <literal>doc</literal> points to a valid DocBook file containing
4646- the module documentation. Its contents is automatically added to
4545+ <literal>doc</literal> points to a valid
4646+ <link xlink:href="https://nixos.org/manual/nixpkgs/unstable/#sec-contributing-markup">Nixpkgs-flavored
4747+ CommonMark</link> file containing the module documentation. Its
4848+ contents is automatically added to
4749 <xref linkend="ch-configuration" />. Changes to a module
4850 documentation have to be checked to not break building the NixOS
4951 manual:
5052 </para>
5153 <programlisting>
5254$ nix-build nixos/release.nix -A manual.x86_64-linux
5353-</programlisting>
5454- <para>
5555- This file should <emphasis>not</emphasis> usually be written by
5656- hand. Instead it is preferred to write documentation using
5757- CommonMark and converting it to CommonMark using pandoc. The
5858- simplest documentation can be converted using just
5959- </para>
6060- <programlisting>
6161-$ pandoc doc.md -t docbook --top-level-division=chapter -f markdown+smart > doc.xml
6262-</programlisting>
6363- <para>
6464- More elaborate documentation may wish to add one or more of the
6565- pandoc filters used to build the remainder of the manual, for
6666- example the GNOME desktop uses
6767- </para>
6868- <programlisting>
6969-$ pandoc gnome.md -t docbook --top-level-division=chapter \
7070- --extract-media=media -f markdown+smart \
7171- --lua-filter ../../../../../doc/build-aux/pandoc-filters/myst-reader/roles.lua \
7272- --lua-filter ../../../../../doc/build-aux/pandoc-filters/docbook-writer/rst-roles.lua \
7373- > gnome.xml
7455</programlisting>
7556 </listitem>
7657 <listitem>
-18
nixos/doc/manual/md-to-db.sh
···5050done
51515252popd
5353-5454-# now handle module chapters. we'll need extra checks to ensure that we don't process
5555-# markdown files we're not interested in, so we'll require an x.nix file for ever x.md
5656-# that we'll convert to xml.
5757-pushd "$DIR/../../modules"
5858-5959-mapfile -t MD_FILES < <(find . -type f -regex '.*\.md$')
6060-6161-for mf in ${MD_FILES[*]}; do
6262- [ -f "${mf%.md}.nix" ] || continue
6363-6464- pandoc --top-level-division=chapter "$mf" "${pandoc_flags[@]}" -o "${mf%.md}.xml"
6565- sed -i -e '1 i <!-- Do not edit this file directly, edit its companion .md instead\
6666- and regenerate this file using nixos/doc/manual/md-to-db.sh -->' \
6767- "${mf%.md}.xml"
6868-done
6969-7070-popd
+8-31
nixos/lib/make-options-doc/default.nix
···148148 '';
149149150150 optionsDocBook = pkgs.runCommand "options-docbook.xml" {
151151- MANPAGE_URLS = pkgs.path + "/doc/manpage-urls.json";
152152- OTD_DOCUMENT_TYPE = documentType;
153153- OTD_VARIABLE_LIST_ID = variablelistId;
154154- OTD_OPTION_ID_PREFIX = optionIdPrefix;
155155- OTD_REVISION = revision;
156156-157151 nativeBuildInputs = [
158158- (let
159159- # python3Minimal can't be overridden with packages on Darwin, due to a missing framework.
160160- # Instead of modifying stdenv, we take the easy way out, since most people on Darwin will
161161- # just be hacking on the Nixpkgs manual (which also uses make-options-doc).
162162- python = if pkgs.stdenv.isDarwin then pkgs.python3 else pkgs.python3Minimal;
163163- self = (python.override {
164164- inherit self;
165165- includeSiteCustomize = true;
166166- });
167167- in self.withPackages (p:
168168- let
169169- # TODO add our own small test suite when rendering is split out into a new tool
170170- markdown-it-py = p.markdown-it-py.override {
171171- disableTests = true;
172172- };
173173- mdit-py-plugins = p.mdit-py-plugins.override {
174174- inherit markdown-it-py;
175175- disableTests = true;
176176- };
177177- in [
178178- markdown-it-py
179179- mdit-py-plugins
180180- ]))
152152+ pkgs.nixos-render-docs
181153 ];
182154 } ''
183183- python ${./optionsToDocbook.py} \
155155+ nixos-render-docs options docbook \
156156+ --manpage-urls ${pkgs.path + "/doc/manpage-urls.json"} \
157157+ --revision ${lib.escapeShellArg revision} \
158158+ --document-type ${lib.escapeShellArg documentType} \
159159+ --varlist-id ${lib.escapeShellArg variablelistId} \
160160+ --id-prefix ${lib.escapeShellArg optionIdPrefix} \
184161 ${lib.optionalString markdownByDefault "--markdown-by-default"} \
185162 ${optionsJSON}/share/doc/nixos/options.json \
186186- > options.xml
163163+ options.xml
187164188165 if grep /nixpkgs/nixos/modules options.xml; then
189166 echo "The manual appears to depend on the location of Nixpkgs, which is bad"
-343
nixos/lib/make-options-doc/optionsToDocbook.py
···11-import collections
22-import json
33-import os
44-import sys
55-from typing import Any, Dict, List
66-from collections.abc import MutableMapping, Sequence
77-import inspect
88-99-# for MD conversion
1010-import markdown_it
1111-import markdown_it.renderer
1212-from markdown_it.token import Token
1313-from markdown_it.utils import OptionsDict
1414-from mdit_py_plugins.container import container_plugin
1515-from mdit_py_plugins.deflist import deflist_plugin
1616-from mdit_py_plugins.myst_role import myst_role_plugin
1717-from xml.sax.saxutils import escape, quoteattr
1818-1919-manpage_urls = json.load(open(os.getenv('MANPAGE_URLS')))
2020-2121-class Renderer(markdown_it.renderer.RendererProtocol):
2222- __output__ = "docbook"
2323- def __init__(self, parser=None):
2424- self.rules = {
2525- k: v
2626- for k, v in inspect.getmembers(self, predicate=inspect.ismethod)
2727- if not (k.startswith("render") or k.startswith("_"))
2828- } | {
2929- "container_{.note}_open": self._note_open,
3030- "container_{.note}_close": self._note_close,
3131- "container_{.important}_open": self._important_open,
3232- "container_{.important}_close": self._important_close,
3333- "container_{.warning}_open": self._warning_open,
3434- "container_{.warning}_close": self._warning_close,
3535- }
3636- def render(self, tokens: Sequence[Token], options: OptionsDict, env: MutableMapping) -> str:
3737- assert '-link-tag-stack' not in env
3838- env['-link-tag-stack'] = []
3939- assert '-deflist-stack' not in env
4040- env['-deflist-stack'] = []
4141- def do_one(i, token):
4242- if token.type == "inline":
4343- assert token.children is not None
4444- return self.renderInline(token.children, options, env)
4545- elif token.type in self.rules:
4646- return self.rules[token.type](tokens[i], tokens, i, options, env)
4747- else:
4848- raise NotImplementedError("md token not supported yet", token)
4949- return "".join(map(lambda arg: do_one(*arg), enumerate(tokens)))
5050- def renderInline(self, tokens: Sequence[Token], options: OptionsDict, env: MutableMapping) -> str:
5151- # HACK to support docbook links and xrefs. link handling is only necessary because the docbook
5252- # manpage stylesheet converts - in urls to a mathematical minus, which may be somewhat incorrect.
5353- for i, token in enumerate(tokens):
5454- if token.type != 'link_open':
5555- continue
5656- token.tag = 'link'
5757- # turn [](#foo) into xrefs
5858- if token.attrs['href'][0:1] == '#' and tokens[i + 1].type == 'link_close':
5959- token.tag = "xref"
6060- # turn <x> into links without contents
6161- if tokens[i + 1].type == 'text' and tokens[i + 1].content == token.attrs['href']:
6262- tokens[i + 1].content = ''
6363-6464- def do_one(i, token):
6565- if token.type in self.rules:
6666- return self.rules[token.type](tokens[i], tokens, i, options, env)
6767- else:
6868- raise NotImplementedError("md node not supported yet", token)
6969- return "".join(map(lambda arg: do_one(*arg), enumerate(tokens)))
7070-7171- def text(self, token, tokens, i, options, env):
7272- return escape(token.content)
7373- def paragraph_open(self, token, tokens, i, options, env):
7474- return "<para>"
7575- def paragraph_close(self, token, tokens, i, options, env):
7676- return "</para>"
7777- def hardbreak(self, token, tokens, i, options, env):
7878- return "<literallayout>\n</literallayout>"
7979- def softbreak(self, token, tokens, i, options, env):
8080- # should check options.breaks() and emit hard break if so
8181- return "\n"
8282- def code_inline(self, token, tokens, i, options, env):
8383- return f"<literal>{escape(token.content)}</literal>"
8484- def code_block(self, token, tokens, i, options, env):
8585- return f"<programlisting>{escape(token.content)}</programlisting>"
8686- def link_open(self, token, tokens, i, options, env):
8787- env['-link-tag-stack'].append(token.tag)
8888- (attr, start) = ('linkend', 1) if token.attrs['href'][0] == '#' else ('xlink:href', 0)
8989- return f"<{token.tag} {attr}={quoteattr(token.attrs['href'][start:])}>"
9090- def link_close(self, token, tokens, i, options, env):
9191- return f"</{env['-link-tag-stack'].pop()}>"
9292- def list_item_open(self, token, tokens, i, options, env):
9393- return "<listitem>"
9494- def list_item_close(self, token, tokens, i, options, env):
9595- return "</listitem>\n"
9696- # HACK open and close para for docbook change size. remove soon.
9797- def bullet_list_open(self, token, tokens, i, options, env):
9898- return "<para><itemizedlist>\n"
9999- def bullet_list_close(self, token, tokens, i, options, env):
100100- return "\n</itemizedlist></para>"
101101- def em_open(self, token, tokens, i, options, env):
102102- return "<emphasis>"
103103- def em_close(self, token, tokens, i, options, env):
104104- return "</emphasis>"
105105- def strong_open(self, token, tokens, i, options, env):
106106- return "<emphasis role=\"strong\">"
107107- def strong_close(self, token, tokens, i, options, env):
108108- return "</emphasis>"
109109- def fence(self, token, tokens, i, options, env):
110110- info = f" language={quoteattr(token.info)}" if token.info != "" else ""
111111- return f"<programlisting{info}>{escape(token.content)}</programlisting>"
112112- def blockquote_open(self, token, tokens, i, options, env):
113113- return "<para><blockquote>"
114114- def blockquote_close(self, token, tokens, i, options, env):
115115- return "</blockquote></para>"
116116- def _note_open(self, token, tokens, i, options, env):
117117- return "<para><note>"
118118- def _note_close(self, token, tokens, i, options, env):
119119- return "</note></para>"
120120- def _important_open(self, token, tokens, i, options, env):
121121- return "<para><important>"
122122- def _important_close(self, token, tokens, i, options, env):
123123- return "</important></para>"
124124- def _warning_open(self, token, tokens, i, options, env):
125125- return "<para><warning>"
126126- def _warning_close(self, token, tokens, i, options, env):
127127- return "</warning></para>"
128128- # markdown-it emits tokens based on the html syntax tree, but docbook is
129129- # slightly different. html has <dl>{<dt/>{<dd/>}}</dl>,
130130- # docbook has <variablelist>{<varlistentry><term/><listitem/></varlistentry>}<variablelist>
131131- # we have to reject multiple definitions for the same term for time being.
132132- def dl_open(self, token, tokens, i, options, env):
133133- env['-deflist-stack'].append({})
134134- return "<para><variablelist>"
135135- def dl_close(self, token, tokens, i, options, env):
136136- env['-deflist-stack'].pop()
137137- return "</variablelist></para>"
138138- def dt_open(self, token, tokens, i, options, env):
139139- env['-deflist-stack'][-1]['has-dd'] = False
140140- return "<varlistentry><term>"
141141- def dt_close(self, token, tokens, i, options, env):
142142- return "</term>"
143143- def dd_open(self, token, tokens, i, options, env):
144144- if env['-deflist-stack'][-1]['has-dd']:
145145- raise Exception("multiple definitions per term not supported")
146146- env['-deflist-stack'][-1]['has-dd'] = True
147147- return "<listitem>"
148148- def dd_close(self, token, tokens, i, options, env):
149149- return "</listitem></varlistentry>"
150150- def myst_role(self, token, tokens, i, options, env):
151151- if token.meta['name'] == 'command':
152152- return f"<command>{escape(token.content)}</command>"
153153- if token.meta['name'] == 'file':
154154- return f"<filename>{escape(token.content)}</filename>"
155155- if token.meta['name'] == 'var':
156156- return f"<varname>{escape(token.content)}</varname>"
157157- if token.meta['name'] == 'env':
158158- return f"<envar>{escape(token.content)}</envar>"
159159- if token.meta['name'] == 'option':
160160- return f"<option>{escape(token.content)}</option>"
161161- if token.meta['name'] == 'manpage':
162162- [page, section] = [ s.strip() for s in token.content.rsplit('(', 1) ]
163163- section = section[:-1]
164164- man = f"{page}({section})"
165165- title = f"<refentrytitle>{escape(page)}</refentrytitle>"
166166- vol = f"<manvolnum>{escape(section)}</manvolnum>"
167167- ref = f"<citerefentry>{title}{vol}</citerefentry>"
168168- if man in manpage_urls:
169169- return f"<link xlink:href={quoteattr(manpage_urls[man])}>{ref}</link>"
170170- else:
171171- return ref
172172- raise NotImplementedError("md node not supported yet", token)
173173-174174-md = (
175175- markdown_it.MarkdownIt(renderer_cls=Renderer)
176176- # TODO maybe fork the plugin and have only a single rule for all?
177177- .use(container_plugin, name="{.note}")
178178- .use(container_plugin, name="{.important}")
179179- .use(container_plugin, name="{.warning}")
180180- .use(deflist_plugin)
181181- .use(myst_role_plugin)
182182-)
183183-184184-# converts in-place!
185185-def convertMD(options: Dict[str, Any]) -> str:
186186- def optionIs(option: Dict[str, Any], key: str, typ: str) -> bool:
187187- if key not in option: return False
188188- if type(option[key]) != dict: return False
189189- if '_type' not in option[key]: return False
190190- return option[key]['_type'] == typ
191191-192192- def convertCode(name: str, option: Dict[str, Any], key: str):
193193- if optionIs(option, key, 'literalMD'):
194194- option[key] = md.render(f"*{key.capitalize()}:*\n{option[key]['text']}")
195195- elif optionIs(option, key, 'literalExpression'):
196196- code = option[key]['text']
197197- # for multi-line code blocks we only have to count ` runs at the beginning
198198- # of a line, but this is much easier.
199199- multiline = '\n' in code
200200- longest, current = (0, 0)
201201- for c in code:
202202- current = current + 1 if c == '`' else 0
203203- longest = max(current, longest)
204204- # inline literals need a space to separate ticks from content, code blocks
205205- # need newlines. inline literals need one extra tick, code blocks need three.
206206- ticks, sep = ('`' * (longest + (3 if multiline else 1)), '\n' if multiline else ' ')
207207- code = f"{ticks}{sep}{code}{sep}{ticks}"
208208- option[key] = md.render(f"*{key.capitalize()}:*\n{code}")
209209- elif optionIs(option, key, 'literalDocBook'):
210210- option[key] = f"<para><emphasis>{key.capitalize()}:</emphasis> {option[key]['text']}</para>"
211211- elif key in option:
212212- raise Exception(f"{name} {key} has unrecognized type", option[key])
213213-214214- for (name, option) in options.items():
215215- try:
216216- if optionIs(option, 'description', 'mdDoc'):
217217- option['description'] = md.render(option['description']['text'])
218218- elif markdownByDefault:
219219- option['description'] = md.render(option['description'])
220220- else:
221221- option['description'] = ("<nixos:option-description><para>" +
222222- option['description'] +
223223- "</para></nixos:option-description>")
224224-225225- convertCode(name, option, 'example')
226226- convertCode(name, option, 'default')
227227-228228- if 'relatedPackages' in option:
229229- option['relatedPackages'] = md.render(option['relatedPackages'])
230230- except Exception as e:
231231- raise Exception(f"Failed to render option {name}") from e
232232-233233- return options
234234-235235-id_translate_table = {
236236- ord('*'): ord('_'),
237237- ord('<'): ord('_'),
238238- ord(' '): ord('_'),
239239- ord('>'): ord('_'),
240240- ord('['): ord('_'),
241241- ord(']'): ord('_'),
242242- ord(':'): ord('_'),
243243- ord('"'): ord('_'),
244244-}
245245-246246-def need_env(n):
247247- if n not in os.environ:
248248- raise RuntimeError("required environment variable not set", n)
249249- return os.environ[n]
250250-251251-OTD_REVISION = need_env('OTD_REVISION')
252252-OTD_DOCUMENT_TYPE = need_env('OTD_DOCUMENT_TYPE')
253253-OTD_VARIABLE_LIST_ID = need_env('OTD_VARIABLE_LIST_ID')
254254-OTD_OPTION_ID_PREFIX = need_env('OTD_OPTION_ID_PREFIX')
255255-256256-def print_decl_def(header, locs):
257257- print(f"""<para><emphasis>{header}:</emphasis></para>""")
258258- print(f"""<simplelist>""")
259259- for loc in locs:
260260- # locations can be either plain strings (specific to nixpkgs), or attrsets
261261- # { name = "foo/bar.nix"; url = "https://github.com/....."; }
262262- if isinstance(loc, str):
263263- # Hyperlink the filename either to the NixOS github
264264- # repository (if it’s a module and we have a revision number),
265265- # or to the local filesystem.
266266- if not loc.startswith('/'):
267267- if OTD_REVISION == 'local':
268268- href = f"https://github.com/NixOS/nixpkgs/blob/master/{loc}"
269269- else:
270270- href = f"https://github.com/NixOS/nixpkgs/blob/{OTD_REVISION}/{loc}"
271271- else:
272272- href = f"file://{loc}"
273273- # Print the filename and make it user-friendly by replacing the
274274- # /nix/store/<hash> prefix by the default location of nixos
275275- # sources.
276276- if not loc.startswith('/'):
277277- name = f"<nixpkgs/{loc}>"
278278- elif loc.contains('nixops') and loc.contains('/nix/'):
279279- name = f"<nixops/{loc[loc.find('/nix/') + 5:]}>"
280280- else:
281281- name = loc
282282- print(f"""<member><filename xlink:href={quoteattr(href)}>""")
283283- print(escape(name))
284284- print(f"""</filename></member>""")
285285- else:
286286- href = f" xlink:href={quoteattr(loc['url'])}" if 'url' in loc else ""
287287- print(f"""<member><filename{href}>{escape(loc['name'])}</filename></member>""")
288288- print(f"""</simplelist>""")
289289-290290-markdownByDefault = False
291291-optOffset = 0
292292-for arg in sys.argv[1:]:
293293- if arg == "--markdown-by-default":
294294- optOffset += 1
295295- markdownByDefault = True
296296-297297-options = convertMD(json.load(open(sys.argv[1 + optOffset], 'r')))
298298-299299-keys = list(options.keys())
300300-keys.sort(key=lambda opt: [ (0 if p.startswith("enable") else 1 if p.startswith("package") else 2, p)
301301- for p in options[opt]['loc'] ])
302302-303303-print(f"""<?xml version="1.0" encoding="UTF-8"?>""")
304304-if OTD_DOCUMENT_TYPE == 'appendix':
305305- print("""<appendix xmlns="http://docbook.org/ns/docbook" xml:id="appendix-configuration-options">""")
306306- print(""" <title>Configuration Options</title>""")
307307-print(f"""<variablelist xmlns:xlink="http://www.w3.org/1999/xlink"
308308- xmlns:nixos="tag:nixos.org"
309309- xmlns="http://docbook.org/ns/docbook"
310310- xml:id="{OTD_VARIABLE_LIST_ID}">""")
311311-312312-for name in keys:
313313- opt = options[name]
314314- id = OTD_OPTION_ID_PREFIX + name.translate(id_translate_table)
315315- print(f"""<varlistentry>""")
316316- # NOTE adding extra spaces here introduces spaces into xref link expansions
317317- print(f"""<term xlink:href={quoteattr("#" + id)} xml:id={quoteattr(id)}>""", end='')
318318- print(f"""<option>{escape(name)}</option>""", end='')
319319- print(f"""</term>""")
320320- print(f"""<listitem>""")
321321- print(opt['description'])
322322- if typ := opt.get('type'):
323323- ro = " <emphasis>(read only)</emphasis>" if opt.get('readOnly', False) else ""
324324- print(f"""<para><emphasis>Type:</emphasis> {escape(typ)}{ro}</para>""")
325325- if default := opt.get('default'):
326326- print(default)
327327- if example := opt.get('example'):
328328- print(example)
329329- if related := opt.get('relatedPackages'):
330330- print(f"""<para>""")
331331- print(f""" <emphasis>Related packages:</emphasis>""")
332332- print(f"""</para>""")
333333- print(related)
334334- if decl := opt.get('declarations'):
335335- print_decl_def("Declared by", decl)
336336- if defs := opt.get('definitions'):
337337- print_decl_def("Defined by", defs)
338338- print(f"""</listitem>""")
339339- print(f"""</varlistentry>""")
340340-341341-print("""</variablelist>""")
342342-if OTD_DOCUMENT_TYPE == 'appendix':
343343- print("""</appendix>""")
···11-<!-- Do not edit this file directly, edit its companion .md instead
22- and regenerate this file using nixos/doc/manual/md-to-db.sh -->
33-<chapter xmlns="http://docbook.org/ns/docbook" xmlns:xlink="http://www.w3.org/1999/xlink" xml:id="module-services-input-methods">
44- <title>Input Methods</title>
55- <para>
66- Input methods are an operating system component that allows any
77- data, such as keyboard strokes or mouse movements, to be received as
88- input. In this way users can enter characters and symbols not found
99- on their input devices. Using an input method is obligatory for any
1010- language that has more graphemes than there are keys on the
1111- keyboard.
1212- </para>
1313- <para>
1414- The following input methods are available in NixOS:
1515- </para>
1616- <itemizedlist spacing="compact">
1717- <listitem>
1818- <para>
1919- IBus: The intelligent input bus.
2020- </para>
2121- </listitem>
2222- <listitem>
2323- <para>
2424- Fcitx: A customizable lightweight input method.
2525- </para>
2626- </listitem>
2727- <listitem>
2828- <para>
2929- Nabi: A Korean input method based on XIM.
3030- </para>
3131- </listitem>
3232- <listitem>
3333- <para>
3434- Uim: The universal input method, is a library with a XIM bridge.
3535- </para>
3636- </listitem>
3737- <listitem>
3838- <para>
3939- Hime: An extremely easy-to-use input method framework.
4040- </para>
4141- </listitem>
4242- <listitem>
4343- <para>
4444- Kime: Korean IME
4545- </para>
4646- </listitem>
4747- </itemizedlist>
4848- <section xml:id="module-services-input-methods-ibus">
4949- <title>IBus</title>
5050- <para>
5151- IBus is an Intelligent Input Bus. It provides full featured and
5252- user friendly input method user interface.
5353- </para>
5454- <para>
5555- The following snippet can be used to configure IBus:
5656- </para>
5757- <programlisting>
5858-i18n.inputMethod = {
5959- enabled = "ibus";
6060- ibus.engines = with pkgs.ibus-engines; [ anthy hangul mozc ];
6161-};
6262-</programlisting>
6363- <para>
6464- <literal>i18n.inputMethod.ibus.engines</literal> is optional and
6565- can be used to add extra IBus engines.
6666- </para>
6767- <para>
6868- Available extra IBus engines are:
6969- </para>
7070- <itemizedlist>
7171- <listitem>
7272- <para>
7373- Anthy (<literal>ibus-engines.anthy</literal>): Anthy is a
7474- system for Japanese input method. It converts Hiragana text to
7575- Kana Kanji mixed text.
7676- </para>
7777- </listitem>
7878- <listitem>
7979- <para>
8080- Hangul (<literal>ibus-engines.hangul</literal>): Korean input
8181- method.
8282- </para>
8383- </listitem>
8484- <listitem>
8585- <para>
8686- m17n (<literal>ibus-engines.m17n</literal>): m17n is an input
8787- method that uses input methods and corresponding icons in the
8888- m17n database.
8989- </para>
9090- </listitem>
9191- <listitem>
9292- <para>
9393- mozc (<literal>ibus-engines.mozc</literal>): A Japanese input
9494- method from Google.
9595- </para>
9696- </listitem>
9797- <listitem>
9898- <para>
9999- Table (<literal>ibus-engines.table</literal>): An input method
100100- that load tables of input methods.
101101- </para>
102102- </listitem>
103103- <listitem>
104104- <para>
105105- table-others (<literal>ibus-engines.table-others</literal>):
106106- Various table-based input methods. To use this, and any other
107107- table-based input methods, it must appear in the list of
108108- engines along with <literal>table</literal>. For example:
109109- </para>
110110- <programlisting>
111111-ibus.engines = with pkgs.ibus-engines; [ table table-others ];
112112-</programlisting>
113113- </listitem>
114114- </itemizedlist>
115115- <para>
116116- To use any input method, the package must be added in the
117117- configuration, as shown above, and also (after running
118118- <literal>nixos-rebuild</literal>) the input method must be added
119119- from IBus’ preference dialog.
120120- </para>
121121- <section xml:id="module-services-input-methods-troubleshooting">
122122- <title>Troubleshooting</title>
123123- <para>
124124- If IBus works in some applications but not others, a likely
125125- cause of this is that IBus is depending on a different version
126126- of <literal>glib</literal> to what the applications are
127127- depending on. This can be checked by running
128128- <literal>nix-store -q --requisites <path> | grep glib</literal>,
129129- where <literal><path></literal> is the path of either IBus
130130- or an application in the Nix store. The <literal>glib</literal>
131131- packages must match exactly. If they do not, uninstalling and
132132- reinstalling the application is a likely fix.
133133- </para>
134134- </section>
135135- </section>
136136- <section xml:id="module-services-input-methods-fcitx">
137137- <title>Fcitx</title>
138138- <para>
139139- Fcitx is an input method framework with extension support. It has
140140- three built-in Input Method Engine, Pinyin, QuWei and Table-based
141141- input methods.
142142- </para>
143143- <para>
144144- The following snippet can be used to configure Fcitx:
145145- </para>
146146- <programlisting>
147147-i18n.inputMethod = {
148148- enabled = "fcitx";
149149- fcitx.engines = with pkgs.fcitx-engines; [ mozc hangul m17n ];
150150-};
151151-</programlisting>
152152- <para>
153153- <literal>i18n.inputMethod.fcitx.engines</literal> is optional and
154154- can be used to add extra Fcitx engines.
155155- </para>
156156- <para>
157157- Available extra Fcitx engines are:
158158- </para>
159159- <itemizedlist spacing="compact">
160160- <listitem>
161161- <para>
162162- Anthy (<literal>fcitx-engines.anthy</literal>): Anthy is a
163163- system for Japanese input method. It converts Hiragana text to
164164- Kana Kanji mixed text.
165165- </para>
166166- </listitem>
167167- <listitem>
168168- <para>
169169- Chewing (<literal>fcitx-engines.chewing</literal>): Chewing is
170170- an intelligent Zhuyin input method. It is one of the most
171171- popular input methods among Traditional Chinese Unix users.
172172- </para>
173173- </listitem>
174174- <listitem>
175175- <para>
176176- Hangul (<literal>fcitx-engines.hangul</literal>): Korean input
177177- method.
178178- </para>
179179- </listitem>
180180- <listitem>
181181- <para>
182182- Unikey (<literal>fcitx-engines.unikey</literal>): Vietnamese
183183- input method.
184184- </para>
185185- </listitem>
186186- <listitem>
187187- <para>
188188- m17n (<literal>fcitx-engines.m17n</literal>): m17n is an input
189189- method that uses input methods and corresponding icons in the
190190- m17n database.
191191- </para>
192192- </listitem>
193193- <listitem>
194194- <para>
195195- mozc (<literal>fcitx-engines.mozc</literal>): A Japanese input
196196- method from Google.
197197- </para>
198198- </listitem>
199199- <listitem>
200200- <para>
201201- table-others (<literal>fcitx-engines.table-others</literal>):
202202- Various table-based input methods.
203203- </para>
204204- </listitem>
205205- </itemizedlist>
206206- </section>
207207- <section xml:id="module-services-input-methods-nabi">
208208- <title>Nabi</title>
209209- <para>
210210- Nabi is an easy to use Korean X input method. It allows you to
211211- enter phonetic Korean characters (hangul) and pictographic Korean
212212- characters (hanja).
213213- </para>
214214- <para>
215215- The following snippet can be used to configure Nabi:
216216- </para>
217217- <programlisting>
218218-i18n.inputMethod = {
219219- enabled = "nabi";
220220-};
221221-</programlisting>
222222- </section>
223223- <section xml:id="module-services-input-methods-uim">
224224- <title>Uim</title>
225225- <para>
226226- Uim (short for <quote>universal input method</quote>) is a
227227- multilingual input method framework. Applications can use it
228228- through so-called bridges.
229229- </para>
230230- <para>
231231- The following snippet can be used to configure uim:
232232- </para>
233233- <programlisting>
234234-i18n.inputMethod = {
235235- enabled = "uim";
236236-};
237237-</programlisting>
238238- <para>
239239- Note: The <xref linkend="opt-i18n.inputMethod.uim.toolbar" />
240240- option can be used to choose uim toolbar.
241241- </para>
242242- </section>
243243- <section xml:id="module-services-input-methods-hime">
244244- <title>Hime</title>
245245- <para>
246246- Hime is an extremely easy-to-use input method framework. It is
247247- lightweight, stable, powerful and supports many commonly used
248248- input methods, including Cangjie, Zhuyin, Dayi, Rank, Shrimp,
249249- Greek, Korean Pinyin, Latin Alphabet, etc…
250250- </para>
251251- <para>
252252- The following snippet can be used to configure Hime:
253253- </para>
254254- <programlisting>
255255-i18n.inputMethod = {
256256- enabled = "hime";
257257-};
258258-</programlisting>
259259- </section>
260260- <section xml:id="module-services-input-methods-kime">
261261- <title>Kime</title>
262262- <para>
263263- Kime is Korean IME. it’s built with Rust language and let you get
264264- simple, safe, fast Korean typing
265265- </para>
266266- <para>
267267- The following snippet can be used to configure Kime:
268268- </para>
269269- <programlisting>
270270-i18n.inputMethod = {
271271- enabled = "kime";
272272-};
273273-</programlisting>
274274- </section>
275275-</chapter>
+1-1
nixos/modules/misc/meta.nix
···4747 doc = mkOption {
4848 type = docFile;
4949 internal = true;
5050- example = "./meta.chapter.xml";
5050+ example = "./meta.chapter.md";
5151 description = lib.mdDoc ''
5252 Documentation prologue for the set of options of each module. This
5353 option should be defined at most once per module.
···11-<!-- Do not edit this file directly, edit its companion .md instead
22- and regenerate this file using nixos/doc/manual/md-to-db.sh -->
33-<chapter xmlns="http://docbook.org/ns/docbook" xmlns:xlink="http://www.w3.org/1999/xlink" xml:id="module-programs-digitalbitbox">
44- <title>Digital Bitbox</title>
55- <para>
66- Digital Bitbox is a hardware wallet and second-factor authenticator.
77- </para>
88- <para>
99- The <literal>digitalbitbox</literal> programs module may be
1010- installed by setting <literal>programs.digitalbitbox</literal> to
1111- <literal>true</literal> in a manner similar to
1212- </para>
1313- <programlisting>
1414-programs.digitalbitbox.enable = true;
1515-</programlisting>
1616- <para>
1717- and bundles the <literal>digitalbitbox</literal> package (see
1818- <xref linkend="sec-digitalbitbox-package" />), which contains the
1919- <literal>dbb-app</literal> and <literal>dbb-cli</literal> binaries,
2020- along with the hardware module (see
2121- <xref linkend="sec-digitalbitbox-hardware-module" />) which sets up
2222- the necessary udev rules to access the device.
2323- </para>
2424- <para>
2525- Enabling the digitalbitbox module is pretty much the easiest way to
2626- get a Digital Bitbox device working on your system.
2727- </para>
2828- <para>
2929- For more information, see
3030- <link xlink:href="https://digitalbitbox.com/start_linux">https://digitalbitbox.com/start_linux</link>.
3131- </para>
3232- <section xml:id="sec-digitalbitbox-package">
3333- <title>Package</title>
3434- <para>
3535- The binaries, <literal>dbb-app</literal> (a GUI tool) and
3636- <literal>dbb-cli</literal> (a CLI tool), are available through the
3737- <literal>digitalbitbox</literal> package which could be installed
3838- as follows:
3939- </para>
4040- <programlisting>
4141-environment.systemPackages = [
4242- pkgs.digitalbitbox
4343-];
4444-</programlisting>
4545- </section>
4646- <section xml:id="sec-digitalbitbox-hardware-module">
4747- <title>Hardware</title>
4848- <para>
4949- The digitalbitbox hardware package enables the udev rules for
5050- Digital Bitbox devices and may be installed as follows:
5151- </para>
5252- <programlisting>
5353-hardware.digitalbitbox.enable = true;
5454-</programlisting>
5555- <para>
5656- In order to alter the udev rules, one may provide different values
5757- for the <literal>udevRule51</literal> and
5858- <literal>udevRule52</literal> attributes by means of overriding as
5959- follows:
6060- </para>
6161- <programlisting>
6262-programs.digitalbitbox = {
6363- enable = true;
6464- package = pkgs.digitalbitbox.override {
6565- udevRule51 = "something else";
6666- };
6767-};
6868-</programlisting>
6969- </section>
7070-</chapter>
···11-<!-- Do not edit this file directly, edit its companion .md instead
22- and regenerate this file using nixos/doc/manual/md-to-db.sh -->
33-<chapter xmlns="http://docbook.org/ns/docbook" xmlns:xlink="http://www.w3.org/1999/xlink" xml:id="module-program-plotinus">
44- <title>Plotinus</title>
55- <para>
66- <emphasis>Source:</emphasis>
77- <filename>modules/programs/plotinus.nix</filename>
88- </para>
99- <para>
1010- <emphasis>Upstream documentation:</emphasis>
1111- <link xlink:href="https://github.com/p-e-w/plotinus">https://github.com/p-e-w/plotinus</link>
1212- </para>
1313- <para>
1414- Plotinus is a searchable command palette in every modern GTK
1515- application.
1616- </para>
1717- <para>
1818- When in a GTK 3 application and Plotinus is enabled, you can press
1919- <literal>Ctrl+Shift+P</literal> to open the command palette. The
2020- command palette provides a searchable list of of all menu items in
2121- the application.
2222- </para>
2323- <para>
2424- To enable Plotinus, add the following to your
2525- <filename>configuration.nix</filename>:
2626- </para>
2727- <programlisting>
2828-programs.plotinus.enable = true;
2929-</programlisting>
3030-</chapter>
···11-<!-- Do not edit this file directly, edit its companion .md instead
22- and regenerate this file using nixos/doc/manual/md-to-db.sh -->
33-<chapter xmlns="http://docbook.org/ns/docbook" xmlns:xlink="http://www.w3.org/1999/xlink" xml:id="module-programs-zsh-ohmyzsh">
44- <title>Oh my ZSH</title>
55- <para>
66- <link xlink:href="https://ohmyz.sh/"><literal>oh-my-zsh</literal></link>
77- is a framework to manage your
88- <link xlink:href="https://www.zsh.org/">ZSH</link> configuration
99- including completion scripts for several CLI tools or custom prompt
1010- themes.
1111- </para>
1212- <section xml:id="module-programs-oh-my-zsh-usage">
1313- <title>Basic usage</title>
1414- <para>
1515- The module uses the <literal>oh-my-zsh</literal> package with all
1616- available features. The initial setup using Nix expressions is
1717- fairly similar to the configuration format of
1818- <literal>oh-my-zsh</literal>.
1919- </para>
2020- <programlisting>
2121-{
2222- programs.zsh.ohMyZsh = {
2323- enable = true;
2424- plugins = [ "git" "python" "man" ];
2525- theme = "agnoster";
2626- };
2727-}
2828-</programlisting>
2929- <para>
3030- For a detailed explanation of these arguments please refer to the
3131- <link xlink:href="https://github.com/robbyrussell/oh-my-zsh/wiki"><literal>oh-my-zsh</literal>
3232- docs</link>.
3333- </para>
3434- <para>
3535- The expression generates the needed configuration and writes it
3636- into your <literal>/etc/zshrc</literal>.
3737- </para>
3838- </section>
3939- <section xml:id="module-programs-oh-my-zsh-additions">
4040- <title>Custom additions</title>
4141- <para>
4242- Sometimes third-party or custom scripts such as a modified theme
4343- may be needed. <literal>oh-my-zsh</literal> provides the
4444- <link xlink:href="https://github.com/robbyrussell/oh-my-zsh/wiki/Customization#overriding-internals"><literal>ZSH_CUSTOM</literal></link>
4545- environment variable for this which points to a directory with
4646- additional scripts.
4747- </para>
4848- <para>
4949- The module can do this as well:
5050- </para>
5151- <programlisting>
5252-{
5353- programs.zsh.ohMyZsh.custom = "~/path/to/custom/scripts";
5454-}
5555-</programlisting>
5656- </section>
5757- <section xml:id="module-programs-oh-my-zsh-environments">
5858- <title>Custom environments</title>
5959- <para>
6060- There are several extensions for <literal>oh-my-zsh</literal>
6161- packaged in <literal>nixpkgs</literal>. One of them is
6262- <link xlink:href="https://github.com/spwhitt/nix-zsh-completions">nix-zsh-completions</link>
6363- which bundles completion scripts and a plugin for
6464- <literal>oh-my-zsh</literal>.
6565- </para>
6666- <para>
6767- Rather than using a single mutable path for
6868- <literal>ZSH_CUSTOM</literal>, it’s also possible to generate this
6969- path from a list of Nix packages:
7070- </para>
7171- <programlisting>
7272-{ pkgs, ... }:
7373-{
7474- programs.zsh.ohMyZsh.customPkgs = [
7575- pkgs.nix-zsh-completions
7676- # and even more...
7777- ];
7878-}
7979-</programlisting>
8080- <para>
8181- Internally a single store path will be created using
8282- <literal>buildEnv</literal>. Please refer to the docs of
8383- <link xlink:href="https://nixos.org/nixpkgs/manual/#sec-building-environment"><literal>buildEnv</literal></link>
8484- for further reference.
8585- </para>
8686- <para>
8787- <emphasis>Please keep in mind that this is not compatible with
8888- <literal>programs.zsh.ohMyZsh.custom</literal> as it requires an
8989- immutable store path while <literal>custom</literal> shall remain
9090- mutable! An evaluation failure will be thrown if both
9191- <literal>custom</literal> and <literal>customPkgs</literal> are
9292- set.</emphasis>
9393- </para>
9494- </section>
9595- <section xml:id="module-programs-oh-my-zsh-packaging-customizations">
9696- <title>Package your own customizations</title>
9797- <para>
9898- If third-party customizations (e.g. new themes) are supposed to be
9999- added to <literal>oh-my-zsh</literal> there are several pitfalls
100100- to keep in mind:
101101- </para>
102102- <itemizedlist>
103103- <listitem>
104104- <para>
105105- To comply with the default structure of <literal>ZSH</literal>
106106- the entire output needs to be written to
107107- <literal>$out/share/zsh.</literal>
108108- </para>
109109- </listitem>
110110- <listitem>
111111- <para>
112112- Completion scripts are supposed to be stored at
113113- <literal>$out/share/zsh/site-functions</literal>. This
114114- directory is part of the
115115- <link xlink:href="http://zsh.sourceforge.net/Doc/Release/Functions.html"><literal>fpath</literal></link>
116116- and the package should be compatible with pure
117117- <literal>ZSH</literal> setups. The module will automatically
118118- link the contents of <literal>site-functions</literal> to
119119- completions directory in the proper store path.
120120- </para>
121121- </listitem>
122122- <listitem>
123123- <para>
124124- The <literal>plugins</literal> directory needs the structure
125125- <literal>pluginname/pluginname.plugin.zsh</literal> as
126126- structured in the
127127- <link xlink:href="https://github.com/robbyrussell/oh-my-zsh/tree/91b771914bc7c43dd7c7a43b586c5de2c225ceb7/plugins">upstream
128128- repo.</link>
129129- </para>
130130- </listitem>
131131- </itemizedlist>
132132- <para>
133133- A derivation for <literal>oh-my-zsh</literal> may look like this:
134134- </para>
135135- <programlisting>
136136-{ stdenv, fetchFromGitHub }:
137137-138138-stdenv.mkDerivation rec {
139139- name = "exemplary-zsh-customization-${version}";
140140- version = "1.0.0";
141141- src = fetchFromGitHub {
142142- # path to the upstream repository
143143- };
144144-145145- dontBuild = true;
146146- installPhase = ''
147147- mkdir -p $out/share/zsh/site-functions
148148- cp {themes,plugins} $out/share/zsh
149149- cp completions $out/share/zsh/site-functions
150150- '';
151151-}
152152-</programlisting>
153153- </section>
154154-</chapter>
···11-<!-- Do not edit this file directly, edit its companion .md instead
22- and regenerate this file using nixos/doc/manual/md-to-db.sh -->
33-<chapter xmlns="http://docbook.org/ns/docbook" xmlns:xlink="http://www.w3.org/1999/xlink" xml:id="module-security-acme">
44- <title>SSL/TLS Certificates with ACME</title>
55- <para>
66- NixOS supports automatic domain validation & certificate
77- retrieval and renewal using the ACME protocol. Any provider can be
88- used, but by default NixOS uses Let’s Encrypt. The alternative ACME
99- client
1010- <link xlink:href="https://go-acme.github.io/lego/">lego</link> is
1111- used under the hood.
1212- </para>
1313- <para>
1414- Automatic cert validation and configuration for Apache and Nginx
1515- virtual hosts is included in NixOS, however if you would like to
1616- generate a wildcard cert or you are not using a web server you will
1717- have to configure DNS based validation.
1818- </para>
1919- <section xml:id="module-security-acme-prerequisites">
2020- <title>Prerequisites</title>
2121- <para>
2222- To use the ACME module, you must accept the provider’s terms of
2323- service by setting
2424- <xref linkend="opt-security.acme.acceptTerms" /> to
2525- <literal>true</literal>. The Let’s Encrypt ToS can be found
2626- <link xlink:href="https://letsencrypt.org/repository/">here</link>.
2727- </para>
2828- <para>
2929- You must also set an email address to be used when creating
3030- accounts with Let’s Encrypt. You can set this for all certs with
3131- <xref linkend="opt-security.acme.defaults.email" /> and/or on a
3232- per-cert basis with
3333- <xref linkend="opt-security.acme.certs._name_.email" />. This
3434- address is only used for registration and renewal reminders, and
3535- cannot be used to administer the certificates in any way.
3636- </para>
3737- <para>
3838- Alternatively, you can use a different ACME server by changing the
3939- <xref linkend="opt-security.acme.defaults.server" /> option to a
4040- provider of your choosing, or just change the server for one cert
4141- with <xref linkend="opt-security.acme.certs._name_.server" />.
4242- </para>
4343- <para>
4444- You will need an HTTP server or DNS server for verification. For
4545- HTTP, the server must have a webroot defined that can serve
4646- <filename>.well-known/acme-challenge</filename>. This directory
4747- must be writeable by the user that will run the ACME client. For
4848- DNS, you must set up credentials with your provider/server for use
4949- with lego.
5050- </para>
5151- </section>
5252- <section xml:id="module-security-acme-nginx">
5353- <title>Using ACME certificates in Nginx</title>
5454- <para>
5555- NixOS supports fetching ACME certificates for you by setting
5656- <literal>enableACME = true;</literal> in a virtualHost config. We
5757- first create self-signed placeholder certificates in place of the
5858- real ACME certs. The placeholder certs are overwritten when the
5959- ACME certs arrive. For <literal>foo.example.com</literal> the
6060- config would look like this:
6161- </para>
6262- <programlisting>
6363-security.acme.acceptTerms = true;
6464-security.acme.defaults.email = "admin+acme@example.com";
6565-services.nginx = {
6666- enable = true;
6767- virtualHosts = {
6868- "foo.example.com" = {
6969- forceSSL = true;
7070- enableACME = true;
7171- # All serverAliases will be added as extra domain names on the certificate.
7272- serverAliases = [ "bar.example.com" ];
7373- locations."/" = {
7474- root = "/var/www";
7575- };
7676- };
7777-7878- # We can also add a different vhost and reuse the same certificate
7979- # but we have to append extraDomainNames manually beforehand:
8080- # security.acme.certs."foo.example.com".extraDomainNames = [ "baz.example.com" ];
8181- "baz.example.com" = {
8282- forceSSL = true;
8383- useACMEHost = "foo.example.com";
8484- locations."/" = {
8585- root = "/var/www";
8686- };
8787- };
8888- };
8989-}
9090-</programlisting>
9191- </section>
9292- <section xml:id="module-security-acme-httpd">
9393- <title>Using ACME certificates in Apache/httpd</title>
9494- <para>
9595- Using ACME certificates with Apache virtual hosts is identical to
9696- using them with Nginx. The attribute names are all the same, just
9797- replace <quote>nginx</quote> with <quote>httpd</quote> where
9898- appropriate.
9999- </para>
100100- </section>
101101- <section xml:id="module-security-acme-configuring">
102102- <title>Manual configuration of HTTP-01 validation</title>
103103- <para>
104104- First off you will need to set up a virtual host to serve the
105105- challenges. This example uses a vhost called
106106- <literal>certs.example.com</literal>, with the intent that you
107107- will generate certs for all your vhosts and redirect everyone to
108108- HTTPS.
109109- </para>
110110- <programlisting>
111111-security.acme.acceptTerms = true;
112112-security.acme.defaults.email = "admin+acme@example.com";
113113-114114-# /var/lib/acme/.challenges must be writable by the ACME user
115115-# and readable by the Nginx user. The easiest way to achieve
116116-# this is to add the Nginx user to the ACME group.
117117-users.users.nginx.extraGroups = [ "acme" ];
118118-119119-services.nginx = {
120120- enable = true;
121121- virtualHosts = {
122122- "acmechallenge.example.com" = {
123123- # Catchall vhost, will redirect users to HTTPS for all vhosts
124124- serverAliases = [ "*.example.com" ];
125125- locations."/.well-known/acme-challenge" = {
126126- root = "/var/lib/acme/.challenges";
127127- };
128128- locations."/" = {
129129- return = "301 https://$host$request_uri";
130130- };
131131- };
132132- };
133133-}
134134-# Alternative config for Apache
135135-users.users.wwwrun.extraGroups = [ "acme" ];
136136-services.httpd = {
137137- enable = true;
138138- virtualHosts = {
139139- "acmechallenge.example.com" = {
140140- # Catchall vhost, will redirect users to HTTPS for all vhosts
141141- serverAliases = [ "*.example.com" ];
142142- # /var/lib/acme/.challenges must be writable by the ACME user and readable by the Apache user.
143143- # By default, this is the case.
144144- documentRoot = "/var/lib/acme/.challenges";
145145- extraConfig = ''
146146- RewriteEngine On
147147- RewriteCond %{HTTPS} off
148148- RewriteCond %{REQUEST_URI} !^/\.well-known/acme-challenge [NC]
149149- RewriteRule (.*) https://%{HTTP_HOST}%{REQUEST_URI} [R=301]
150150- '';
151151- };
152152- };
153153-}
154154-</programlisting>
155155- <para>
156156- Now you need to configure ACME to generate a certificate.
157157- </para>
158158- <programlisting>
159159-security.acme.certs."foo.example.com" = {
160160- webroot = "/var/lib/acme/.challenges";
161161- email = "foo@example.com";
162162- # Ensure that the web server you use can read the generated certs
163163- # Take a look at the group option for the web server you choose.
164164- group = "nginx";
165165- # Since we have a wildcard vhost to handle port 80,
166166- # we can generate certs for anything!
167167- # Just make sure your DNS resolves them.
168168- extraDomainNames = [ "mail.example.com" ];
169169-};
170170-</programlisting>
171171- <para>
172172- The private key <filename>key.pem</filename> and certificate
173173- <filename>fullchain.pem</filename> will be put into
174174- <filename>/var/lib/acme/foo.example.com</filename>.
175175- </para>
176176- <para>
177177- Refer to <xref linkend="ch-options" /> for all available
178178- configuration options for the
179179- <link linkend="opt-security.acme.certs">security.acme</link>
180180- module.
181181- </para>
182182- </section>
183183- <section xml:id="module-security-acme-config-dns">
184184- <title>Configuring ACME for DNS validation</title>
185185- <para>
186186- This is useful if you want to generate a wildcard certificate,
187187- since ACME servers will only hand out wildcard certs over DNS
188188- validation. There are a number of supported DNS providers and
189189- servers you can utilise, see the
190190- <link xlink:href="https://go-acme.github.io/lego/dns/">lego
191191- docs</link> for provider/server specific configuration values. For
192192- the sake of these docs, we will provide a fully self-hosted
193193- example using bind.
194194- </para>
195195- <programlisting>
196196-services.bind = {
197197- enable = true;
198198- extraConfig = ''
199199- include "/var/lib/secrets/dnskeys.conf";
200200- '';
201201- zones = [
202202- rec {
203203- name = "example.com";
204204- file = "/var/db/bind/${name}";
205205- master = true;
206206- extraConfig = "allow-update { key rfc2136key.example.com.; };";
207207- }
208208- ];
209209-}
210210-211211-# Now we can configure ACME
212212-security.acme.acceptTerms = true;
213213-security.acme.defaults.email = "admin+acme@example.com";
214214-security.acme.certs."example.com" = {
215215- domain = "*.example.com";
216216- dnsProvider = "rfc2136";
217217- credentialsFile = "/var/lib/secrets/certs.secret";
218218- # We don't need to wait for propagation since this is a local DNS server
219219- dnsPropagationCheck = false;
220220-};
221221-</programlisting>
222222- <para>
223223- The <filename>dnskeys.conf</filename> and
224224- <filename>certs.secret</filename> must be kept secure and thus you
225225- should not keep their contents in your Nix config. Instead,
226226- generate them one time with a systemd service:
227227- </para>
228228- <programlisting>
229229-systemd.services.dns-rfc2136-conf = {
230230- requiredBy = ["acme-example.com.service" "bind.service"];
231231- before = ["acme-example.com.service" "bind.service"];
232232- unitConfig = {
233233- ConditionPathExists = "!/var/lib/secrets/dnskeys.conf";
234234- };
235235- serviceConfig = {
236236- Type = "oneshot";
237237- UMask = 0077;
238238- };
239239- path = [ pkgs.bind ];
240240- script = ''
241241- mkdir -p /var/lib/secrets
242242- chmod 755 /var/lib/secrets
243243- tsig-keygen rfc2136key.example.com > /var/lib/secrets/dnskeys.conf
244244- chown named:root /var/lib/secrets/dnskeys.conf
245245- chmod 400 /var/lib/secrets/dnskeys.conf
246246-247247- # extract secret value from the dnskeys.conf
248248- while read x y; do if [ "$x" = "secret" ]; then secret="''${y:1:''${#y}-3}"; fi; done < /var/lib/secrets/dnskeys.conf
249249-250250- cat > /var/lib/secrets/certs.secret << EOF
251251- RFC2136_NAMESERVER='127.0.0.1:53'
252252- RFC2136_TSIG_ALGORITHM='hmac-sha256.'
253253- RFC2136_TSIG_KEY='rfc2136key.example.com'
254254- RFC2136_TSIG_SECRET='$secret'
255255- EOF
256256- chmod 400 /var/lib/secrets/certs.secret
257257- '';
258258-};
259259-</programlisting>
260260- <para>
261261- Now you’re all set to generate certs! You should monitor the first
262262- invocation by running
263263- <literal>systemctl start acme-example.com.service & journalctl -fu acme-example.com.service</literal>
264264- and watching its log output.
265265- </para>
266266- </section>
267267- <section xml:id="module-security-acme-config-dns-with-vhosts">
268268- <title>Using DNS validation with web server virtual hosts</title>
269269- <para>
270270- It is possible to use DNS-01 validation with all certificates,
271271- including those automatically configured via the Nginx/Apache
272272- <link linkend="opt-services.nginx.virtualHosts._name_.enableACME"><literal>enableACME</literal></link>
273273- option. This configuration pattern is fully supported and part of
274274- the module’s test suite for Nginx + Apache.
275275- </para>
276276- <para>
277277- You must follow the guide above on configuring DNS-01 validation
278278- first, however instead of setting the options for one certificate
279279- (e.g.
280280- <xref linkend="opt-security.acme.certs._name_.dnsProvider" />) you
281281- will set them as defaults (e.g.
282282- <xref linkend="opt-security.acme.defaults.dnsProvider" />).
283283- </para>
284284- <programlisting>
285285-# Configure ACME appropriately
286286-security.acme.acceptTerms = true;
287287-security.acme.defaults.email = "admin+acme@example.com";
288288-security.acme.defaults = {
289289- dnsProvider = "rfc2136";
290290- credentialsFile = "/var/lib/secrets/certs.secret";
291291- # We don't need to wait for propagation since this is a local DNS server
292292- dnsPropagationCheck = false;
293293-};
294294-295295-# For each virtual host you would like to use DNS-01 validation with,
296296-# set acmeRoot = null
297297-services.nginx = {
298298- enable = true;
299299- virtualHosts = {
300300- "foo.example.com" = {
301301- enableACME = true;
302302- acmeRoot = null;
303303- };
304304- };
305305-}
306306-</programlisting>
307307- <para>
308308- And that’s it! Next time your configuration is rebuilt, or when
309309- you add a new virtualHost, it will be DNS-01 validated.
310310- </para>
311311- </section>
312312- <section xml:id="module-security-acme-root-owned">
313313- <title>Using ACME with services demanding root owned
314314- certificates</title>
315315- <para>
316316- Some services refuse to start if the configured certificate files
317317- are not owned by root. PostgreSQL and OpenSMTPD are examples of
318318- these. There is no way to change the user the ACME module uses (it
319319- will always be <literal>acme</literal>), however you can use
320320- systemd’s <literal>LoadCredential</literal> feature to resolve
321321- this elegantly. Below is an example configuration for OpenSMTPD,
322322- but this pattern can be applied to any service.
323323- </para>
324324- <programlisting>
325325-# Configure ACME however you like (DNS or HTTP validation), adding
326326-# the following configuration for the relevant certificate.
327327-# Note: You cannot use `systemctl reload` here as that would mean
328328-# the LoadCredential configuration below would be skipped and
329329-# the service would continue to use old certificates.
330330-security.acme.certs."mail.example.com".postRun = ''
331331- systemctl restart opensmtpd
332332-'';
333333-334334-# Now you must augment OpenSMTPD's systemd service to load
335335-# the certificate files.
336336-systemd.services.opensmtpd.requires = ["acme-finished-mail.example.com.target"];
337337-systemd.services.opensmtpd.serviceConfig.LoadCredential = let
338338- certDir = config.security.acme.certs."mail.example.com".directory;
339339-in [
340340- "cert.pem:${certDir}/cert.pem"
341341- "key.pem:${certDir}/key.pem"
342342-];
343343-344344-# Finally, configure OpenSMTPD to use these certs.
345345-services.opensmtpd = let
346346- credsDir = "/run/credentials/opensmtpd.service";
347347-in {
348348- enable = true;
349349- setSendmail = false;
350350- serverConfiguration = ''
351351- pki mail.example.com cert "${credsDir}/cert.pem"
352352- pki mail.example.com key "${credsDir}/key.pem"
353353- listen on localhost tls pki mail.example.com
354354- action act1 relay host smtp://127.0.0.1:10027
355355- match for local action act1
356356- '';
357357-};
358358-</programlisting>
359359- </section>
360360- <section xml:id="module-security-acme-regenerate">
361361- <title>Regenerating certificates</title>
362362- <para>
363363- Should you need to regenerate a particular certificate in a hurry,
364364- such as when a vulnerability is found in Let’s Encrypt, there is
365365- now a convenient mechanism for doing so. Running
366366- <literal>systemctl clean --what=state acme-example.com.service</literal>
367367- will remove all certificate files and the account data for the
368368- given domain, allowing you to then
369369- <literal>systemctl start acme-example.com.service</literal> to
370370- generate fresh ones.
371371- </para>
372372- </section>
373373- <section xml:id="module-security-acme-fix-jws">
374374- <title>Fixing JWS Verification error</title>
375375- <para>
376376- It is possible that your account credentials file may become
377377- corrupt and need to be regenerated. In this scenario lego will
378378- produce the error <literal>JWS verification error</literal>. The
379379- solution is to simply delete the associated accounts file and
380380- re-run the affected service(s).
381381- </para>
382382- <programlisting>
383383-# Find the accounts folder for the certificate
384384-systemctl cat acme-example.com.service | grep -Po 'accounts/[^:]*'
385385-export accountdir="$(!!)"
386386-# Move this folder to some place else
387387-mv /var/lib/acme/.lego/$accountdir{,.bak}
388388-# Recreate the folder using systemd-tmpfiles
389389-systemd-tmpfiles --create
390390-# Get a new account and reissue certificates
391391-# Note: Do this for all certs that share the same account email address
392392-systemctl start acme-example.com.service
393393-</programlisting>
394394- </section>
395395-</chapter>
···11-<!-- Do not edit this file directly, edit its companion .md instead
22- and regenerate this file using nixos/doc/manual/md-to-db.sh -->
33-<chapter xmlns="http://docbook.org/ns/docbook" xmlns:xlink="http://www.w3.org/1999/xlink" xml:id="module-borgbase">
44- <title>BorgBackup</title>
55- <para>
66- <emphasis>Source:</emphasis>
77- <filename>modules/services/backup/borgbackup.nix</filename>
88- </para>
99- <para>
1010- <emphasis>Upstream documentation:</emphasis>
1111- <link xlink:href="https://borgbackup.readthedocs.io/">https://borgbackup.readthedocs.io/</link>
1212- </para>
1313- <para>
1414- <link xlink:href="https://www.borgbackup.org/">BorgBackup</link>
1515- (short: Borg) is a deduplicating backup program. Optionally, it
1616- supports compression and authenticated encryption.
1717- </para>
1818- <para>
1919- The main goal of Borg is to provide an efficient and secure way to
2020- backup data. The data deduplication technique used makes Borg
2121- suitable for daily backups since only changes are stored. The
2222- authenticated encryption technique makes it suitable for backups to
2323- not fully trusted targets.
2424- </para>
2525- <section xml:id="module-services-backup-borgbackup-configuring">
2626- <title>Configuring</title>
2727- <para>
2828- A complete list of options for the Borgbase module may be found
2929- <link linkend="opt-services.borgbackup.jobs">here</link>.
3030- </para>
3131- </section>
3232- <section xml:id="opt-services-backup-borgbackup-local-directory">
3333- <title>Basic usage for a local backup</title>
3434- <para>
3535- A very basic configuration for backing up to a locally accessible
3636- directory is:
3737- </para>
3838- <programlisting>
3939-{
4040- opt.services.borgbackup.jobs = {
4141- { rootBackup = {
4242- paths = "/";
4343- exclude = [ "/nix" "/path/to/local/repo" ];
4444- repo = "/path/to/local/repo";
4545- doInit = true;
4646- encryption = {
4747- mode = "repokey";
4848- passphrase = "secret";
4949- };
5050- compression = "auto,lzma";
5151- startAt = "weekly";
5252- };
5353- }
5454- };
5555-}
5656-</programlisting>
5757- <warning>
5858- <para>
5959- If you do not want the passphrase to be stored in the
6060- world-readable Nix store, use passCommand. You find an example
6161- below.
6262- </para>
6363- </warning>
6464- </section>
6565- <section xml:id="opt-services-backup-create-server">
6666- <title>Create a borg backup server</title>
6767- <para>
6868- You should use a different SSH key for each repository you write
6969- to, because the specified keys are restricted to running borg
7070- serve and can only access this single repository. You need the
7171- output of the generate pub file.
7272- </para>
7373- <programlisting>
7474-# sudo ssh-keygen -N '' -t ed25519 -f /run/keys/id_ed25519_my_borg_repo
7575-# cat /run/keys/id_ed25519_my_borg_repo
7676-ssh-ed25519 AAAAC3NzaC1lZDI1NTE5AAAAID78zmOyA+5uPG4Ot0hfAy+sLDPU1L4AiIoRYEIVbbQ/ root@nixos
7777-</programlisting>
7878- <para>
7979- Add the following snippet to your NixOS configuration:
8080- </para>
8181- <programlisting>
8282-{
8383- services.borgbackup.repos = {
8484- my_borg_repo = {
8585- authorizedKeys = [
8686- "ssh-ed25519 AAAAC3NzaC1lZDI1NTE5AAAAID78zmOyA+5uPG4Ot0hfAy+sLDPU1L4AiIoRYEIVbbQ/ root@nixos"
8787- ] ;
8888- path = "/var/lib/my_borg_repo" ;
8989- };
9090- };
9191-}
9292-</programlisting>
9393- </section>
9494- <section xml:id="opt-services-backup-borgbackup-remote-server">
9595- <title>Backup to the borg repository server</title>
9696- <para>
9797- The following NixOS snippet creates an hourly backup to the
9898- service (on the host nixos) as created in the section above. We
9999- assume that you have stored a secret passphrasse in the file
100100- <filename>/run/keys/borgbackup_passphrase</filename>, which should
101101- be only accessible by root
102102- </para>
103103- <programlisting>
104104-{
105105- services.borgbackup.jobs = {
106106- backupToLocalServer = {
107107- paths = [ "/etc/nixos" ];
108108- doInit = true;
109109- repo = "borg@nixos:." ;
110110- encryption = {
111111- mode = "repokey-blake2";
112112- passCommand = "cat /run/keys/borgbackup_passphrase";
113113- };
114114- environment = { BORG_RSH = "ssh -i /run/keys/id_ed25519_my_borg_repo"; };
115115- compression = "auto,lzma";
116116- startAt = "hourly";
117117- };
118118- };
119119-};
120120-</programlisting>
121121- <para>
122122- The following few commands (run as root) let you test your backup.
123123- </para>
124124- <programlisting>
125125-> nixos-rebuild switch
126126-...restarting the following units: polkit.service
127127-> systemctl restart borgbackup-job-backupToLocalServer
128128-> sleep 10
129129-> systemctl restart borgbackup-job-backupToLocalServer
130130-> export BORG_PASSPHRASE=topSecrect
131131-> borg list --rsh='ssh -i /run/keys/id_ed25519_my_borg_repo' borg@nixos:.
132132-nixos-backupToLocalServer-2020-03-30T21:46:17 Mon, 2020-03-30 21:46:19 [84feb97710954931ca384182f5f3cb90665f35cef214760abd7350fb064786ac]
133133-nixos-backupToLocalServer-2020-03-30T21:46:30 Mon, 2020-03-30 21:46:32 [e77321694ecd160ca2228611747c6ad1be177d6e0d894538898de7a2621b6e68]
134134-</programlisting>
135135- </section>
136136- <section xml:id="opt-services-backup-borgbackup-borgbase">
137137- <title>Backup to a hosting service</title>
138138- <para>
139139- Several companies offer
140140- <link xlink:href="https://www.borgbackup.org/support/commercial.html">(paid)
141141- hosting services</link> for Borg repositories.
142142- </para>
143143- <para>
144144- To backup your home directory to borgbase you have to:
145145- </para>
146146- <itemizedlist>
147147- <listitem>
148148- <para>
149149- Generate a SSH key without a password, to access the remote
150150- server. E.g.
151151- </para>
152152- <programlisting>
153153-sudo ssh-keygen -N '' -t ed25519 -f /run/keys/id_ed25519_borgbase
154154-</programlisting>
155155- </listitem>
156156- <listitem>
157157- <para>
158158- Create the repository on the server by following the
159159- instructions for your hosting server.
160160- </para>
161161- </listitem>
162162- <listitem>
163163- <para>
164164- Initialize the repository on the server. Eg.
165165- </para>
166166- <programlisting>
167167-sudo borg init --encryption=repokey-blake2 \
168168- -rsh "ssh -i /run/keys/id_ed25519_borgbase" \
169169- zzz2aaaaa@zzz2aaaaa.repo.borgbase.com:repo
170170-</programlisting>
171171- </listitem>
172172- <listitem>
173173- <para>
174174- Add it to your NixOS configuration, e.g.
175175- </para>
176176- <programlisting>
177177-{
178178- services.borgbackup.jobs = {
179179- my_Remote_Backup = {
180180- paths = [ "/" ];
181181- exclude = [ "/nix" "'**/.cache'" ];
182182- repo = "zzz2aaaaa@zzz2aaaaa.repo.borgbase.com:repo";
183183- encryption = {
184184- mode = "repokey-blake2";
185185- passCommand = "cat /run/keys/borgbackup_passphrase";
186186- };
187187- environment = { BORG_RSH = "ssh -i /run/keys/id_ed25519_borgbase"; };
188188- compression = "auto,lzma";
189189- startAt = "daily";
190190- };
191191- };
192192-}}
193193-</programlisting>
194194- </listitem>
195195- </itemizedlist>
196196- </section>
197197- <section xml:id="opt-services-backup-borgbackup-vorta">
198198- <title>Vorta backup client for the desktop</title>
199199- <para>
200200- Vorta is a backup client for macOS and Linux desktops. It
201201- integrates the mighty BorgBackup with your desktop environment to
202202- protect your data from disk failure, ransomware and theft.
203203- </para>
204204- <para>
205205- It can be installed in NixOS e.g. by adding
206206- <literal>pkgs.vorta</literal> to
207207- <xref linkend="opt-environment.systemPackages" />.
208208- </para>
209209- <para>
210210- Details about using Vorta can be found under
211211- <link xlink:href="https://vorta.borgbase.com/usage">https://vorta.borgbase.com</link>
212212- .
213213- </para>
214214- </section>
215215-</chapter>
···11-<!-- Do not edit this file directly, edit its companion .md instead
22- and regenerate this file using nixos/doc/manual/md-to-db.sh -->
33-<chapter xmlns="http://docbook.org/ns/docbook" xmlns:xlink="http://www.w3.org/1999/xlink" xml:id="module-services-foundationdb">
44- <title>FoundationDB</title>
55- <para>
66- <emphasis>Source:</emphasis>
77- <filename>modules/services/databases/foundationdb.nix</filename>
88- </para>
99- <para>
1010- <emphasis>Upstream documentation:</emphasis>
1111- <link xlink:href="https://apple.github.io/foundationdb/">https://apple.github.io/foundationdb/</link>
1212- </para>
1313- <para>
1414- <emphasis>Maintainer:</emphasis> Austin Seipp
1515- </para>
1616- <para>
1717- <emphasis>Available version(s):</emphasis> 5.1.x, 5.2.x, 6.0.x
1818- </para>
1919- <para>
2020- FoundationDB (or <quote>FDB</quote>) is an open source, distributed,
2121- transactional key-value store.
2222- </para>
2323- <section xml:id="module-services-foundationdb-configuring">
2424- <title>Configuring and basic setup</title>
2525- <para>
2626- To enable FoundationDB, add the following to your
2727- <filename>configuration.nix</filename>:
2828- </para>
2929- <programlisting>
3030-services.foundationdb.enable = true;
3131-services.foundationdb.package = pkgs.foundationdb52; # FoundationDB 5.2.x
3232-</programlisting>
3333- <para>
3434- The <option>services.foundationdb.package</option> option is
3535- required, and must always be specified. Due to the fact
3636- FoundationDB network protocols and on-disk storage formats may
3737- change between (major) versions, and upgrades must be explicitly
3838- handled by the user, you must always manually specify this
3939- yourself so that the NixOS module will use the proper version.
4040- Note that minor, bugfix releases are always compatible.
4141- </para>
4242- <para>
4343- After running <command>nixos-rebuild</command>, you can verify
4444- whether FoundationDB is running by executing
4545- <command>fdbcli</command> (which is added to
4646- <option>environment.systemPackages</option>):
4747- </para>
4848- <programlisting>
4949-$ sudo -u foundationdb fdbcli
5050-Using cluster file `/etc/foundationdb/fdb.cluster'.
5151-5252-The database is available.
5353-5454-Welcome to the fdbcli. For help, type `help'.
5555-fdb> status
5656-5757-Using cluster file `/etc/foundationdb/fdb.cluster'.
5858-5959-Configuration:
6060- Redundancy mode - single
6161- Storage engine - memory
6262- Coordinators - 1
6363-6464-Cluster:
6565- FoundationDB processes - 1
6666- Machines - 1
6767- Memory availability - 5.4 GB per process on machine with least available
6868- Fault Tolerance - 0 machines
6969- Server time - 04/20/18 15:21:14
7070-7171-...
7272-7373-fdb>
7474-</programlisting>
7575- <para>
7676- You can also write programs using the available client libraries.
7777- For example, the following Python program can be run in order to
7878- grab the cluster status, as a quick example. (This example uses
7979- <command>nix-shell</command> shebang support to automatically
8080- supply the necessary Python modules).
8181- </para>
8282- <programlisting>
8383-a@link> cat fdb-status.py
8484-#! /usr/bin/env nix-shell
8585-#! nix-shell -i python -p python pythonPackages.foundationdb52
8686-8787-import fdb
8888-import json
8989-9090-def main():
9191- fdb.api_version(520)
9292- db = fdb.open()
9393-9494- @fdb.transactional
9595- def get_status(tr):
9696- return str(tr['\xff\xff/status/json'])
9797-9898- obj = json.loads(get_status(db))
9999- print('FoundationDB available: %s' % obj['client']['database_status']['available'])
100100-101101-if __name__ == "__main__":
102102- main()
103103-a@link> chmod +x fdb-status.py
104104-a@link> ./fdb-status.py
105105-FoundationDB available: True
106106-a@link>
107107-</programlisting>
108108- <para>
109109- FoundationDB is run under the <command>foundationdb</command> user
110110- and group by default, but this may be changed in the NixOS
111111- configuration. The systemd unit
112112- <command>foundationdb.service</command> controls the
113113- <command>fdbmonitor</command> process.
114114- </para>
115115- <para>
116116- By default, the NixOS module for FoundationDB creates a single
117117- SSD-storage based database for development and basic usage. This
118118- storage engine is designed for SSDs and will perform poorly on
119119- HDDs; however it can handle far more data than the alternative
120120- <quote>memory</quote> engine and is a better default choice for
121121- most deployments. (Note that you can change the storage backend
122122- on-the-fly for a given FoundationDB cluster using
123123- <command>fdbcli</command>.)
124124- </para>
125125- <para>
126126- Furthermore, only 1 server process and 1 backup agent are started
127127- in the default configuration. See below for more on scaling to
128128- increase this.
129129- </para>
130130- <para>
131131- FoundationDB stores all data for all server processes under
132132- <filename>/var/lib/foundationdb</filename>. You can override this
133133- using <option>services.foundationdb.dataDir</option>, e.g.
134134- </para>
135135- <programlisting>
136136-services.foundationdb.dataDir = "/data/fdb";
137137-</programlisting>
138138- <para>
139139- Similarly, logs are stored under
140140- <filename>/var/log/foundationdb</filename> by default, and there
141141- is a corresponding <option>services.foundationdb.logDir</option>
142142- as well.
143143- </para>
144144- </section>
145145- <section xml:id="module-services-foundationdb-scaling">
146146- <title>Scaling processes and backup agents</title>
147147- <para>
148148- Scaling the number of server processes is quite easy; simply
149149- specify <option>services.foundationdb.serverProcesses</option> to
150150- be the number of FoundationDB worker processes that should be
151151- started on the machine.
152152- </para>
153153- <para>
154154- FoundationDB worker processes typically require 4GB of RAM
155155- per-process at minimum for good performance, so this option is set
156156- to 1 by default since the maximum amount of RAM is unknown. You’re
157157- advised to abide by this restriction, so pick a number of
158158- processes so that each has 4GB or more.
159159- </para>
160160- <para>
161161- A similar option exists in order to scale backup agent processes,
162162- <option>services.foundationdb.backupProcesses</option>. Backup
163163- agents are not as performance/RAM sensitive, so feel free to
164164- experiment with the number of available backup processes.
165165- </para>
166166- </section>
167167- <section xml:id="module-services-foundationdb-clustering">
168168- <title>Clustering</title>
169169- <para>
170170- FoundationDB on NixOS works similarly to other Linux systems, so
171171- this section will be brief. Please refer to the full FoundationDB
172172- documentation for more on clustering.
173173- </para>
174174- <para>
175175- FoundationDB organizes clusters using a set of
176176- <emphasis>coordinators</emphasis>, which are just
177177- specially-designated worker processes. By default, every
178178- installation of FoundationDB on NixOS will start as its own
179179- individual cluster, with a single coordinator: the first worker
180180- process on <command>localhost</command>.
181181- </para>
182182- <para>
183183- Coordinators are specified globally using the
184184- <command>/etc/foundationdb/fdb.cluster</command> file, which all
185185- servers and client applications will use to find and join
186186- coordinators. Note that this file <emphasis>can not</emphasis> be
187187- managed by NixOS so easily: FoundationDB is designed so that it
188188- will rewrite the file at runtime for all clients and nodes when
189189- cluster coordinators change, with clients transparently handling
190190- this without intervention. It is fundamentally a mutable file, and
191191- you should not try to manage it in any way in NixOS.
192192- </para>
193193- <para>
194194- When dealing with a cluster, there are two main things you want to
195195- do:
196196- </para>
197197- <itemizedlist spacing="compact">
198198- <listitem>
199199- <para>
200200- Add a node to the cluster for storage/compute.
201201- </para>
202202- </listitem>
203203- <listitem>
204204- <para>
205205- Promote an ordinary worker to a coordinator.
206206- </para>
207207- </listitem>
208208- </itemizedlist>
209209- <para>
210210- A node must already be a member of the cluster in order to
211211- properly be promoted to a coordinator, so you must always add it
212212- first if you wish to promote it.
213213- </para>
214214- <para>
215215- To add a machine to a FoundationDB cluster:
216216- </para>
217217- <itemizedlist spacing="compact">
218218- <listitem>
219219- <para>
220220- Choose one of the servers to start as the initial coordinator.
221221- </para>
222222- </listitem>
223223- <listitem>
224224- <para>
225225- Copy the <command>/etc/foundationdb/fdb.cluster</command> file
226226- from this server to all the other servers. Restart
227227- FoundationDB on all of these other servers, so they join the
228228- cluster.
229229- </para>
230230- </listitem>
231231- <listitem>
232232- <para>
233233- All of these servers are now connected and working together in
234234- the cluster, under the chosen coordinator.
235235- </para>
236236- </listitem>
237237- </itemizedlist>
238238- <para>
239239- At this point, you can add as many nodes as you want by just
240240- repeating the above steps. By default there will still be a single
241241- coordinator: you can use <command>fdbcli</command> to change this
242242- and add new coordinators.
243243- </para>
244244- <para>
245245- As a convenience, FoundationDB can automatically assign
246246- coordinators based on the redundancy mode you wish to achieve for
247247- the cluster. Once all the nodes have been joined, simply set the
248248- replication policy, and then issue the
249249- <command>coordinators auto</command> command
250250- </para>
251251- <para>
252252- For example, assuming we have 3 nodes available, we can enable
253253- double redundancy mode, then auto-select coordinators. For double
254254- redundancy, 3 coordinators is ideal: therefore FoundationDB will
255255- make <emphasis>every</emphasis> node a coordinator automatically:
256256- </para>
257257- <programlisting>
258258-fdbcli> configure double ssd
259259-fdbcli> coordinators auto
260260-</programlisting>
261261- <para>
262262- This will transparently update all the servers within seconds, and
263263- appropriately rewrite the <command>fdb.cluster</command> file, as
264264- well as informing all client processes to do the same.
265265- </para>
266266- </section>
267267- <section xml:id="module-services-foundationdb-connectivity">
268268- <title>Client connectivity</title>
269269- <para>
270270- By default, all clients must use the current
271271- <command>fdb.cluster</command> file to access a given FoundationDB
272272- cluster. This file is located by default in
273273- <command>/etc/foundationdb/fdb.cluster</command> on all machines
274274- with the FoundationDB service enabled, so you may copy the active
275275- one from your cluster to a new node in order to connect, if it is
276276- not part of the cluster.
277277- </para>
278278- </section>
279279- <section xml:id="module-services-foundationdb-authorization">
280280- <title>Client authorization and TLS</title>
281281- <para>
282282- By default, any user who can connect to a FoundationDB process
283283- with the correct cluster configuration can access anything.
284284- FoundationDB uses a pluggable design to transport security, and
285285- out of the box it supports a LibreSSL-based plugin for TLS
286286- support. This plugin not only does in-flight encryption, but also
287287- performs client authorization based on the given endpoint’s
288288- certificate chain. For example, a FoundationDB server may be
289289- configured to only accept client connections over TLS, where the
290290- client TLS certificate is from organization <emphasis>Acme
291291- Co</emphasis> in the <emphasis>Research and Development</emphasis>
292292- unit.
293293- </para>
294294- <para>
295295- Configuring TLS with FoundationDB is done using the
296296- <option>services.foundationdb.tls</option> options in order to
297297- control the peer verification string, as well as the certificate
298298- and its private key.
299299- </para>
300300- <para>
301301- Note that the certificate and its private key must be accessible
302302- to the FoundationDB user account that the server runs under. These
303303- files are also NOT managed by NixOS, as putting them into the
304304- store may reveal private information.
305305- </para>
306306- <para>
307307- After you have a key and certificate file in place, it is not
308308- enough to simply set the NixOS module options – you must also
309309- configure the <command>fdb.cluster</command> file to specify that
310310- a given set of coordinators use TLS. This is as simple as adding
311311- the suffix <command>:tls</command> to your cluster coordinator
312312- configuration, after the port number. For example, assuming you
313313- have a coordinator on localhost with the default configuration,
314314- simply specifying:
315315- </para>
316316- <programlisting>
317317-XXXXXX:XXXXXX@127.0.0.1:4500:tls
318318-</programlisting>
319319- <para>
320320- will configure all clients and server processes to use TLS from
321321- now on.
322322- </para>
323323- </section>
324324- <section xml:id="module-services-foundationdb-disaster-recovery">
325325- <title>Backups and Disaster Recovery</title>
326326- <para>
327327- The usual rules for doing FoundationDB backups apply on NixOS as
328328- written in the FoundationDB manual. However, one important
329329- difference is the security profile for NixOS: by default, the
330330- <command>foundationdb</command> systemd unit uses <emphasis>Linux
331331- namespaces</emphasis> to restrict write access to the system,
332332- except for the log directory, data directory, and the
333333- <command>/etc/foundationdb/</command> directory. This is enforced
334334- by default and cannot be disabled.
335335- </para>
336336- <para>
337337- However, a side effect of this is that the
338338- <command>fdbbackup</command> command doesn’t work properly for
339339- local filesystem backups: FoundationDB uses a server process
340340- alongside the database processes to perform backups and copy the
341341- backups to the filesystem. As a result, this process is put under
342342- the restricted namespaces above: the backup process can only write
343343- to a limited number of paths.
344344- </para>
345345- <para>
346346- In order to allow flexible backup locations on local disks, the
347347- FoundationDB NixOS module supports a
348348- <option>services.foundationdb.extraReadWritePaths</option> option.
349349- This option takes a list of paths, and adds them to the systemd
350350- unit, allowing the processes inside the service to write (and
351351- read) the specified directories.
352352- </para>
353353- <para>
354354- For example, to create backups in
355355- <command>/opt/fdb-backups</command>, first set up the paths in the
356356- module options:
357357- </para>
358358- <programlisting>
359359-services.foundationdb.extraReadWritePaths = [ "/opt/fdb-backups" ];
360360-</programlisting>
361361- <para>
362362- Restart the FoundationDB service, and it will now be able to write
363363- to this directory (even if it does not yet exist.) Note: this path
364364- <emphasis>must</emphasis> exist before restarting the unit.
365365- Otherwise, systemd will not include it in the private FoundationDB
366366- namespace (and it will not add it dynamically at runtime).
367367- </para>
368368- <para>
369369- You can now perform a backup:
370370- </para>
371371- <programlisting>
372372-$ sudo -u foundationdb fdbbackup start -t default -d file:///opt/fdb-backups
373373-$ sudo -u foundationdb fdbbackup status -t default
374374-</programlisting>
375375- </section>
376376- <section xml:id="module-services-foundationdb-limitations">
377377- <title>Known limitations</title>
378378- <para>
379379- The FoundationDB setup for NixOS should currently be considered
380380- beta. FoundationDB is not new software, but the NixOS compilation
381381- and integration has only undergone fairly basic testing of all the
382382- available functionality.
383383- </para>
384384- <itemizedlist spacing="compact">
385385- <listitem>
386386- <para>
387387- There is no way to specify individual parameters for
388388- individual <command>fdbserver</command> processes. Currently,
389389- all server processes inherit all the global
390390- <command>fdbmonitor</command> settings.
391391- </para>
392392- </listitem>
393393- <listitem>
394394- <para>
395395- Ruby bindings are not currently installed.
396396- </para>
397397- </listitem>
398398- <listitem>
399399- <para>
400400- Go bindings are not currently installed.
401401- </para>
402402- </listitem>
403403- </itemizedlist>
404404- </section>
405405- <section xml:id="module-services-foundationdb-options">
406406- <title>Options</title>
407407- <para>
408408- NixOS’s FoundationDB module allows you to configure all of the
409409- most relevant configuration options for
410410- <command>fdbmonitor</command>, matching it quite closely. A
411411- complete list of options for the FoundationDB module may be found
412412- <link linkend="opt-services.foundationdb.enable">here</link>. You
413413- should also read the FoundationDB documentation as well.
414414- </para>
415415- </section>
416416- <section xml:id="module-services-foundationdb-full-docs">
417417- <title>Full documentation</title>
418418- <para>
419419- FoundationDB is a complex piece of software, and requires careful
420420- administration to properly use. Full documentation for
421421- administration can be found here:
422422- <link xlink:href="https://apple.github.io/foundationdb/">https://apple.github.io/foundationdb/</link>.
423423- </para>
424424- </section>
425425-</chapter>
···11-<!-- Do not edit this file directly, edit its companion .md instead
22- and regenerate this file using nixos/doc/manual/md-to-db.sh -->
33-<chapter xmlns="http://docbook.org/ns/docbook" xmlns:xlink="http://www.w3.org/1999/xlink" xml:id="module-postgresql">
44- <title>PostgreSQL</title>
55- <para>
66- <emphasis>Source:</emphasis>
77- <filename>modules/services/databases/postgresql.nix</filename>
88- </para>
99- <para>
1010- <emphasis>Upstream documentation:</emphasis>
1111- <link xlink:href="http://www.postgresql.org/docs/">http://www.postgresql.org/docs/</link>
1212- </para>
1313- <para>
1414- PostgreSQL is an advanced, free relational database.
1515- </para>
1616- <section xml:id="module-services-postgres-configuring">
1717- <title>Configuring</title>
1818- <para>
1919- To enable PostgreSQL, add the following to your
2020- <filename>configuration.nix</filename>:
2121- </para>
2222- <programlisting>
2323-services.postgresql.enable = true;
2424-services.postgresql.package = pkgs.postgresql_11;
2525-</programlisting>
2626- <para>
2727- Note that you are required to specify the desired version of
2828- PostgreSQL (e.g. <literal>pkgs.postgresql_11</literal>). Since
2929- upgrading your PostgreSQL version requires a database dump and
3030- reload (see below), NixOS cannot provide a default value for
3131- <xref linkend="opt-services.postgresql.package" /> such as the
3232- most recent release of PostgreSQL.
3333- </para>
3434- <para>
3535- By default, PostgreSQL stores its databases in
3636- <filename>/var/lib/postgresql/$psqlSchema</filename>. You can
3737- override this using
3838- <xref linkend="opt-services.postgresql.dataDir" />, e.g.
3939- </para>
4040- <programlisting>
4141-services.postgresql.dataDir = "/data/postgresql";
4242-</programlisting>
4343- </section>
4444- <section xml:id="module-services-postgres-upgrading">
4545- <title>Upgrading</title>
4646- <note>
4747- <para>
4848- The steps below demonstrate how to upgrade from an older version
4949- to <literal>pkgs.postgresql_13</literal>. These instructions are
5050- also applicable to other versions.
5151- </para>
5252- </note>
5353- <para>
5454- Major PostgreSQL upgrades require a downtime and a few imperative
5555- steps to be called. This is the case because each major version
5656- has some internal changes in the databases’ state during major
5757- releases. Because of that, NixOS places the state into
5858- <filename>/var/lib/postgresql/<version></filename> where
5959- each <literal>version</literal> can be obtained like this:
6060- </para>
6161- <programlisting>
6262-$ nix-instantiate --eval -A postgresql_13.psqlSchema
6363-"13"
6464-</programlisting>
6565- <para>
6666- For an upgrade, a script like this can be used to simplify the
6767- process:
6868- </para>
6969- <programlisting>
7070-{ config, pkgs, ... }:
7171-{
7272- environment.systemPackages = [
7373- (let
7474- # XXX specify the postgresql package you'd like to upgrade to.
7575- # Do not forget to list the extensions you need.
7676- newPostgres = pkgs.postgresql_13.withPackages (pp: [
7777- # pp.plv8
7878- ]);
7979- in pkgs.writeScriptBin "upgrade-pg-cluster" ''
8080- set -eux
8181- # XXX it's perhaps advisable to stop all services that depend on postgresql
8282- systemctl stop postgresql
8383-8484- export NEWDATA="/var/lib/postgresql/${newPostgres.psqlSchema}"
8585-8686- export NEWBIN="${newPostgres}/bin"
8787-8888- export OLDDATA="${config.services.postgresql.dataDir}"
8989- export OLDBIN="${config.services.postgresql.package}/bin"
9090-9191- install -d -m 0700 -o postgres -g postgres "$NEWDATA"
9292- cd "$NEWDATA"
9393- sudo -u postgres $NEWBIN/initdb -D "$NEWDATA"
9494-9595- sudo -u postgres $NEWBIN/pg_upgrade \
9696- --old-datadir "$OLDDATA" --new-datadir "$NEWDATA" \
9797- --old-bindir $OLDBIN --new-bindir $NEWBIN \
9898- "$@"
9999- '')
100100- ];
101101-}
102102-</programlisting>
103103- <para>
104104- The upgrade process is:
105105- </para>
106106- <orderedlist numeration="arabic">
107107- <listitem>
108108- <para>
109109- Rebuild nixos configuration with the configuration above added
110110- to your <filename>configuration.nix</filename>. Alternatively,
111111- add that into separate file and reference it in
112112- <literal>imports</literal> list.
113113- </para>
114114- </listitem>
115115- <listitem>
116116- <para>
117117- Login as root (<literal>sudo su -</literal>)
118118- </para>
119119- </listitem>
120120- <listitem>
121121- <para>
122122- Run <literal>upgrade-pg-cluster</literal>. It will stop old
123123- postgresql, initialize a new one and migrate the old one to
124124- the new one. You may supply arguments like
125125- <literal>--jobs 4</literal> and <literal>--link</literal> to
126126- speedup migration process. See
127127- <link xlink:href="https://www.postgresql.org/docs/current/pgupgrade.html">https://www.postgresql.org/docs/current/pgupgrade.html</link>
128128- for details.
129129- </para>
130130- </listitem>
131131- <listitem>
132132- <para>
133133- Change postgresql package in NixOS configuration to the one
134134- you were upgrading to via
135135- <xref linkend="opt-services.postgresql.package" />. Rebuild
136136- NixOS. This should start new postgres using upgraded data
137137- directory and all services you stopped during the upgrade.
138138- </para>
139139- </listitem>
140140- <listitem>
141141- <para>
142142- After the upgrade it’s advisable to analyze the new cluster.
143143- </para>
144144- <itemizedlist>
145145- <listitem>
146146- <para>
147147- For PostgreSQL ≥ 14, use the <literal>vacuumdb</literal>
148148- command printed by the upgrades script.
149149- </para>
150150- </listitem>
151151- <listitem>
152152- <para>
153153- For PostgreSQL < 14, run (as
154154- <literal>su -l postgres</literal> in the
155155- <xref linkend="opt-services.postgresql.dataDir" />, in
156156- this example <filename>/var/lib/postgresql/13</filename>):
157157- </para>
158158- <programlisting>
159159-$ ./analyze_new_cluster.sh
160160-</programlisting>
161161- </listitem>
162162- </itemizedlist>
163163- <warning>
164164- <para>
165165- The next step removes the old state-directory!
166166- </para>
167167- </warning>
168168- <programlisting>
169169-$ ./delete_old_cluster.sh
170170-</programlisting>
171171- </listitem>
172172- </orderedlist>
173173- </section>
174174- <section xml:id="module-services-postgres-options">
175175- <title>Options</title>
176176- <para>
177177- A complete list of options for the PostgreSQL module may be found
178178- <link linkend="opt-services.postgresql.enable">here</link>.
179179- </para>
180180- </section>
181181- <section xml:id="module-services-postgres-plugins">
182182- <title>Plugins</title>
183183- <para>
184184- Plugins collection for each PostgreSQL version can be accessed
185185- with <literal>.pkgs</literal>. For example, for
186186- <literal>pkgs.postgresql_11</literal> package, its plugin
187187- collection is accessed by
188188- <literal>pkgs.postgresql_11.pkgs</literal>:
189189- </para>
190190- <programlisting>
191191-$ nix repl '<nixpkgs>'
192192-193193-Loading '<nixpkgs>'...
194194-Added 10574 variables.
195195-196196-nix-repl> postgresql_11.pkgs.<TAB><TAB>
197197-postgresql_11.pkgs.cstore_fdw postgresql_11.pkgs.pg_repack
198198-postgresql_11.pkgs.pg_auto_failover postgresql_11.pkgs.pg_safeupdate
199199-postgresql_11.pkgs.pg_bigm postgresql_11.pkgs.pg_similarity
200200-postgresql_11.pkgs.pg_cron postgresql_11.pkgs.pg_topn
201201-postgresql_11.pkgs.pg_hll postgresql_11.pkgs.pgjwt
202202-postgresql_11.pkgs.pg_partman postgresql_11.pkgs.pgroonga
203203-...
204204-</programlisting>
205205- <para>
206206- To add plugins via NixOS configuration, set
207207- <literal>services.postgresql.extraPlugins</literal>:
208208- </para>
209209- <programlisting>
210210-services.postgresql.package = pkgs.postgresql_11;
211211-services.postgresql.extraPlugins = with pkgs.postgresql_11.pkgs; [
212212- pg_repack
213213- postgis
214214-];
215215-</programlisting>
216216- <para>
217217- You can build custom PostgreSQL-with-plugins (to be used outside
218218- of NixOS) using function <literal>.withPackages</literal>. For
219219- example, creating a custom PostgreSQL package in an overlay can
220220- look like:
221221- </para>
222222- <programlisting>
223223-self: super: {
224224- postgresql_custom = self.postgresql_11.withPackages (ps: [
225225- ps.pg_repack
226226- ps.postgis
227227- ]);
228228-}
229229-</programlisting>
230230- <para>
231231- Here’s a recipe on how to override a particular plugin through an
232232- overlay:
233233- </para>
234234- <programlisting>
235235-self: super: {
236236- postgresql_11 = super.postgresql_11.override { this = self.postgresql_11; } // {
237237- pkgs = super.postgresql_11.pkgs // {
238238- pg_repack = super.postgresql_11.pkgs.pg_repack.overrideAttrs (_: {
239239- name = "pg_repack-v20181024";
240240- src = self.fetchzip {
241241- url = "https://github.com/reorg/pg_repack/archive/923fa2f3c709a506e111cc963034bf2fd127aa00.tar.gz";
242242- sha256 = "17k6hq9xaax87yz79j773qyigm4fwk8z4zh5cyp6z0sxnwfqxxw5";
243243- };
244244- });
245245- };
246246- };
247247-}
248248-</programlisting>
249249- </section>
250250-</chapter>
···11-<!-- Do not edit this file directly, edit its companion .md instead
22- and regenerate this file using nixos/doc/manual/md-to-db.sh -->
33-<chapter xmlns="http://docbook.org/ns/docbook" xmlns:xlink="http://www.w3.org/1999/xlink" xml:id="module-services-flatpak">
44- <title>Flatpak</title>
55- <para>
66- <emphasis>Source:</emphasis>
77- <filename>modules/services/desktop/flatpak.nix</filename>
88- </para>
99- <para>
1010- <emphasis>Upstream documentation:</emphasis>
1111- <link xlink:href="https://github.com/flatpak/flatpak/wiki">https://github.com/flatpak/flatpak/wiki</link>
1212- </para>
1313- <para>
1414- Flatpak is a system for building, distributing, and running
1515- sandboxed desktop applications on Linux.
1616- </para>
1717- <para>
1818- To enable Flatpak, add the following to your
1919- <filename>configuration.nix</filename>:
2020- </para>
2121- <programlisting>
2222- services.flatpak.enable = true;
2323-</programlisting>
2424- <para>
2525- For the sandboxed apps to work correctly, desktop integration
2626- portals need to be installed. If you run GNOME, this will be handled
2727- automatically for you; in other cases, you will need to add
2828- something like the following to your
2929- <filename>configuration.nix</filename>:
3030- </para>
3131- <programlisting>
3232- xdg.portal.extraPortals = [ pkgs.xdg-desktop-portal-gtk ];
3333-</programlisting>
3434- <para>
3535- Then, you will need to add a repository, for example,
3636- <link xlink:href="https://github.com/flatpak/flatpak/wiki">Flathub</link>,
3737- either using the following commands:
3838- </para>
3939- <programlisting>
4040-$ flatpak remote-add --if-not-exists flathub https://flathub.org/repo/flathub.flatpakrepo
4141-$ flatpak update
4242-</programlisting>
4343- <para>
4444- or by opening the
4545- <link xlink:href="https://flathub.org/repo/flathub.flatpakrepo">repository
4646- file</link> in GNOME Software.
4747- </para>
4848- <para>
4949- Finally, you can search and install programs:
5050- </para>
5151- <programlisting>
5252-$ flatpak search bustle
5353-$ flatpak install flathub org.freedesktop.Bustle
5454-$ flatpak run org.freedesktop.Bustle
5555-</programlisting>
5656- <para>
5757- Again, GNOME Software offers graphical interface for these tasks.
5858- </para>
5959-</chapter>
···11-<!-- Do not edit this file directly, edit its companion .md instead
22- and regenerate this file using nixos/doc/manual/md-to-db.sh -->
33-<chapter xmlns="http://docbook.org/ns/docbook" xmlns:xlink="http://www.w3.org/1999/xlink" xml:id="module-services-blackfire">
44- <title>Blackfire profiler</title>
55- <para>
66- <emphasis>Source:</emphasis>
77- <filename>modules/services/development/blackfire.nix</filename>
88- </para>
99- <para>
1010- <emphasis>Upstream documentation:</emphasis>
1111- <link xlink:href="https://blackfire.io/docs/introduction">https://blackfire.io/docs/introduction</link>
1212- </para>
1313- <para>
1414- <link xlink:href="https://blackfire.io">Blackfire</link> is a
1515- proprietary tool for profiling applications. There are several
1616- languages supported by the product but currently only PHP support is
1717- packaged in Nixpkgs. The back-end consists of a module that is
1818- loaded into the language runtime (called <emphasis>probe</emphasis>)
1919- and a service (<emphasis>agent</emphasis>) that the probe connects
2020- to and that sends the profiles to the server.
2121- </para>
2222- <para>
2323- To use it, you will need to enable the agent and the probe on your
2424- server. The exact method will depend on the way you use PHP but here
2525- is an example of NixOS configuration for PHP-FPM:
2626- </para>
2727- <programlisting>
2828-let
2929- php = pkgs.php.withExtensions ({ enabled, all }: enabled ++ (with all; [
3030- blackfire
3131- ]));
3232-in {
3333- # Enable the probe extension for PHP-FPM.
3434- services.phpfpm = {
3535- phpPackage = php;
3636- };
3737-3838- # Enable and configure the agent.
3939- services.blackfire-agent = {
4040- enable = true;
4141- settings = {
4242- # You will need to get credentials at https://blackfire.io/my/settings/credentials
4343- # You can also use other options described in https://blackfire.io/docs/up-and-running/configuration/agent
4444- server-id = "XXXXXXXX-XXXX-XXXX-XXXX-XXXXXXXXXXXX";
4545- server-token = "XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX";
4646- };
4747- };
4848-4949- # Make the agent run on start-up.
5050- # (WantedBy= from the upstream unit not respected: https://github.com/NixOS/nixpkgs/issues/81138)
5151- # Alternately, you can start it manually with `systemctl start blackfire-agent`.
5252- systemd.services.blackfire-agent.wantedBy = [ "phpfpm-foo.service" ];
5353-}
5454-</programlisting>
5555- <para>
5656- On your developer machine, you will also want to install
5757- <link xlink:href="https://blackfire.io/docs/up-and-running/installation#install-a-profiling-client">the
5858- client</link> (see <literal>blackfire</literal> package) or the
5959- browser extension to actually trigger the profiling.
6060- </para>
6161-</chapter>
···11-<!-- Do not edit this file directly, edit its companion .md instead
22- and regenerate this file using nixos/doc/manual/md-to-db.sh -->
33-<chapter xmlns="http://docbook.org/ns/docbook" xmlns:xlink="http://www.w3.org/1999/xlink" xml:id="module-services-emacs">
44- <title>Emacs</title>
55- <para>
66- <link xlink:href="https://www.gnu.org/software/emacs/">Emacs</link>
77- is an extensible, customizable, self-documenting real-time display
88- editor — and more. At its core is an interpreter for Emacs Lisp, a
99- dialect of the Lisp programming language with extensions to support
1010- text editing.
1111- </para>
1212- <para>
1313- Emacs runs within a graphical desktop environment using the X Window
1414- System, but works equally well on a text terminal. Under macOS, a
1515- <quote>Mac port</quote> edition is available, which uses Apple’s
1616- native GUI frameworks.
1717- </para>
1818- <para>
1919- Nixpkgs provides a superior environment for running Emacs. It’s
2020- simple to create custom builds by overriding the default packages.
2121- Chaotic collections of Emacs Lisp code and extensions can be brought
2222- under control using declarative package management. NixOS even
2323- provides a <command>systemd</command> user service for automatically
2424- starting the Emacs daemon.
2525- </para>
2626- <section xml:id="module-services-emacs-installing">
2727- <title>Installing Emacs</title>
2828- <para>
2929- Emacs can be installed in the normal way for Nix (see
3030- <xref linkend="sec-package-management" />). In addition, a NixOS
3131- <emphasis>service</emphasis> can be enabled.
3232- </para>
3333- <section xml:id="module-services-emacs-releases">
3434- <title>The Different Releases of Emacs</title>
3535- <para>
3636- Nixpkgs defines several basic Emacs packages. The following are
3737- attributes belonging to the <varname>pkgs</varname> set:
3838- </para>
3939- <variablelist spacing="compact">
4040- <varlistentry>
4141- <term>
4242- <varname>emacs</varname>
4343- </term>
4444- <listitem>
4545- <para>
4646- The latest stable version of Emacs using the
4747- <link xlink:href="http://www.gtk.org">GTK 2</link> widget
4848- toolkit.
4949- </para>
5050- </listitem>
5151- </varlistentry>
5252- <varlistentry>
5353- <term>
5454- <varname>emacs-nox</varname>
5555- </term>
5656- <listitem>
5757- <para>
5858- Emacs built without any dependency on X11 libraries.
5959- </para>
6060- </listitem>
6161- </varlistentry>
6262- <varlistentry>
6363- <term>
6464- <varname>emacsMacport</varname>
6565- </term>
6666- <listitem>
6767- <para>
6868- Emacs with the <quote>Mac port</quote> patches, providing
6969- a more native look and feel under macOS.
7070- </para>
7171- </listitem>
7272- </varlistentry>
7373- </variablelist>
7474- <para>
7575- If those aren’t suitable, then the following imitation Emacs
7676- editors are also available in Nixpkgs:
7777- <link xlink:href="https://www.gnu.org/software/zile/">Zile</link>,
7878- <link xlink:href="http://homepage.boetes.org/software/mg/">mg</link>,
7979- <link xlink:href="http://yi-editor.github.io/">Yi</link>,
8080- <link xlink:href="https://joe-editor.sourceforge.io/">jmacs</link>.
8181- </para>
8282- </section>
8383- <section xml:id="module-services-emacs-adding-packages">
8484- <title>Adding Packages to Emacs</title>
8585- <para>
8686- Emacs includes an entire ecosystem of functionality beyond text
8787- editing, including a project planner, mail and news reader,
8888- debugger interface, calendar, and more.
8989- </para>
9090- <para>
9191- Most extensions are gotten with the Emacs packaging system
9292- (<filename>package.el</filename>) from
9393- <link xlink:href="https://elpa.gnu.org/">Emacs Lisp Package
9494- Archive (ELPA)</link>,
9595- <link xlink:href="https://melpa.org/">MELPA</link>,
9696- <link xlink:href="https://stable.melpa.org/">MELPA
9797- Stable</link>, and
9898- <link xlink:href="http://orgmode.org/elpa.html">Org ELPA</link>.
9999- Nixpkgs is regularly updated to mirror all these archives.
100100- </para>
101101- <para>
102102- Under NixOS, you can continue to use
103103- <literal>package-list-packages</literal> and
104104- <literal>package-install</literal> to install packages. You can
105105- also declare the set of Emacs packages you need using the
106106- derivations from Nixpkgs. The rest of this section discusses
107107- declarative installation of Emacs packages through nixpkgs.
108108- </para>
109109- <para>
110110- The first step to declare the list of packages you want in your
111111- Emacs installation is to create a dedicated derivation. This can
112112- be done in a dedicated <filename>emacs.nix</filename> file such
113113- as:
114114- </para>
115115- <para>
116116- <anchor xml:id="ex-emacsNix" />
117117- </para>
118118- <programlisting language="nix">
119119-/*
120120-This is a nix expression to build Emacs and some Emacs packages I like
121121-from source on any distribution where Nix is installed. This will install
122122-all the dependencies from the nixpkgs repository and build the binary files
123123-without interfering with the host distribution.
124124-125125-To build the project, type the following from the current directory:
126126-127127-$ nix-build emacs.nix
128128-129129-To run the newly compiled executable:
130130-131131-$ ./result/bin/emacs
132132-*/
133133-134134-# The first non-comment line in this file indicates that
135135-# the whole file represents a function.
136136-{ pkgs ? import <nixpkgs> {} }:
137137-138138-let
139139- # The let expression below defines a myEmacs binding pointing to the
140140- # current stable version of Emacs. This binding is here to separate
141141- # the choice of the Emacs binary from the specification of the
142142- # required packages.
143143- myEmacs = pkgs.emacs;
144144- # This generates an emacsWithPackages function. It takes a single
145145- # argument: a function from a package set to a list of packages
146146- # (the packages that will be available in Emacs).
147147- emacsWithPackages = (pkgs.emacsPackagesFor myEmacs).emacsWithPackages;
148148-in
149149- # The rest of the file specifies the list of packages to install. In the
150150- # example, two packages (magit and zerodark-theme) are taken from
151151- # MELPA stable.
152152- emacsWithPackages (epkgs: (with epkgs.melpaStablePackages; [
153153- magit # ; Integrate git <C-x g>
154154- zerodark-theme # ; Nicolas' theme
155155- ])
156156- # Two packages (undo-tree and zoom-frm) are taken from MELPA.
157157- ++ (with epkgs.melpaPackages; [
158158- undo-tree # ; <C-x u> to show the undo tree
159159- zoom-frm # ; increase/decrease font size for all buffers %lt;C-x C-+>
160160- ])
161161- # Three packages are taken from GNU ELPA.
162162- ++ (with epkgs.elpaPackages; [
163163- auctex # ; LaTeX mode
164164- beacon # ; highlight my cursor when scrolling
165165- nameless # ; hide current package name everywhere in elisp code
166166- ])
167167- # notmuch is taken from a nixpkgs derivation which contains an Emacs mode.
168168- ++ [
169169- pkgs.notmuch # From main packages set
170170- ])
171171-</programlisting>
172172- <para>
173173- The result of this configuration will be an
174174- <command>emacs</command> command which launches Emacs with all
175175- of your chosen packages in the <varname>load-path</varname>.
176176- </para>
177177- <para>
178178- You can check that it works by executing this in a terminal:
179179- </para>
180180- <programlisting>
181181-$ nix-build emacs.nix
182182-$ ./result/bin/emacs -q
183183-</programlisting>
184184- <para>
185185- and then typing <literal>M-x package-initialize</literal>. Check
186186- that you can use all the packages you want in this Emacs
187187- instance. For example, try switching to the zerodark theme
188188- through
189189- <literal>M-x load-theme <RET> zerodark <RET> y</literal>.
190190- </para>
191191- <tip>
192192- <para>
193193- A few popular extensions worth checking out are: auctex,
194194- company, edit-server, flycheck, helm, iedit, magit,
195195- multiple-cursors, projectile, and yasnippet.
196196- </para>
197197- </tip>
198198- <para>
199199- The list of available packages in the various ELPA repositories
200200- can be seen with the following commands:
201201- <anchor xml:id="module-services-emacs-querying-packages" />
202202- </para>
203203- <programlisting>
204204-nix-env -f "<nixpkgs>" -qaP -A emacs.pkgs.elpaPackages
205205-nix-env -f "<nixpkgs>" -qaP -A emacs.pkgs.melpaPackages
206206-nix-env -f "<nixpkgs>" -qaP -A emacs.pkgs.melpaStablePackages
207207-nix-env -f "<nixpkgs>" -qaP -A emacs.pkgs.orgPackages
208208-</programlisting>
209209- <para>
210210- If you are on NixOS, you can install this particular Emacs for
211211- all users by adding it to the list of system packages (see
212212- <xref linkend="sec-declarative-package-mgmt" />). Simply modify
213213- your file <filename>configuration.nix</filename> to make it
214214- contain:
215215- <anchor xml:id="module-services-emacs-configuration-nix" />
216216- </para>
217217- <programlisting>
218218-{
219219- environment.systemPackages = [
220220- # [...]
221221- (import /path/to/emacs.nix { inherit pkgs; })
222222- ];
223223-}
224224-</programlisting>
225225- <para>
226226- In this case, the next <command>nixos-rebuild switch</command>
227227- will take care of adding your <command>emacs</command> to the
228228- <varname>PATH</varname> environment variable (see
229229- <xref linkend="sec-changing-config" />).
230230- </para>
231231- <para>
232232- If you are not on NixOS or want to install this particular Emacs
233233- only for yourself, you can do so by adding it to your
234234- <filename>~/.config/nixpkgs/config.nix</filename> (see
235235- <link xlink:href="https://nixos.org/nixpkgs/manual/#sec-modify-via-packageOverrides">Nixpkgs
236236- manual</link>):
237237- <anchor xml:id="module-services-emacs-config-nix" />
238238- </para>
239239- <programlisting>
240240-{
241241- packageOverrides = super: let self = super.pkgs; in {
242242- myemacs = import /path/to/emacs.nix { pkgs = self; };
243243- };
244244-}
245245-</programlisting>
246246- <para>
247247- In this case, the next
248248- <literal>nix-env -f '<nixpkgs>' -iA myemacs</literal> will
249249- take care of adding your emacs to the <varname>PATH</varname>
250250- environment variable.
251251- </para>
252252- </section>
253253- <section xml:id="module-services-emacs-advanced">
254254- <title>Advanced Emacs Configuration</title>
255255- <para>
256256- If you want, you can tweak the Emacs package itself from your
257257- <filename>emacs.nix</filename>. For example, if you want to have
258258- a GTK 3-based Emacs instead of the default GTK 2-based binary
259259- and remove the automatically generated
260260- <filename>emacs.desktop</filename> (useful if you only use
261261- <command>emacsclient</command>), you can change your file
262262- <filename>emacs.nix</filename> in this way:
263263- </para>
264264- <para>
265265- <anchor xml:id="ex-emacsGtk3Nix" />
266266- </para>
267267- <programlisting>
268268-{ pkgs ? import <nixpkgs> {} }:
269269-let
270270- myEmacs = (pkgs.emacs.override {
271271- # Use gtk3 instead of the default gtk2
272272- withGTK3 = true;
273273- withGTK2 = false;
274274- }).overrideAttrs (attrs: {
275275- # I don't want emacs.desktop file because I only use
276276- # emacsclient.
277277- postInstall = (attrs.postInstall or "") + ''
278278- rm $out/share/applications/emacs.desktop
279279- '';
280280- });
281281-in [...]
282282-</programlisting>
283283- <para>
284284- After building this file as shown in
285285- <link linkend="ex-emacsNix">the example above</link>, you will
286286- get an GTK 3-based Emacs binary pre-loaded with your favorite
287287- packages.
288288- </para>
289289- </section>
290290- </section>
291291- <section xml:id="module-services-emacs-running">
292292- <title>Running Emacs as a Service</title>
293293- <para>
294294- NixOS provides an optional <command>systemd</command> service
295295- which launches
296296- <link xlink:href="https://www.gnu.org/software/emacs/manual/html_node/emacs/Emacs-Server.html">Emacs
297297- daemon</link> with the user’s login session.
298298- </para>
299299- <para>
300300- <emphasis>Source:</emphasis>
301301- <filename>modules/services/editors/emacs.nix</filename>
302302- </para>
303303- <section xml:id="module-services-emacs-enabling">
304304- <title>Enabling the Service</title>
305305- <para>
306306- To install and enable the <command>systemd</command> user
307307- service for Emacs daemon, add the following to your
308308- <filename>configuration.nix</filename>:
309309- </para>
310310- <programlisting>
311311-services.emacs.enable = true;
312312-services.emacs.package = import /home/cassou/.emacs.d { pkgs = pkgs; };
313313-</programlisting>
314314- <para>
315315- The <varname>services.emacs.package</varname> option allows a
316316- custom derivation to be used, for example, one created by
317317- <literal>emacsWithPackages</literal>.
318318- </para>
319319- <para>
320320- Ensure that the Emacs server is enabled for your user’s Emacs
321321- configuration, either by customizing the
322322- <varname>server-mode</varname> variable, or by adding
323323- <literal>(server-start)</literal> to
324324- <filename>~/.emacs.d/init.el</filename>.
325325- </para>
326326- <para>
327327- To start the daemon, execute the following:
328328- </para>
329329- <programlisting>
330330-$ nixos-rebuild switch # to activate the new configuration.nix
331331-$ systemctl --user daemon-reload # to force systemd reload
332332-$ systemctl --user start emacs.service # to start the Emacs daemon
333333-</programlisting>
334334- <para>
335335- The server should now be ready to serve Emacs clients.
336336- </para>
337337- </section>
338338- <section xml:id="module-services-emacs-starting-client">
339339- <title>Starting the client</title>
340340- <para>
341341- Ensure that the emacs server is enabled, either by customizing
342342- the <varname>server-mode</varname> variable, or by adding
343343- <literal>(server-start)</literal> to
344344- <filename>~/.emacs</filename>.
345345- </para>
346346- <para>
347347- To connect to the emacs daemon, run one of the following:
348348- </para>
349349- <programlisting>
350350-emacsclient FILENAME
351351-emacsclient --create-frame # opens a new frame (window)
352352-emacsclient --create-frame --tty # opens a new frame on the current terminal
353353-</programlisting>
354354- </section>
355355- <section xml:id="module-services-emacs-editor-variable">
356356- <title>Configuring the <varname>EDITOR</varname> variable</title>
357357- <para>
358358- If <xref linkend="opt-services.emacs.defaultEditor" /> is
359359- <literal>true</literal>, the <varname>EDITOR</varname> variable
360360- will be set to a wrapper script which launches
361361- <command>emacsclient</command>.
362362- </para>
363363- <para>
364364- Any setting of <varname>EDITOR</varname> in the shell config
365365- files will override
366366- <varname>services.emacs.defaultEditor</varname>. To make sure
367367- <varname>EDITOR</varname> refers to the Emacs wrapper script,
368368- remove any existing <varname>EDITOR</varname> assignment from
369369- <filename>.profile</filename>, <filename>.bashrc</filename>,
370370- <filename>.zshenv</filename> or any other shell config file.
371371- </para>
372372- <para>
373373- If you have formed certain bad habits when editing files, these
374374- can be corrected with a shell alias to the wrapper script:
375375- </para>
376376- <programlisting>
377377-alias vi=$EDITOR
378378-</programlisting>
379379- </section>
380380- <section xml:id="module-services-emacs-per-user">
381381- <title>Per-User Enabling of the Service</title>
382382- <para>
383383- In general, <command>systemd</command> user services are
384384- globally enabled by symlinks in
385385- <filename>/etc/systemd/user</filename>. In the case where Emacs
386386- daemon is not wanted for all users, it is possible to install
387387- the service but not globally enable it:
388388- </para>
389389- <programlisting>
390390-services.emacs.enable = false;
391391-services.emacs.install = true;
392392-</programlisting>
393393- <para>
394394- To enable the <command>systemd</command> user service for just
395395- the currently logged in user, run:
396396- </para>
397397- <programlisting>
398398-systemctl --user enable emacs
399399-</programlisting>
400400- <para>
401401- This will add the symlink
402402- <filename>~/.config/systemd/user/emacs.service</filename>.
403403- </para>
404404- </section>
405405- </section>
406406- <section xml:id="module-services-emacs-configuring">
407407- <title>Configuring Emacs</title>
408408- <para>
409409- The Emacs init file should be changed to load the extension
410410- packages at startup:
411411- <anchor xml:id="module-services-emacs-package-initialisation" />
412412- </para>
413413- <programlisting>
414414-(require 'package)
415415-416416-;; optional. makes unpure packages archives unavailable
417417-(setq package-archives nil)
418418-419419-(setq package-enable-at-startup nil)
420420-(package-initialize)
421421-</programlisting>
422422- <para>
423423- After the declarative emacs package configuration has been tested,
424424- previously downloaded packages can be cleaned up by removing
425425- <filename>~/.emacs.d/elpa</filename> (do make a backup first, in
426426- case you forgot a package).
427427- </para>
428428- <section xml:id="module-services-emacs-major-mode">
429429- <title>A Major Mode for Nix Expressions</title>
430430- <para>
431431- Of interest may be <varname>melpaPackages.nix-mode</varname>,
432432- which provides syntax highlighting for the Nix language. This is
433433- particularly convenient if you regularly edit Nix files.
434434- </para>
435435- </section>
436436- <section xml:id="module-services-emacs-man-pages">
437437- <title>Accessing man pages</title>
438438- <para>
439439- You can use <literal>woman</literal> to get completion of all
440440- available man pages. For example, type
441441- <literal>M-x woman <RET> nixos-rebuild <RET>.</literal>
442442- </para>
443443- </section>
444444- <section xml:id="sec-emacs-docbook-xml">
445445- <title>Editing DocBook 5 XML Documents</title>
446446- <para>
447447- Emacs includes
448448- <link xlink:href="https://www.gnu.org/software/emacs/manual/html_node/nxml-mode/Introduction.html">nXML</link>,
449449- a major-mode for validating and editing XML documents. When
450450- editing DocBook 5.0 documents, such as
451451- <link linkend="book-nixos-manual">this one</link>, nXML needs to
452452- be configured with the relevant schema, which is not included.
453453- </para>
454454- <para>
455455- To install the DocBook 5.0 schemas, either add
456456- <varname>pkgs.docbook5</varname> to
457457- <xref linkend="opt-environment.systemPackages" />
458458- (<link linkend="sec-declarative-package-mgmt">NixOS</link>), or
459459- run <literal>nix-env -f '<nixpkgs>' -iA docbook5</literal>
460460- (<link linkend="sec-ad-hoc-packages">Nix</link>).
461461- </para>
462462- <para>
463463- Then customize the variable
464464- <varname>rng-schema-locating-files</varname> to include
465465- <filename>~/.emacs.d/schemas.xml</filename> and put the
466466- following text into that file:
467467- <anchor xml:id="ex-emacs-docbook-xml" />
468468- </para>
469469- <programlisting language="xml">
470470-<?xml version="1.0"?>
471471-<!--
472472- To let emacs find this file, evaluate:
473473- (add-to-list 'rng-schema-locating-files "~/.emacs.d/schemas.xml")
474474--->
475475-<locatingRules xmlns="http://thaiopensource.com/ns/locating-rules/1.0">
476476- <!--
477477- Use this variation if pkgs.docbook5 is added to environment.systemPackages
478478- -->
479479- <namespace ns="http://docbook.org/ns/docbook"
480480- uri="/run/current-system/sw/share/xml/docbook-5.0/rng/docbookxi.rnc"/>
481481- <!--
482482- Use this variation if installing schema with "nix-env -iA pkgs.docbook5".
483483- <namespace ns="http://docbook.org/ns/docbook"
484484- uri="../.nix-profile/share/xml/docbook-5.0/rng/docbookxi.rnc"/>
485485- -->
486486-</locatingRules>
487487-</programlisting>
488488- </section>
489489- </section>
490490-</chapter>
···11-<!-- Do not edit this file directly, edit its companion .md instead
22- and regenerate this file using nixos/doc/manual/md-to-db.sh -->
33-<chapter xmlns="http://docbook.org/ns/docbook" xmlns:xlink="http://www.w3.org/1999/xlink" xml:id="trezor">
44- <title>Trezor</title>
55- <para>
66- Trezor is an open-source cryptocurrency hardware wallet and security
77- token allowing secure storage of private keys.
88- </para>
99- <para>
1010- It offers advanced features such U2F two-factor authorization, SSH
1111- login through
1212- <link xlink:href="https://wiki.trezor.io/Apps:SSH_agent">Trezor SSH
1313- agent</link>,
1414- <link xlink:href="https://wiki.trezor.io/GPG">GPG</link> and a
1515- <link xlink:href="https://wiki.trezor.io/Trezor_Password_Manager">password
1616- manager</link>. For more information, guides and documentation, see
1717- <link xlink:href="https://wiki.trezor.io">https://wiki.trezor.io</link>.
1818- </para>
1919- <para>
2020- To enable Trezor support, add the following to your
2121- <filename>configuration.nix</filename>:
2222- </para>
2323- <programlisting>
2424-services.trezord.enable = true;
2525-</programlisting>
2626- <para>
2727- This will add all necessary udev rules and start Trezor Bridge.
2828- </para>
2929-</chapter>
···11-<!-- Do not edit this file directly, edit its companion .md instead
22- and regenerate this file using nixos/doc/manual/md-to-db.sh -->
33-<chapter xmlns="http://docbook.org/ns/docbook" xmlns:xlink="http://www.w3.org/1999/xlink" xml:id="module-services-mailman">
44- <title>Mailman</title>
55- <para>
66- <link xlink:href="https://www.list.org">Mailman</link> is free
77- software for managing electronic mail discussion and e-newsletter
88- lists. Mailman and its web interface can be configured using the
99- corresponding NixOS module. Note that this service is best used with
1010- an existing, securely configured Postfix setup, as it does not
1111- automatically configure this.
1212- </para>
1313- <section xml:id="module-services-mailman-basic-usage">
1414- <title>Basic usage with Postfix</title>
1515- <para>
1616- For a basic configuration with Postfix as the MTA, the following
1717- settings are suggested:
1818- </para>
1919- <programlisting>
2020-{ config, ... }: {
2121- services.postfix = {
2222- enable = true;
2323- relayDomains = ["hash:/var/lib/mailman/data/postfix_domains"];
2424- sslCert = config.security.acme.certs."lists.example.org".directory + "/full.pem";
2525- sslKey = config.security.acme.certs."lists.example.org".directory + "/key.pem";
2626- config = {
2727- transport_maps = ["hash:/var/lib/mailman/data/postfix_lmtp"];
2828- local_recipient_maps = ["hash:/var/lib/mailman/data/postfix_lmtp"];
2929- };
3030- };
3131- services.mailman = {
3232- enable = true;
3333- serve.enable = true;
3434- hyperkitty.enable = true;
3535- webHosts = ["lists.example.org"];
3636- siteOwner = "mailman@example.org";
3737- };
3838- services.nginx.virtualHosts."lists.example.org".enableACME = true;
3939- networking.firewall.allowedTCPPorts = [ 25 80 443 ];
4040-}
4141-</programlisting>
4242- <para>
4343- DNS records will also be required:
4444- </para>
4545- <itemizedlist spacing="compact">
4646- <listitem>
4747- <para>
4848- <literal>AAAA</literal> and <literal>A</literal> records
4949- pointing to the host in question, in order for browsers to be
5050- able to discover the address of the web server;
5151- </para>
5252- </listitem>
5353- <listitem>
5454- <para>
5555- An <literal>MX</literal> record pointing to a domain name at
5656- which the host is reachable, in order for other mail servers
5757- to be able to deliver emails to the mailing lists it hosts.
5858- </para>
5959- </listitem>
6060- </itemizedlist>
6161- <para>
6262- After this has been done and appropriate DNS records have been set
6363- up, the Postorius mailing list manager and the Hyperkitty archive
6464- browser will be available at https://lists.example.org/. Note that
6565- this setup is not sufficient to deliver emails to most email
6666- providers nor to avoid spam – a number of additional measures for
6767- authenticating incoming and outgoing mails, such as SPF, DMARC and
6868- DKIM are necessary, but outside the scope of the Mailman module.
6969- </para>
7070- </section>
7171- <section xml:id="module-services-mailman-other-mtas">
7272- <title>Using with other MTAs</title>
7373- <para>
7474- Mailman also supports other MTA, though with a little bit more
7575- configuration. For example, to use Mailman with Exim, you can use
7676- the following settings:
7777- </para>
7878- <programlisting>
7979-{ config, ... }: {
8080- services = {
8181- mailman = {
8282- enable = true;
8383- siteOwner = "mailman@example.org";
8484- enablePostfix = false;
8585- settings.mta = {
8686- incoming = "mailman.mta.exim4.LMTP";
8787- outgoing = "mailman.mta.deliver.deliver";
8888- lmtp_host = "localhost";
8989- lmtp_port = "8024";
9090- smtp_host = "localhost";
9191- smtp_port = "25";
9292- configuration = "python:mailman.config.exim4";
9393- };
9494- };
9595- exim = {
9696- enable = true;
9797- # You can configure Exim in a separate file to reduce configuration.nix clutter
9898- config = builtins.readFile ./exim.conf;
9999- };
100100- };
101101-}
102102-</programlisting>
103103- <para>
104104- The exim config needs some special additions to work with Mailman.
105105- Currently NixOS can’t manage Exim config with such granularity.
106106- Please refer to
107107- <link xlink:href="https://mailman.readthedocs.io/en/latest/src/mailman/docs/mta.html">Mailman
108108- documentation</link> for more info on configuring Mailman for
109109- working with Exim.
110110- </para>
111111- </section>
112112-</chapter>
···11-<!-- Do not edit this file directly, edit its companion .md instead
22- and regenerate this file using nixos/doc/manual/md-to-db.sh -->
33-<chapter xmlns="http://docbook.org/ns/docbook" xmlns:xlink="http://www.w3.org/1999/xlink" xml:id="module-services-mjolnir">
44- <title>Mjolnir (Matrix Moderation Tool)</title>
55- <para>
66- This chapter will show you how to set up your own, self-hosted
77- <link xlink:href="https://github.com/matrix-org/mjolnir">Mjolnir</link>
88- instance.
99- </para>
1010- <para>
1111- As an all-in-one moderation tool, it can protect your server from
1212- malicious invites, spam messages, and whatever else you don’t want.
1313- In addition to server-level protection, Mjolnir is great for
1414- communities wanting to protect their rooms without having to use
1515- their personal accounts for moderation.
1616- </para>
1717- <para>
1818- The bot by default includes support for bans, redactions, anti-spam,
1919- server ACLs, room directory changes, room alias transfers, account
2020- deactivation, room shutdown, and more.
2121- </para>
2222- <para>
2323- See the
2424- <link xlink:href="https://github.com/matrix-org/mjolnir#readme">README</link>
2525- page and the
2626- <link xlink:href="https://github.com/matrix-org/mjolnir/blob/main/docs/moderators.md">Moderator’s
2727- guide</link> for additional instructions on how to setup and use
2828- Mjolnir.
2929- </para>
3030- <para>
3131- For <link linkend="opt-services.mjolnir.settings">additional
3232- settings</link> see
3333- <link xlink:href="https://github.com/matrix-org/mjolnir/blob/main/config/default.yaml">the
3434- default configuration</link>.
3535- </para>
3636- <section xml:id="module-services-mjolnir-setup">
3737- <title>Mjolnir Setup</title>
3838- <para>
3939- First create a new Room which will be used as a management room
4040- for Mjolnir. In this room, Mjolnir will log possible errors and
4141- debugging information. You’ll need to set this Room-ID in
4242- <link linkend="opt-services.mjolnir.managementRoom">services.mjolnir.managementRoom</link>.
4343- </para>
4444- <para>
4545- Next, create a new user for Mjolnir on your homeserver, if not
4646- present already.
4747- </para>
4848- <para>
4949- The Mjolnir Matrix user expects to be free of any rate limiting.
5050- See
5151- <link xlink:href="https://github.com/matrix-org/synapse/issues/6286">Synapse
5252- #6286</link> for an example on how to achieve this.
5353- </para>
5454- <para>
5555- If you want Mjolnir to be able to deactivate users, move room
5656- aliases, shutdown rooms, etc. you’ll need to make the Mjolnir user
5757- a Matrix server admin.
5858- </para>
5959- <para>
6060- Now invite the Mjolnir user to the management room.
6161- </para>
6262- <para>
6363- It is recommended to use
6464- <link xlink:href="https://github.com/matrix-org/pantalaimon">Pantalaimon</link>,
6565- so your management room can be encrypted. This also applies if you
6666- are looking to moderate an encrypted room.
6767- </para>
6868- <para>
6969- To enable the Pantalaimon E2E Proxy for mjolnir, enable
7070- <link linkend="opt-services.mjolnir.pantalaimon.enable">services.mjolnir.pantalaimon</link>.
7171- This will autoconfigure a new Pantalaimon instance, which will
7272- connect to the homeserver set in
7373- <link linkend="opt-services.mjolnir.homeserverUrl">services.mjolnir.homeserverUrl</link>
7474- and Mjolnir itself will be configured to connect to the new
7575- Pantalaimon instance.
7676- </para>
7777- <programlisting>
7878-{
7979- services.mjolnir = {
8080- enable = true;
8181- homeserverUrl = "https://matrix.domain.tld";
8282- pantalaimon = {
8383- enable = true;
8484- username = "mjolnir";
8585- passwordFile = "/run/secrets/mjolnir-password";
8686- };
8787- protectedRooms = [
8888- "https://matrix.to/#/!xxx:domain.tld"
8989- ];
9090- managementRoom = "!yyy:domain.tld";
9191- };
9292-}
9393-</programlisting>
9494- <section xml:id="module-services-mjolnir-setup-ems">
9595- <title>Element Matrix Services (EMS)</title>
9696- <para>
9797- If you are using a managed
9898- <link xlink:href="https://ems.element.io/"><quote>Element Matrix
9999- Services (EMS)</quote></link> server, you will need to consent
100100- to the terms and conditions. Upon startup, an error log entry
101101- with a URL to the consent page will be generated.
102102- </para>
103103- </section>
104104- </section>
105105- <section xml:id="module-services-mjolnir-matrix-synapse-antispam">
106106- <title>Synapse Antispam Module</title>
107107- <para>
108108- A Synapse module is also available to apply the same rulesets the
109109- bot uses across an entire homeserver.
110110- </para>
111111- <para>
112112- To use the Antispam Module, add
113113- <literal>matrix-synapse-plugins.matrix-synapse-mjolnir-antispam</literal>
114114- to the Synapse plugin list and enable the
115115- <literal>mjolnir.Module</literal> module.
116116- </para>
117117- <programlisting>
118118-{
119119- services.matrix-synapse = {
120120- plugins = with pkgs; [
121121- matrix-synapse-plugins.matrix-synapse-mjolnir-antispam
122122- ];
123123- extraConfig = ''
124124- modules:
125125- - module: mjolnir.Module
126126- config:
127127- # Prevent servers/users in the ban lists from inviting users on this
128128- # server to rooms. Default true.
129129- block_invites: true
130130- # Flag messages sent by servers/users in the ban lists as spam. Currently
131131- # this means that spammy messages will appear as empty to users. Default
132132- # false.
133133- block_messages: false
134134- # Remove users from the user directory search by filtering matrix IDs and
135135- # display names by the entries in the user ban list. Default false.
136136- block_usernames: false
137137- # The room IDs of the ban lists to honour. Unlike other parts of Mjolnir,
138138- # this list cannot be room aliases or permalinks. This server is expected
139139- # to already be joined to the room - Mjolnir will not automatically join
140140- # these rooms.
141141- ban_lists:
142142- - "!roomid:example.org"
143143- '';
144144- };
145145-}
146146-</programlisting>
147147- </section>
148148-</chapter>
···11-<!-- Do not edit this file directly, edit its companion .md instead
22- and regenerate this file using nixos/doc/manual/md-to-db.sh -->
33-<chapter xmlns="http://docbook.org/ns/docbook" xmlns:xlink="http://www.w3.org/1999/xlink" xml:id="module-services-matrix">
44- <title>Matrix</title>
55- <para>
66- <link xlink:href="https://matrix.org/">Matrix</link> is an open
77- standard for interoperable, decentralised, real-time communication
88- over IP. It can be used to power Instant Messaging, VoIP/WebRTC
99- signalling, Internet of Things communication - or anywhere you need
1010- a standard HTTP API for publishing and subscribing to data whilst
1111- tracking the conversation history.
1212- </para>
1313- <para>
1414- This chapter will show you how to set up your own, self-hosted
1515- Matrix homeserver using the Synapse reference homeserver, and how to
1616- serve your own copy of the Element web client. See the
1717- <link xlink:href="https://matrix.org/docs/projects/try-matrix-now.html">Try
1818- Matrix Now!</link> overview page for links to Element Apps for
1919- Android and iOS, desktop clients, as well as bridges to other
2020- networks and other projects around Matrix.
2121- </para>
2222- <section xml:id="module-services-matrix-synapse">
2323- <title>Synapse Homeserver</title>
2424- <para>
2525- <link xlink:href="https://github.com/matrix-org/synapse">Synapse</link>
2626- is the reference homeserver implementation of Matrix from the core
2727- development team at matrix.org. The following configuration
2828- example will set up a synapse server for the
2929- <literal>example.org</literal> domain, served from the host
3030- <literal>myhostname.example.org</literal>. For more information,
3131- please refer to the
3232- <link xlink:href="https://matrix-org.github.io/synapse/latest/setup/installation.html">installation
3333- instructions of Synapse</link> .
3434- </para>
3535- <programlisting>
3636-{ pkgs, lib, config, ... }:
3737-let
3838- fqdn = "${config.networking.hostName}.${config.networking.domain}";
3939- clientConfig = {
4040- "m.homeserver".base_url = "https://${fqdn}";
4141- "m.identity_server" = {};
4242- };
4343- serverConfig."m.server" = "${config.services.matrix-synapse.settings.server_name}:443";
4444- mkWellKnown = data: ''
4545- add_header Content-Type application/json;
4646- add_header Access-Control-Allow-Origin *;
4747- return 200 '${builtins.toJSON data}';
4848- '';
4949-in {
5050- networking.hostName = "myhostname";
5151- networking.domain = "example.org";
5252- networking.firewall.allowedTCPPorts = [ 80 443 ];
5353-5454- services.postgresql.enable = true;
5555- services.postgresql.initialScript = pkgs.writeText "synapse-init.sql" ''
5656- CREATE ROLE "matrix-synapse" WITH LOGIN PASSWORD 'synapse';
5757- CREATE DATABASE "matrix-synapse" WITH OWNER "matrix-synapse"
5858- TEMPLATE template0
5959- LC_COLLATE = "C"
6060- LC_CTYPE = "C";
6161- '';
6262-6363- services.nginx = {
6464- enable = true;
6565- recommendedTlsSettings = true;
6666- recommendedOptimisation = true;
6767- recommendedGzipSettings = true;
6868- recommendedProxySettings = true;
6969- virtualHosts = {
7070- # If the A and AAAA DNS records on example.org do not point on the same host as the
7171- # records for myhostname.example.org, you can easily move the /.well-known
7272- # virtualHost section of the code to the host that is serving example.org, while
7373- # the rest stays on myhostname.example.org with no other changes required.
7474- # This pattern also allows to seamlessly move the homeserver from
7575- # myhostname.example.org to myotherhost.example.org by only changing the
7676- # /.well-known redirection target.
7777- "${config.networking.domain}" = {
7878- enableACME = true;
7979- forceSSL = true;
8080- # This section is not needed if the server_name of matrix-synapse is equal to
8181- # the domain (i.e. example.org from @foo:example.org) and the federation port
8282- # is 8448.
8383- # Further reference can be found in the docs about delegation under
8484- # https://matrix-org.github.io/synapse/latest/delegate.html
8585- locations."= /.well-known/matrix/server".extraConfig = mkWellKnown serverConfig;
8686- # This is usually needed for homeserver discovery (from e.g. other Matrix clients).
8787- # Further reference can be found in the upstream docs at
8888- # https://spec.matrix.org/latest/client-server-api/#getwell-knownmatrixclient
8989- locations."= /.well-known/matrix/client".extraConfig = mkWellKnown clientConfig;
9090- };
9191- "${fqdn}" = {
9292- enableACME = true;
9393- forceSSL = true;
9494- # It's also possible to do a redirect here or something else, this vhost is not
9595- # needed for Matrix. It's recommended though to *not put* element
9696- # here, see also the section about Element.
9797- locations."/".extraConfig = ''
9898- return 404;
9999- '';
100100- # Forward all Matrix API calls to the synapse Matrix homeserver. A trailing slash
101101- # *must not* be used here.
102102- locations."/_matrix".proxyPass = "http://[::1]:8008";
103103- # Forward requests for e.g. SSO and password-resets.
104104- locations."/_synapse/client".proxyPass = "http://[::1]:8008";
105105- };
106106- };
107107- };
108108-109109- services.matrix-synapse = {
110110- enable = true;
111111- settings.server_name = config.networking.domain;
112112- settings.listeners = [
113113- { port = 8008;
114114- bind_addresses = [ "::1" ];
115115- type = "http";
116116- tls = false;
117117- x_forwarded = true;
118118- resources = [ {
119119- names = [ "client" "federation" ];
120120- compress = true;
121121- } ];
122122- }
123123- ];
124124- };
125125-}
126126-</programlisting>
127127- </section>
128128- <section xml:id="module-services-matrix-register-users">
129129- <title>Registering Matrix users</title>
130130- <para>
131131- If you want to run a server with public registration by anybody,
132132- you can then enable
133133- <literal>services.matrix-synapse.settings.enable_registration = true;</literal>.
134134- Otherwise, or you can generate a registration secret with
135135- <command>pwgen -s 64 1</command> and set it with
136136- <xref linkend="opt-services.matrix-synapse.settings.registration_shared_secret" />.
137137- To create a new user or admin, run the following after you have
138138- set the secret and have rebuilt NixOS:
139139- </para>
140140- <programlisting>
141141-$ nix-shell -p matrix-synapse
142142-$ register_new_matrix_user -k your-registration-shared-secret http://localhost:8008
143143-New user localpart: your-username
144144-Password:
145145-Confirm password:
146146-Make admin [no]:
147147-Success!
148148-</programlisting>
149149- <para>
150150- In the example, this would create a user with the Matrix
151151- Identifier <literal>@your-username:example.org</literal>.
152152- </para>
153153- <warning>
154154- <para>
155155- When using
156156- <xref linkend="opt-services.matrix-synapse.settings.registration_shared_secret" />,
157157- the secret will end up in the world-readable store. Instead it’s
158158- recommended to deploy the secret in an additional file like
159159- this:
160160- </para>
161161- <itemizedlist>
162162- <listitem>
163163- <para>
164164- Create a file with the following contents:
165165- </para>
166166- <programlisting>
167167-registration_shared_secret: your-very-secret-secret
168168-</programlisting>
169169- </listitem>
170170- <listitem>
171171- <para>
172172- Deploy the file with a secret-manager such as
173173- <link xlink:href="https://nixops.readthedocs.io/en/latest/overview.html#managing-keys"><option>deployment.keys</option></link>
174174- from
175175- <citerefentry><refentrytitle>nixops</refentrytitle><manvolnum>1</manvolnum></citerefentry>
176176- or
177177- <link xlink:href="https://github.com/Mic92/sops-nix/">sops-nix</link>
178178- to e.g.
179179- <filename>/run/secrets/matrix-shared-secret</filename> and
180180- ensure that it’s readable by
181181- <literal>matrix-synapse</literal>.
182182- </para>
183183- </listitem>
184184- <listitem>
185185- <para>
186186- Include the file like this in your configuration:
187187- </para>
188188- <programlisting>
189189-{
190190- services.matrix-synapse.extraConfigFiles = [
191191- "/run/secrets/matrix-shared-secret"
192192- ];
193193-}
194194-</programlisting>
195195- </listitem>
196196- </itemizedlist>
197197- </warning>
198198- <note>
199199- <para>
200200- It’s also possible to user alternative authentication mechanism
201201- such as
202202- <link xlink:href="https://github.com/matrix-org/matrix-synapse-ldap3">LDAP
203203- (via <literal>matrix-synapse-ldap3</literal>)</link> or
204204- <link xlink:href="https://matrix-org.github.io/synapse/latest/openid.html">OpenID</link>.
205205- </para>
206206- </note>
207207- </section>
208208- <section xml:id="module-services-matrix-element-web">
209209- <title>Element (formerly known as Riot) Web Client</title>
210210- <para>
211211- <link xlink:href="https://github.com/vector-im/riot-web/">Element
212212- Web</link> is the reference web client for Matrix and developed by
213213- the core team at matrix.org. Element was formerly known as
214214- Riot.im, see the
215215- <link xlink:href="https://element.io/blog/welcome-to-element/">Element
216216- introductory blog post</link> for more information. The following
217217- snippet can be optionally added to the code before to complete the
218218- synapse installation with a web client served at
219219- <literal>https://element.myhostname.example.org</literal> and
220220- <literal>https://element.example.org</literal>. Alternatively, you
221221- can use the hosted copy at
222222- <link xlink:href="https://app.element.io/">https://app.element.io/</link>,
223223- or use other web clients or native client applications. Due to the
224224- <literal>/.well-known</literal> urls set up done above, many
225225- clients should fill in the required connection details
226226- automatically when you enter your Matrix Identifier. See
227227- <link xlink:href="https://matrix.org/docs/projects/try-matrix-now.html">Try
228228- Matrix Now!</link> for a list of existing clients and their
229229- supported featureset.
230230- </para>
231231- <programlisting>
232232-{
233233- services.nginx.virtualHosts."element.${fqdn}" = {
234234- enableACME = true;
235235- forceSSL = true;
236236- serverAliases = [
237237- "element.${config.networking.domain}"
238238- ];
239239-240240- root = pkgs.element-web.override {
241241- conf = {
242242- default_server_config = clientConfig; # see `clientConfig` from the snippet above.
243243- };
244244- };
245245- };
246246-}
247247-</programlisting>
248248- <note>
249249- <para>
250250- The Element developers do not recommend running Element and your
251251- Matrix homeserver on the same fully-qualified domain name for
252252- security reasons. In the example, this means that you should not
253253- reuse the <literal>myhostname.example.org</literal> virtualHost
254254- to also serve Element, but instead serve it on a different
255255- subdomain, like <literal>element.example.org</literal> in the
256256- example. See the
257257- <link xlink:href="https://github.com/vector-im/element-web/tree/v1.10.0#important-security-notes">Element
258258- Important Security Notes</link> for more information on this
259259- subject.
260260- </para>
261261- </note>
262262- </section>
263263-</chapter>
···11-<!-- Do not edit this file directly, edit its companion .md instead
22- and regenerate this file using nixos/doc/manual/md-to-db.sh -->
33-<chapter xmlns="http://docbook.org/ns/docbook" xmlns:xlink="http://www.w3.org/1999/xlink" xml:id="module-services-gitlab">
44- <title>GitLab</title>
55- <para>
66- GitLab is a feature-rich git hosting service.
77- </para>
88- <section xml:id="module-services-gitlab-prerequisites">
99- <title>Prerequisites</title>
1010- <para>
1111- The <literal>gitlab</literal> service exposes only an Unix socket
1212- at <literal>/run/gitlab/gitlab-workhorse.socket</literal>. You
1313- need to configure a webserver to proxy HTTP requests to the
1414- socket.
1515- </para>
1616- <para>
1717- For instance, the following configuration could be used to use
1818- nginx as frontend proxy:
1919- </para>
2020- <programlisting>
2121-services.nginx = {
2222- enable = true;
2323- recommendedGzipSettings = true;
2424- recommendedOptimisation = true;
2525- recommendedProxySettings = true;
2626- recommendedTlsSettings = true;
2727- virtualHosts."git.example.com" = {
2828- enableACME = true;
2929- forceSSL = true;
3030- locations."/".proxyPass = "http://unix:/run/gitlab/gitlab-workhorse.socket";
3131- };
3232-};
3333-</programlisting>
3434- </section>
3535- <section xml:id="module-services-gitlab-configuring">
3636- <title>Configuring</title>
3737- <para>
3838- GitLab depends on both PostgreSQL and Redis and will automatically
3939- enable both services. In the case of PostgreSQL, a database and a
4040- role will be created.
4141- </para>
4242- <para>
4343- The default state dir is <literal>/var/gitlab/state</literal>.
4444- This is where all data like the repositories and uploads will be
4545- stored.
4646- </para>
4747- <para>
4848- A basic configuration with some custom settings could look like
4949- this:
5050- </para>
5151- <programlisting>
5252-services.gitlab = {
5353- enable = true;
5454- databasePasswordFile = "/var/keys/gitlab/db_password";
5555- initialRootPasswordFile = "/var/keys/gitlab/root_password";
5656- https = true;
5757- host = "git.example.com";
5858- port = 443;
5959- user = "git";
6060- group = "git";
6161- smtp = {
6262- enable = true;
6363- address = "localhost";
6464- port = 25;
6565- };
6666- secrets = {
6767- dbFile = "/var/keys/gitlab/db";
6868- secretFile = "/var/keys/gitlab/secret";
6969- otpFile = "/var/keys/gitlab/otp";
7070- jwsFile = "/var/keys/gitlab/jws";
7171- };
7272- extraConfig = {
7373- gitlab = {
7474- email_from = "gitlab-no-reply@example.com";
7575- email_display_name = "Example GitLab";
7676- email_reply_to = "gitlab-no-reply@example.com";
7777- default_projects_features = { builds = false; };
7878- };
7979- };
8080-};
8181-</programlisting>
8282- <para>
8383- If you’re setting up a new GitLab instance, generate new secrets.
8484- You for instance use
8585- <literal>tr -dc A-Za-z0-9 < /dev/urandom | head -c 128 > /var/keys/gitlab/db</literal>
8686- to generate a new db secret. Make sure the files can be read by,
8787- and only by, the user specified by
8888- <link linkend="opt-services.gitlab.user">services.gitlab.user</link>.
8989- GitLab encrypts sensitive data stored in the database. If you’re
9090- restoring an existing GitLab instance, you must specify the
9191- secrets secret from <literal>config/secrets.yml</literal> located
9292- in your GitLab state folder.
9393- </para>
9494- <para>
9595- When <literal>incoming_mail.enabled</literal> is set to
9696- <literal>true</literal> in
9797- <link linkend="opt-services.gitlab.extraConfig">extraConfig</link>
9898- an additional service called <literal>gitlab-mailroom</literal> is
9999- enabled for fetching incoming mail.
100100- </para>
101101- <para>
102102- Refer to <xref linkend="ch-options" /> for all available
103103- configuration options for the
104104- <link linkend="opt-services.gitlab.enable">services.gitlab</link>
105105- module.
106106- </para>
107107- </section>
108108- <section xml:id="module-services-gitlab-maintenance">
109109- <title>Maintenance</title>
110110- <section xml:id="module-services-gitlab-maintenance-backups">
111111- <title>Backups</title>
112112- <para>
113113- Backups can be configured with the options in
114114- <link linkend="opt-services.gitlab.backup.keepTime">services.gitlab.backup</link>.
115115- Use the
116116- <link linkend="opt-services.gitlab.backup.startAt">services.gitlab.backup.startAt</link>
117117- option to configure regular backups.
118118- </para>
119119- <para>
120120- To run a manual backup, start the
121121- <literal>gitlab-backup</literal> service:
122122- </para>
123123- <programlisting>
124124-$ systemctl start gitlab-backup.service
125125-</programlisting>
126126- </section>
127127- <section xml:id="module-services-gitlab-maintenance-rake">
128128- <title>Rake tasks</title>
129129- <para>
130130- You can run GitLab’s rake tasks with
131131- <literal>gitlab-rake</literal> which will be available on the
132132- system when GitLab is enabled. You will have to run the command
133133- as the user that you configured to run GitLab with.
134134- </para>
135135- <para>
136136- A list of all available rake tasks can be obtained by running:
137137- </para>
138138- <programlisting>
139139-$ sudo -u git -H gitlab-rake -T
140140-</programlisting>
141141- </section>
142142- </section>
143143-</chapter>
···11-<!-- Do not edit this file directly, edit its companion .md instead
22- and regenerate this file using nixos/doc/manual/md-to-db.sh -->
33-<chapter xmlns="http://docbook.org/ns/docbook" xmlns:xlink="http://www.w3.org/1999/xlink" xml:id="module-services-sourcehut">
44- <title>Sourcehut</title>
55- <para>
66- <link xlink:href="https://sr.ht.com/">Sourcehut</link> is an
77- open-source, self-hostable software development platform. The server
88- setup can be automated using
99- <link linkend="opt-services.sourcehut.enable">services.sourcehut</link>.
1010- </para>
1111- <section xml:id="module-services-sourcehut-basic-usage">
1212- <title>Basic usage</title>
1313- <para>
1414- Sourcehut is a Python and Go based set of applications. This NixOS
1515- module also provides basic configuration integrating Sourcehut
1616- into locally running <literal>services.nginx</literal>,
1717- <literal>services.redis.servers.sourcehut</literal>,
1818- <literal>services.postfix</literal> and
1919- <literal>services.postgresql</literal> services.
2020- </para>
2121- <para>
2222- A very basic configuration may look like this:
2323- </para>
2424- <programlisting>
2525-{ pkgs, ... }:
2626-let
2727- fqdn =
2828- let
2929- join = hostName: domain: hostName + optionalString (domain != null) ".${domain}";
3030- in join config.networking.hostName config.networking.domain;
3131-in {
3232-3333- networking = {
3434- hostName = "srht";
3535- domain = "tld";
3636- firewall.allowedTCPPorts = [ 22 80 443 ];
3737- };
3838-3939- services.sourcehut = {
4040- enable = true;
4141- git.enable = true;
4242- man.enable = true;
4343- meta.enable = true;
4444- nginx.enable = true;
4545- postfix.enable = true;
4646- postgresql.enable = true;
4747- redis.enable = true;
4848- settings = {
4949- "sr.ht" = {
5050- environment = "production";
5151- global-domain = fqdn;
5252- origin = "https://${fqdn}";
5353- # Produce keys with srht-keygen from sourcehut.coresrht.
5454- network-key = "/run/keys/path/to/network-key";
5555- service-key = "/run/keys/path/to/service-key";
5656- };
5757- webhooks.private-key= "/run/keys/path/to/webhook-key";
5858- };
5959- };
6060-6161- security.acme.certs."${fqdn}".extraDomainNames = [
6262- "meta.${fqdn}"
6363- "man.${fqdn}"
6464- "git.${fqdn}"
6565- ];
6666-6767- services.nginx = {
6868- enable = true;
6969- # only recommendedProxySettings are strictly required, but the rest make sense as well.
7070- recommendedTlsSettings = true;
7171- recommendedOptimisation = true;
7272- recommendedGzipSettings = true;
7373- recommendedProxySettings = true;
7474-7575- # Settings to setup what certificates are used for which endpoint.
7676- virtualHosts = {
7777- "${fqdn}".enableACME = true;
7878- "meta.${fqdn}".useACMEHost = fqdn:
7979- "man.${fqdn}".useACMEHost = fqdn:
8080- "git.${fqdn}".useACMEHost = fqdn:
8181- };
8282- };
8383-}
8484-</programlisting>
8585- <para>
8686- The <literal>hostName</literal> option is used internally to
8787- configure the nginx reverse-proxy. The <literal>settings</literal>
8888- attribute set is used by the configuration generator and the
8989- result is placed in <literal>/etc/sr.ht/config.ini</literal>.
9090- </para>
9191- </section>
9292- <section xml:id="module-services-sourcehut-configuration">
9393- <title>Configuration</title>
9494- <para>
9595- All configuration parameters are also stored in
9696- <literal>/etc/sr.ht/config.ini</literal> which is generated by the
9797- module and linked from the store to ensure that all values from
9898- <literal>config.ini</literal> can be modified by the module.
9999- </para>
100100- </section>
101101- <section xml:id="module-services-sourcehut-httpd">
102102- <title>Using an alternative webserver as reverse-proxy (e.g.
103103- <literal>httpd</literal>)</title>
104104- <para>
105105- By default, <literal>nginx</literal> is used as reverse-proxy for
106106- <literal>sourcehut</literal>. However, it’s possible to use e.g.
107107- <literal>httpd</literal> by explicitly disabling
108108- <literal>nginx</literal> using
109109- <xref linkend="opt-services.nginx.enable" /> and fixing the
110110- <literal>settings</literal>.
111111- </para>
112112- </section>
113113-</chapter>
···11-<!-- Do not edit this file directly, edit its companion .md instead
22- and regenerate this file using nixos/doc/manual/md-to-db.sh -->
33-<chapter xmlns="http://docbook.org/ns/docbook" xmlns:xlink="http://www.w3.org/1999/xlink" xml:id="module-services-taskserver">
44- <title>Taskserver</title>
55- <para>
66- Taskserver is the server component of
77- <link xlink:href="https://taskwarrior.org/">Taskwarrior</link>, a
88- free and open source todo list application.
99- </para>
1010- <para>
1111- <emphasis>Upstream documentation:</emphasis>
1212- <link xlink:href="https://taskwarrior.org/docs/#taskd">https://taskwarrior.org/docs/#taskd</link>
1313- </para>
1414- <section xml:id="module-services-taskserver-configuration">
1515- <title>Configuration</title>
1616- <para>
1717- Taskserver does all of its authentication via TLS using client
1818- certificates, so you either need to roll your own CA or purchase a
1919- certificate from a known CA, which allows creation of client
2020- certificates. These certificates are usually advertised as
2121- <quote>server certificates</quote>.
2222- </para>
2323- <para>
2424- So in order to make it easier to handle your own CA, there is a
2525- helper tool called <command>nixos-taskserver</command> which
2626- manages the custom CA along with Taskserver organisations, users
2727- and groups.
2828- </para>
2929- <para>
3030- While the client certificates in Taskserver only authenticate
3131- whether a user is allowed to connect, every user has its own UUID
3232- which identifies it as an entity.
3333- </para>
3434- <para>
3535- With <command>nixos-taskserver</command> the client certificate is
3636- created along with the UUID of the user, so it handles all of the
3737- credentials needed in order to setup the Taskwarrior client to
3838- work with a Taskserver.
3939- </para>
4040- </section>
4141- <section xml:id="module-services-taskserver-nixos-taskserver-tool">
4242- <title>The nixos-taskserver tool</title>
4343- <para>
4444- Because Taskserver by default only provides scripts to setup users
4545- imperatively, the <command>nixos-taskserver</command> tool is used
4646- for addition and deletion of organisations along with users and
4747- groups defined by
4848- <xref linkend="opt-services.taskserver.organisations" /> and as
4949- well for imperative set up.
5050- </para>
5151- <para>
5252- The tool is designed to not interfere if the command is used to
5353- manually set up some organisations, users or groups.
5454- </para>
5555- <para>
5656- For example if you add a new organisation using
5757- <command>nixos-taskserver org add foo</command>, the organisation
5858- is not modified and deleted no matter what you define in
5959- <option>services.taskserver.organisations</option>, even if you’re
6060- adding the same organisation in that option.
6161- </para>
6262- <para>
6363- The tool is modelled to imitate the official
6464- <command>taskd</command> command, documentation for each
6565- subcommand can be shown by using the <option>--help</option>
6666- switch.
6767- </para>
6868- </section>
6969- <section xml:id="module-services-taskserver-declarative-ca-management">
7070- <title>Declarative/automatic CA management</title>
7171- <para>
7272- Everything is done according to what you specify in the module
7373- options, however in order to set up a Taskwarrior client for
7474- synchronisation with a Taskserver instance, you have to transfer
7575- the keys and certificates to the client machine.
7676- </para>
7777- <para>
7878- This is done using
7979- <command>nixos-taskserver user export $orgname $username</command>
8080- which is printing a shell script fragment to stdout which can
8181- either be used verbatim or adjusted to import the user on the
8282- client machine.
8383- </para>
8484- <para>
8585- For example, let’s say you have the following configuration:
8686- </para>
8787- <programlisting>
8888-{
8989- services.taskserver.enable = true;
9090- services.taskserver.fqdn = "server";
9191- services.taskserver.listenHost = "::";
9292- services.taskserver.organisations.my-company.users = [ "alice" ];
9393-}
9494-</programlisting>
9595- <para>
9696- This creates an organisation called <literal>my-company</literal>
9797- with the user <literal>alice</literal>.
9898- </para>
9999- <para>
100100- Now in order to import the <literal>alice</literal> user to
101101- another machine <literal>alicebox</literal>, all we need to do is
102102- something like this:
103103- </para>
104104- <programlisting>
105105-$ ssh server nixos-taskserver user export my-company alice | sh
106106-</programlisting>
107107- <para>
108108- Of course, if no SSH daemon is available on the server you can
109109- also copy & paste it directly into a shell.
110110- </para>
111111- <para>
112112- After this step the user should be set up and you can start
113113- synchronising your tasks for the first time with
114114- <command>task sync init</command> on <literal>alicebox</literal>.
115115- </para>
116116- <para>
117117- Subsequent synchronisation requests merely require the command
118118- <command>task sync</command> after that stage.
119119- </para>
120120- </section>
121121- <section xml:id="module-services-taskserver-manual-ca-management">
122122- <title>Manual CA management</title>
123123- <para>
124124- If you set any options within
125125- <link linkend="opt-services.taskserver.pki.manual.ca.cert">service.taskserver.pki.manual</link>.*,
126126- <command>nixos-taskserver</command> won’t issue certificates, but
127127- you can still use it for adding or removing user accounts.
128128- </para>
129129- </section>
130130-</chapter>
···11-<!-- Do not edit this file directly, edit its companion .md instead
22- and regenerate this file using nixos/doc/manual/md-to-db.sh -->
33-<chapter xmlns="http://docbook.org/ns/docbook" xmlns:xlink="http://www.w3.org/1999/xlink" xml:id="module-services-weechat">
44- <title>WeeChat</title>
55- <para>
66- <link xlink:href="https://weechat.org/">WeeChat</link> is a fast and
77- extensible IRC client.
88- </para>
99- <section xml:id="module-services-weechat-basic-usage">
1010- <title>Basic Usage</title>
1111- <para>
1212- By default, the module creates a
1313- <link xlink:href="https://www.freedesktop.org/wiki/Software/systemd/"><literal>systemd</literal></link>
1414- unit which runs the chat client in a detached
1515- <link xlink:href="https://www.gnu.org/software/screen/"><literal>screen</literal></link>
1616- session.
1717- </para>
1818- <para>
1919- This can be done by enabling the <literal>weechat</literal>
2020- service:
2121- </para>
2222- <programlisting>
2323-{ ... }:
2424-2525-{
2626- services.weechat.enable = true;
2727-}
2828-</programlisting>
2929- <para>
3030- The service is managed by a dedicated user named
3131- <literal>weechat</literal> in the state directory
3232- <literal>/var/lib/weechat</literal>.
3333- </para>
3434- </section>
3535- <section xml:id="module-services-weechat-reattach">
3636- <title>Re-attaching to WeeChat</title>
3737- <para>
3838- WeeChat runs in a screen session owned by a dedicated user. To
3939- explicitly allow your another user to attach to this session, the
4040- <literal>screenrc</literal> needs to be tweaked by adding
4141- <link xlink:href="https://www.gnu.org/software/screen/manual/html_node/Multiuser.html#Multiuser">multiuser</link>
4242- support:
4343- </para>
4444- <programlisting>
4545-{
4646- programs.screen.screenrc = ''
4747- multiuser on
4848- acladd normal_user
4949- '';
5050-}
5151-</programlisting>
5252- <para>
5353- Now, the session can be re-attached like this:
5454- </para>
5555- <programlisting>
5656-screen -x weechat/weechat-screen
5757-</programlisting>
5858- <para>
5959- <emphasis>The session name can be changed using
6060- <link xlink:href="options.html#opt-services.weechat.sessionName">services.weechat.sessionName.</link></emphasis>
6161- </para>
6262- </section>
6363-</chapter>
···11-<!-- Do not edit this file directly, edit its companion .md instead
22- and regenerate this file using nixos/doc/manual/md-to-db.sh -->
33-<chapter xmlns="http://docbook.org/ns/docbook" xmlns:xlink="http://www.w3.org/1999/xlink" xml:id="module-services-parsedmarc">
44- <title>parsedmarc</title>
55- <para>
66- <link xlink:href="https://domainaware.github.io/parsedmarc/">parsedmarc</link>
77- is a service which parses incoming
88- <link xlink:href="https://dmarc.org/">DMARC</link> reports and
99- stores or sends them to a downstream service for further analysis.
1010- In combination with Elasticsearch, Grafana and the included Grafana
1111- dashboard, it provides a handy overview of DMARC reports over time.
1212- </para>
1313- <section xml:id="module-services-parsedmarc-basic-usage">
1414- <title>Basic usage</title>
1515- <para>
1616- A very minimal setup which reads incoming reports from an external
1717- email address and saves them to a local Elasticsearch instance
1818- looks like this:
1919- </para>
2020- <programlisting language="nix">
2121-services.parsedmarc = {
2222- enable = true;
2323- settings.imap = {
2424- host = "imap.example.com";
2525- user = "alice@example.com";
2626- password = "/path/to/imap_password_file";
2727- };
2828- provision.geoIp = false; # Not recommended!
2929-};
3030-</programlisting>
3131- <para>
3232- Note that GeoIP provisioning is disabled in the example for
3333- simplicity, but should be turned on for fully functional reports.
3434- </para>
3535- </section>
3636- <section xml:id="module-services-parsedmarc-local-mail">
3737- <title>Local mail</title>
3838- <para>
3939- Instead of watching an external inbox, a local inbox can be
4040- automatically provisioned. The recipient’s name is by default set
4141- to <literal>dmarc</literal>, but can be configured in
4242- <link xlink:href="options.html#opt-services.parsedmarc.provision.localMail.recipientName">services.parsedmarc.provision.localMail.recipientName</link>.
4343- You need to add an MX record pointing to the host. More
4444- concretely: for the example to work, an MX record needs to be set
4545- up for <literal>monitoring.example.com</literal> and the complete
4646- email address that should be configured in the domain’s dmarc
4747- policy is <literal>dmarc@monitoring.example.com</literal>.
4848- </para>
4949- <programlisting language="nix">
5050-services.parsedmarc = {
5151- enable = true;
5252- provision = {
5353- localMail = {
5454- enable = true;
5555- hostname = monitoring.example.com;
5656- };
5757- geoIp = false; # Not recommended!
5858- };
5959-};
6060-</programlisting>
6161- </section>
6262- <section xml:id="module-services-parsedmarc-grafana-geoip">
6363- <title>Grafana and GeoIP</title>
6464- <para>
6565- The reports can be visualized and summarized with parsedmarc’s
6666- official Grafana dashboard. For all views to work, and for the
6767- data to be complete, GeoIP databases are also required. The
6868- following example shows a basic deployment where the provisioned
6969- Elasticsearch instance is automatically added as a Grafana
7070- datasource, and the dashboard is added to Grafana as well.
7171- </para>
7272- <programlisting language="nix">
7373-services.parsedmarc = {
7474- enable = true;
7575- provision = {
7676- localMail = {
7777- enable = true;
7878- hostname = url;
7979- };
8080- grafana = {
8181- datasource = true;
8282- dashboard = true;
8383- };
8484- };
8585-};
8686-8787-# Not required, but recommended for full functionality
8888-services.geoipupdate = {
8989- settings = {
9090- AccountID = 000000;
9191- LicenseKey = "/path/to/license_key_file";
9292- };
9393-};
9494-9595-services.grafana = {
9696- enable = true;
9797- addr = "0.0.0.0";
9898- domain = url;
9999- rootUrl = "https://" + url;
100100- protocol = "socket";
101101- security = {
102102- adminUser = "admin";
103103- adminPasswordFile = "/path/to/admin_password_file";
104104- secretKeyFile = "/path/to/secret_key_file";
105105- };
106106-};
107107-108108-services.nginx = {
109109- enable = true;
110110- recommendedTlsSettings = true;
111111- recommendedOptimisation = true;
112112- recommendedGzipSettings = true;
113113- recommendedProxySettings = true;
114114- upstreams.grafana.servers."unix:/${config.services.grafana.socket}" = {};
115115- virtualHosts.${url} = {
116116- root = config.services.grafana.staticRootPath;
117117- enableACME = true;
118118- forceSSL = true;
119119- locations."/".tryFiles = "$uri @grafana";
120120- locations."@grafana".proxyPass = "http://grafana";
121121- };
122122-};
123123-users.users.nginx.extraGroups = [ "grafana" ];
124124-</programlisting>
125125- </section>
126126-</chapter>
···11-<!-- Do not edit this file directly, edit its companion .md instead
22- and regenerate this file using nixos/doc/manual/md-to-db.sh -->
33-<chapter xmlns="http://docbook.org/ns/docbook" xmlns:xlink="http://www.w3.org/1999/xlink" xml:id="module-services-prometheus-exporters">
44- <title>Prometheus exporters</title>
55- <para>
66- Prometheus exporters provide metrics for the
77- <link xlink:href="https://prometheus.io">prometheus monitoring
88- system</link>.
99- </para>
1010- <section xml:id="module-services-prometheus-exporters-configuration">
1111- <title>Configuration</title>
1212- <para>
1313- One of the most common exporters is the
1414- <link xlink:href="https://github.com/prometheus/node_exporter">node
1515- exporter</link>, it provides hardware and OS metrics from the host
1616- it’s running on. The exporter could be configured as follows:
1717- </para>
1818- <programlisting>
1919- services.prometheus.exporters.node = {
2020- enable = true;
2121- port = 9100;
2222- enabledCollectors = [
2323- "logind"
2424- "systemd"
2525- ];
2626- disabledCollectors = [
2727- "textfile"
2828- ];
2929- openFirewall = true;
3030- firewallFilter = "-i br0 -p tcp -m tcp --dport 9100";
3131- };
3232-</programlisting>
3333- <para>
3434- It should now serve all metrics from the collectors that are
3535- explicitly enabled and the ones that are
3636- <link xlink:href="https://github.com/prometheus/node_exporter#enabled-by-default">enabled
3737- by default</link>, via http under <literal>/metrics</literal>. In
3838- this example the firewall should just allow incoming connections
3939- to the exporter’s port on the bridge interface
4040- <literal>br0</literal> (this would have to be configured
4141- separately of course). For more information about configuration
4242- see <literal>man configuration.nix</literal> or search through the
4343- <link xlink:href="https://nixos.org/nixos/options.html#prometheus.exporters">available
4444- options</link>.
4545- </para>
4646- <para>
4747- Prometheus can now be configured to consume the metrics produced
4848- by the exporter:
4949- </para>
5050- <programlisting>
5151- services.prometheus = {
5252- # ...
5353-5454- scrapeConfigs = [
5555- {
5656- job_name = "node";
5757- static_configs = [{
5858- targets = [ "localhost:${toString config.services.prometheus.exporters.node.port}" ];
5959- }];
6060- }
6161- ];
6262-6363- # ...
6464- }
6565-</programlisting>
6666- </section>
6767- <section xml:id="module-services-prometheus-exporters-new-exporter">
6868- <title>Adding a new exporter</title>
6969- <para>
7070- To add a new exporter, it has to be packaged first (see
7171- <literal>nixpkgs/pkgs/servers/monitoring/prometheus/</literal> for
7272- examples), then a module can be added. The postfix exporter is
7373- used in this example:
7474- </para>
7575- <itemizedlist>
7676- <listitem>
7777- <para>
7878- Some default options for all exporters are provided by
7979- <literal>nixpkgs/nixos/modules/services/monitoring/prometheus/exporters.nix</literal>:
8080- </para>
8181- <itemizedlist spacing="compact">
8282- <listitem>
8383- <para>
8484- <literal>enable</literal>
8585- </para>
8686- </listitem>
8787- <listitem>
8888- <para>
8989- <literal>port</literal>
9090- </para>
9191- </listitem>
9292- <listitem>
9393- <para>
9494- <literal>listenAddress</literal>
9595- </para>
9696- </listitem>
9797- <listitem>
9898- <para>
9999- <literal>extraFlags</literal>
100100- </para>
101101- </listitem>
102102- <listitem>
103103- <para>
104104- <literal>openFirewall</literal>
105105- </para>
106106- </listitem>
107107- <listitem>
108108- <para>
109109- <literal>firewallFilter</literal>
110110- </para>
111111- </listitem>
112112- <listitem>
113113- <para>
114114- <literal>user</literal>
115115- </para>
116116- </listitem>
117117- <listitem>
118118- <para>
119119- <literal>group</literal>
120120- </para>
121121- </listitem>
122122- </itemizedlist>
123123- </listitem>
124124- <listitem>
125125- <para>
126126- As there is already a package available, the module can now be
127127- added. This is accomplished by adding a new file to the
128128- <literal>nixos/modules/services/monitoring/prometheus/exporters/</literal>
129129- directory, which will be called postfix.nix and contains all
130130- exporter specific options and configuration:
131131- </para>
132132- <programlisting>
133133-# nixpgs/nixos/modules/services/prometheus/exporters/postfix.nix
134134-{ config, lib, pkgs, options }:
135135-136136-with lib;
137137-138138-let
139139- # for convenience we define cfg here
140140- cfg = config.services.prometheus.exporters.postfix;
141141-in
142142-{
143143- port = 9154; # The postfix exporter listens on this port by default
144144-145145- # `extraOpts` is an attribute set which contains additional options
146146- # (and optional overrides for default options).
147147- # Note that this attribute is optional.
148148- extraOpts = {
149149- telemetryPath = mkOption {
150150- type = types.str;
151151- default = "/metrics";
152152- description = ''
153153- Path under which to expose metrics.
154154- '';
155155- };
156156- logfilePath = mkOption {
157157- type = types.path;
158158- default = /var/log/postfix_exporter_input.log;
159159- example = /var/log/mail.log;
160160- description = ''
161161- Path where Postfix writes log entries.
162162- This file will be truncated by this exporter!
163163- '';
164164- };
165165- showqPath = mkOption {
166166- type = types.path;
167167- default = /var/spool/postfix/public/showq;
168168- example = /var/lib/postfix/queue/public/showq;
169169- description = ''
170170- Path at which Postfix places its showq socket.
171171- '';
172172- };
173173- };
174174-175175- # `serviceOpts` is an attribute set which contains configuration
176176- # for the exporter's systemd service. One of
177177- # `serviceOpts.script` and `serviceOpts.serviceConfig.ExecStart`
178178- # has to be specified here. This will be merged with the default
179179- # service configuration.
180180- # Note that by default 'DynamicUser' is 'true'.
181181- serviceOpts = {
182182- serviceConfig = {
183183- DynamicUser = false;
184184- ExecStart = ''
185185- ${pkgs.prometheus-postfix-exporter}/bin/postfix_exporter \
186186- --web.listen-address ${cfg.listenAddress}:${toString cfg.port} \
187187- --web.telemetry-path ${cfg.telemetryPath} \
188188- ${concatStringsSep " \\\n " cfg.extraFlags}
189189- '';
190190- };
191191- };
192192-}
193193-</programlisting>
194194- </listitem>
195195- <listitem>
196196- <para>
197197- This should already be enough for the postfix exporter.
198198- Additionally one could now add assertions and conditional
199199- default values. This can be done in the
200200- <quote>meta-module</quote> that combines all exporter
201201- definitions and generates the submodules:
202202- <literal>nixpkgs/nixos/modules/services/prometheus/exporters.nix</literal>
203203- </para>
204204- </listitem>
205205- </itemizedlist>
206206- </section>
207207- <section xml:id="module-services-prometheus-exporters-update-exporter-module">
208208- <title>Updating an exporter module</title>
209209- <para>
210210- Should an exporter option change at some point, it is possible to
211211- add information about the change to the exporter definition
212212- similar to <literal>nixpkgs/nixos/modules/rename.nix</literal>:
213213- </para>
214214- <programlisting>
215215-{ config, lib, pkgs, options }:
216216-217217-with lib;
218218-219219-let
220220- cfg = config.services.prometheus.exporters.nginx;
221221-in
222222-{
223223- port = 9113;
224224- extraOpts = {
225225- # additional module options
226226- # ...
227227- };
228228- serviceOpts = {
229229- # service configuration
230230- # ...
231231- };
232232- imports = [
233233- # 'services.prometheus.exporters.nginx.telemetryEndpoint' -> 'services.prometheus.exporters.nginx.telemetryPath'
234234- (mkRenamedOptionModule [ "telemetryEndpoint" ] [ "telemetryPath" ])
235235-236236- # removed option 'services.prometheus.exporters.nginx.insecure'
237237- (mkRemovedOptionModule [ "insecure" ] ''
238238- This option was replaced by 'prometheus.exporters.nginx.sslVerify' which defaults to true.
239239- '')
240240- ({ options.warnings = options.warnings; })
241241- ];
242242-}
243243-</programlisting>
244244- </section>
245245-</chapter>
···11-<!-- Do not edit this file directly, edit its companion .md instead
22- and regenerate this file using nixos/doc/manual/md-to-db.sh -->
33-<chapter xmlns="http://docbook.org/ns/docbook" xmlns:xlink="http://www.w3.org/1999/xlink" xml:id="module-services-firefox-syncserver">
44- <title>Firefox Sync server</title>
55- <para>
66- A storage server for Firefox Sync that you can easily host yourself.
77- </para>
88- <section xml:id="module-services-firefox-syncserver-quickstart">
99- <title>Quickstart</title>
1010- <para>
1111- The absolute minimal configuration for the sync server looks like
1212- this:
1313- </para>
1414- <programlisting language="nix">
1515-services.mysql.package = pkgs.mariadb;
1616-1717-services.firefox-syncserver = {
1818- enable = true;
1919- secrets = builtins.toFile "sync-secrets" ''
2020- SYNC_MASTER_SECRET=this-secret-is-actually-leaked-to-/nix/store
2121- '';
2222- singleNode = {
2323- enable = true;
2424- hostname = "localhost";
2525- url = "http://localhost:5000";
2626- };
2727-};
2828-</programlisting>
2929- <para>
3030- This will start a sync server that is only accessible locally.
3131- Once the services is running you can navigate to
3232- <literal>about:config</literal> in your Firefox profile and set
3333- <literal>identity.sync.tokenserver.uri</literal> to
3434- <literal>http://localhost:5000/1.0/sync/1.5</literal>. Your
3535- browser will now use your local sync server for data storage.
3636- </para>
3737- <warning>
3838- <para>
3939- This configuration should never be used in production. It is not
4040- encrypted and stores its secrets in a world-readable location.
4141- </para>
4242- </warning>
4343- </section>
4444- <section xml:id="module-services-firefox-syncserver-configuration">
4545- <title>More detailed setup</title>
4646- <para>
4747- The <literal>firefox-syncserver</literal> service provides a
4848- number of options to make setting up small deployment easier.
4949- These are grouped under the <literal>singleNode</literal> element
5050- of the option tree and allow simple configuration of the most
5151- important parameters.
5252- </para>
5353- <para>
5454- Single node setup is split into two kinds of options: those that
5555- affect the sync server itself, and those that affect its
5656- surroundings. Options that affect the sync server are
5757- <literal>capacity</literal>, which configures how many accounts
5858- may be active on this instance, and <literal>url</literal>, which
5959- holds the URL under which the sync server can be accessed. The
6060- <literal>url</literal> can be configured automatically when using
6161- nginx.
6262- </para>
6363- <para>
6464- Options that affect the surroundings of the sync server are
6565- <literal>enableNginx</literal>, <literal>enableTLS</literal> and
6666- <literal>hostnam</literal>. If <literal>enableNginx</literal> is
6767- set the sync server module will automatically add an nginx virtual
6868- host to the system using <literal>hostname</literal> as the domain
6969- and set <literal>url</literal> accordingly. If
7070- <literal>enableTLS</literal> is set the module will also enable
7171- ACME certificates on the new virtual host and force all
7272- connections to be made via TLS.
7373- </para>
7474- <para>
7575- For actual deployment it is also recommended to store the
7676- <literal>secrets</literal> file in a secure location.
7777- </para>
7878- </section>
7979-</chapter>
···11-<!-- Do not edit this file directly, edit its companion .md instead
22- and regenerate this file using nixos/doc/manual/md-to-db.sh -->
33-<chapter xmlns="http://docbook.org/ns/docbook" xmlns:xlink="http://www.w3.org/1999/xlink" xml:id="module-services-mosquitto">
44- <title>Mosquitto</title>
55- <para>
66- Mosquitto is a MQTT broker often used for IoT or home automation
77- data transport.
88- </para>
99- <section xml:id="module-services-mosquitto-quickstart">
1010- <title>Quickstart</title>
1111- <para>
1212- A minimal configuration for Mosquitto is
1313- </para>
1414- <programlisting language="nix">
1515-services.mosquitto = {
1616- enable = true;
1717- listeners = [ {
1818- acl = [ "pattern readwrite #" ];
1919- omitPasswordAuth = true;
2020- settings.allow_anonymous = true;
2121- } ];
2222-};
2323-</programlisting>
2424- <para>
2525- This will start a broker on port 1883, listening on all interfaces
2626- of the machine, allowing read/write access to all topics to any
2727- user without password requirements.
2828- </para>
2929- <para>
3030- User authentication can be configured with the
3131- <literal>users</literal> key of listeners. A config that gives
3232- full read access to a user <literal>monitor</literal> and
3333- restricted write access to a user <literal>service</literal> could
3434- look like
3535- </para>
3636- <programlisting language="nix">
3737-services.mosquitto = {
3838- enable = true;
3939- listeners = [ {
4040- users = {
4141- monitor = {
4242- acl = [ "read #" ];
4343- password = "monitor";
4444- };
4545- service = {
4646- acl = [ "write service/#" ];
4747- password = "service";
4848- };
4949- };
5050- } ];
5151-};
5252-</programlisting>
5353- <para>
5454- TLS authentication is configured by setting TLS-related options of
5555- the listener:
5656- </para>
5757- <programlisting language="nix">
5858-services.mosquitto = {
5959- enable = true;
6060- listeners = [ {
6161- port = 8883; # port change is not required, but helpful to avoid mistakes
6262- # ...
6363- settings = {
6464- cafile = "/path/to/mqtt.ca.pem";
6565- certfile = "/path/to/mqtt.pem";
6666- keyfile = "/path/to/mqtt.key";
6767- };
6868- } ];
6969-</programlisting>
7070- </section>
7171- <section xml:id="module-services-mosquitto-config">
7272- <title>Configuration</title>
7373- <para>
7474- The Mosquitto configuration has four distinct types of settings:
7575- the global settings of the daemon, listeners, plugins, and
7676- bridges. Bridges and listeners are part of the global
7777- configuration, plugins are part of listeners. Users of the broker
7878- are configured as parts of listeners rather than globally,
7979- allowing configurations in which a given user is only allowed to
8080- log in to the broker using specific listeners (eg to configure an
8181- admin user with full access to all topics, but restricted to
8282- localhost).
8383- </para>
8484- <para>
8585- Almost all options of Mosquitto are available for configuration at
8686- their appropriate levels, some as NixOS options written in camel
8787- case, the remainders under <literal>settings</literal> with their
8888- exact names in the Mosquitto config file. The exceptions are
8989- <literal>acl_file</literal> (which is always set according to the
9090- <literal>acl</literal> attributes of a listener and its users) and
9191- <literal>per_listener_settings</literal> (which is always set to
9292- <literal>true</literal>).
9393- </para>
9494- <section xml:id="module-services-mosquitto-config-passwords">
9595- <title>Password authentication</title>
9696- <para>
9797- Mosquitto can be run in two modes, with a password file or
9898- without. Each listener has its own password file, and different
9999- listeners may use different password files. Password file
100100- generation can be disabled by setting
101101- <literal>omitPasswordAuth = true</literal> for a listener; in
102102- this case it is necessary to either set
103103- <literal>settings.allow_anonymous = true</literal> to allow all
104104- logins, or to configure other authentication methods like TLS
105105- client certificates with
106106- <literal>settings.use_identity_as_username = true</literal>.
107107- </para>
108108- <para>
109109- The default is to generate a password file for each listener
110110- from the users configured to that listener. Users with no
111111- configured password will not be added to the password file and
112112- thus will not be able to use the broker.
113113- </para>
114114- </section>
115115- <section xml:id="module-services-mosquitto-config-acl">
116116- <title>ACL format</title>
117117- <para>
118118- Every listener has a Mosquitto <literal>acl_file</literal>
119119- attached to it. This ACL is configured via two attributes of the
120120- config:
121121- </para>
122122- <itemizedlist spacing="compact">
123123- <listitem>
124124- <para>
125125- the <literal>acl</literal> attribute of the listener
126126- configures pattern ACL entries and topic ACL entries for
127127- anonymous users. Each entry must be prefixed with
128128- <literal>pattern</literal> or <literal>topic</literal> to
129129- distinguish between these two cases.
130130- </para>
131131- </listitem>
132132- <listitem>
133133- <para>
134134- the <literal>acl</literal> attribute of every user
135135- configures in the listener configured the ACL for that given
136136- user. Only topic ACLs are supported by Mosquitto in this
137137- setting, so no prefix is required or allowed.
138138- </para>
139139- </listitem>
140140- </itemizedlist>
141141- <para>
142142- The default ACL for a listener is empty, disallowing all
143143- accesses from all clients. To configure a completely open ACL,
144144- set <literal>acl = [ "pattern readwrite #" ]</literal>
145145- in the listener.
146146- </para>
147147- </section>
148148- </section>
149149-</chapter>
···11-<!-- Do not edit this file directly, edit its companion .md instead
22- and regenerate this file using nixos/doc/manual/md-to-db.sh -->
33-<chapter xmlns="http://docbook.org/ns/docbook" xmlns:xlink="http://www.w3.org/1999/xlink" xml:id="module-services-pleroma">
44- <title>Pleroma</title>
55- <para>
66- <link xlink:href="https://pleroma.social/">Pleroma</link> is a
77- lightweight activity pub server.
88- </para>
99- <section xml:id="module-services-pleroma-generate-config">
1010- <title>Generating the Pleroma config</title>
1111- <para>
1212- The <literal>pleroma_ctl</literal> CLI utility will prompt you
1313- some questions and it will generate an initial config file. This
1414- is an example of usage
1515- </para>
1616- <programlisting>
1717-$ mkdir tmp-pleroma
1818-$ cd tmp-pleroma
1919-$ nix-shell -p pleroma-otp
2020-$ pleroma_ctl instance gen --output config.exs --output-psql setup.psql
2121-</programlisting>
2222- <para>
2323- The <literal>config.exs</literal> file can be further customized
2424- following the instructions on the
2525- <link xlink:href="https://docs-develop.pleroma.social/backend/configuration/cheatsheet/">upstream
2626- documentation</link>. Many refinements can be applied also after
2727- the service is running.
2828- </para>
2929- </section>
3030- <section xml:id="module-services-pleroma-initialize-db">
3131- <title>Initializing the database</title>
3232- <para>
3333- First, the Postgresql service must be enabled in the NixOS
3434- configuration
3535- </para>
3636- <programlisting>
3737-services.postgresql = {
3838- enable = true;
3939- package = pkgs.postgresql_13;
4040-};
4141-</programlisting>
4242- <para>
4343- and activated with the usual
4444- </para>
4545- <programlisting>
4646-$ nixos-rebuild switch
4747-</programlisting>
4848- <para>
4949- Then you can create and seed the database, using the
5050- <literal>setup.psql</literal> file that you generated in the
5151- previous section, by running
5252- </para>
5353- <programlisting>
5454-$ sudo -u postgres psql -f setup.psql
5555-</programlisting>
5656- </section>
5757- <section xml:id="module-services-pleroma-enable">
5858- <title>Enabling the Pleroma service locally</title>
5959- <para>
6060- In this section we will enable the Pleroma service only locally,
6161- so its configurations can be improved incrementally.
6262- </para>
6363- <para>
6464- This is an example of configuration, where
6565- <xref linkend="opt-services.pleroma.configs" /> option contains
6666- the content of the file <literal>config.exs</literal>, generated
6767- <link linkend="module-services-pleroma-generate-config">in the
6868- first section</link>, but with the secrets (database password,
6969- endpoint secret key, salts, etc.) removed. Removing secrets is
7070- important, because otherwise they will be stored publicly in the
7171- Nix store.
7272- </para>
7373- <programlisting>
7474-services.pleroma = {
7575- enable = true;
7676- secretConfigFile = "/var/lib/pleroma/secrets.exs";
7777- configs = [
7878- ''
7979- import Config
8080-8181- config :pleroma, Pleroma.Web.Endpoint,
8282- url: [host: "pleroma.example.net", scheme: "https", port: 443],
8383- http: [ip: {127, 0, 0, 1}, port: 4000]
8484-8585- config :pleroma, :instance,
8686- name: "Test",
8787- email: "admin@example.net",
8888- notify_email: "admin@example.net",
8989- limit: 5000,
9090- registrations_open: true
9191-9292- config :pleroma, :media_proxy,
9393- enabled: false,
9494- redirect_on_failure: true
9595-9696- config :pleroma, Pleroma.Repo,
9797- adapter: Ecto.Adapters.Postgres,
9898- username: "pleroma",
9999- database: "pleroma",
100100- hostname: "localhost"
101101-102102- # Configure web push notifications
103103- config :web_push_encryption, :vapid_details,
104104- subject: "mailto:admin@example.net"
105105-106106- # ... TO CONTINUE ...
107107- ''
108108- ];
109109-};
110110-</programlisting>
111111- <para>
112112- Secrets must be moved into a file pointed by
113113- <xref linkend="opt-services.pleroma.secretConfigFile" />, in our
114114- case <literal>/var/lib/pleroma/secrets.exs</literal>. This file
115115- can be created copying the previously generated
116116- <literal>config.exs</literal> file and then removing all the
117117- settings, except the secrets. This is an example
118118- </para>
119119- <programlisting>
120120-# Pleroma instance passwords
121121-122122-import Config
123123-124124-config :pleroma, Pleroma.Web.Endpoint,
125125- secret_key_base: "<the secret generated by pleroma_ctl>",
126126- signing_salt: "<the secret generated by pleroma_ctl>"
127127-128128-config :pleroma, Pleroma.Repo,
129129- password: "<the secret generated by pleroma_ctl>"
130130-131131-# Configure web push notifications
132132-config :web_push_encryption, :vapid_details,
133133- public_key: "<the secret generated by pleroma_ctl>",
134134- private_key: "<the secret generated by pleroma_ctl>"
135135-136136-# ... TO CONTINUE ...
137137-</programlisting>
138138- <para>
139139- Note that the lines of the same configuration group are comma
140140- separated (i.e. all the lines end with a comma, except the last
141141- one), so when the lines with passwords are added or removed,
142142- commas must be adjusted accordingly.
143143- </para>
144144- <para>
145145- The service can be enabled with the usual
146146- </para>
147147- <programlisting>
148148-$ nixos-rebuild switch
149149-</programlisting>
150150- <para>
151151- The service is accessible only from the local
152152- <literal>127.0.0.1:4000</literal> port. It can be tested using a
153153- port forwarding like this
154154- </para>
155155- <programlisting>
156156-$ ssh -L 4000:localhost:4000 myuser@example.net
157157-</programlisting>
158158- <para>
159159- and then accessing
160160- <link xlink:href="http://localhost:4000">http://localhost:4000</link>
161161- from a web browser.
162162- </para>
163163- </section>
164164- <section xml:id="module-services-pleroma-admin-user">
165165- <title>Creating the admin user</title>
166166- <para>
167167- After Pleroma service is running, all
168168- <link xlink:href="https://docs-develop.pleroma.social/">Pleroma
169169- administration utilities</link> can be used. In particular an
170170- admin user can be created with
171171- </para>
172172- <programlisting>
173173-$ pleroma_ctl user new <nickname> <email> --admin --moderator --password <password>
174174-</programlisting>
175175- </section>
176176- <section xml:id="module-services-pleroma-nginx">
177177- <title>Configuring Nginx</title>
178178- <para>
179179- In this configuration, Pleroma is listening only on the local port
180180- 4000. Nginx can be configured as a Reverse Proxy, for forwarding
181181- requests from public ports to the Pleroma service. This is an
182182- example of configuration, using
183183- <link xlink:href="https://letsencrypt.org/">Let’s Encrypt</link>
184184- for the TLS certificates
185185- </para>
186186- <programlisting>
187187-security.acme = {
188188- email = "root@example.net";
189189- acceptTerms = true;
190190-};
191191-192192-services.nginx = {
193193- enable = true;
194194- addSSL = true;
195195-196196- recommendedTlsSettings = true;
197197- recommendedOptimisation = true;
198198- recommendedGzipSettings = true;
199199-200200- recommendedProxySettings = false;
201201- # NOTE: if enabled, the NixOS proxy optimizations will override the Pleroma
202202- # specific settings, and they will enter in conflict.
203203-204204- virtualHosts = {
205205- "pleroma.example.net" = {
206206- http2 = true;
207207- enableACME = true;
208208- forceSSL = true;
209209-210210- locations."/" = {
211211- proxyPass = "http://127.0.0.1:4000";
212212-213213- extraConfig = ''
214214- etag on;
215215- gzip on;
216216-217217- add_header 'Access-Control-Allow-Origin' '*' always;
218218- add_header 'Access-Control-Allow-Methods' 'POST, PUT, DELETE, GET, PATCH, OPTIONS' always;
219219- add_header 'Access-Control-Allow-Headers' 'Authorization, Content-Type, Idempotency-Key' always;
220220- add_header 'Access-Control-Expose-Headers' 'Link, X-RateLimit-Reset, X-RateLimit-Limit, X-RateLimit-Remaining, X-Request-Id' always;
221221- if ($request_method = OPTIONS) {
222222- return 204;
223223- }
224224- add_header X-XSS-Protection "1; mode=block";
225225- add_header X-Permitted-Cross-Domain-Policies none;
226226- add_header X-Frame-Options DENY;
227227- add_header X-Content-Type-Options nosniff;
228228- add_header Referrer-Policy same-origin;
229229- add_header X-Download-Options noopen;
230230- proxy_http_version 1.1;
231231- proxy_set_header Upgrade $http_upgrade;
232232- proxy_set_header Connection "upgrade";
233233- proxy_set_header Host $host;
234234-235235- client_max_body_size 16m;
236236- # NOTE: increase if users need to upload very big files
237237- '';
238238- };
239239- };
240240- };
241241-};
242242-</programlisting>
243243- </section>
244244-</chapter>
···11-<!-- Do not edit this file directly, edit its companion .md instead
22- and regenerate this file using nixos/doc/manual/md-to-db.sh -->
33-<chapter xmlns="http://docbook.org/ns/docbook" xmlns:xlink="http://www.w3.org/1999/xlink" xml:id="module-services-prosody">
44- <title>Prosody</title>
55- <para>
66- <link xlink:href="https://prosody.im/">Prosody</link> is an
77- open-source, modern XMPP server.
88- </para>
99- <section xml:id="module-services-prosody-basic-usage">
1010- <title>Basic usage</title>
1111- <para>
1212- A common struggle for most XMPP newcomers is to find the right set
1313- of XMPP Extensions (XEPs) to setup. Forget to activate a few of
1414- those and your XMPP experience might turn into a nightmare!
1515- </para>
1616- <para>
1717- The XMPP community tackles this problem by creating a meta-XEP
1818- listing a decent set of XEPs you should implement. This meta-XEP
1919- is issued every year, the 2020 edition being
2020- <link xlink:href="https://xmpp.org/extensions/xep-0423.html">XEP-0423</link>.
2121- </para>
2222- <para>
2323- The NixOS Prosody module will implement most of these recommendend
2424- XEPs out of the box. That being said, two components still require
2525- some manual configuration: the
2626- <link xlink:href="https://xmpp.org/extensions/xep-0045.html">Multi
2727- User Chat (MUC)</link> and the
2828- <link xlink:href="https://xmpp.org/extensions/xep-0363.html">HTTP
2929- File Upload</link> ones. You’ll need to create a DNS subdomain for
3030- each of those. The current convention is to name your MUC endpoint
3131- <literal>conference.example.org</literal> and your HTTP upload
3232- domain <literal>upload.example.org</literal>.
3333- </para>
3434- <para>
3535- A good configuration to start with, including a
3636- <link xlink:href="https://xmpp.org/extensions/xep-0045.html">Multi
3737- User Chat (MUC)</link> endpoint as well as a
3838- <link xlink:href="https://xmpp.org/extensions/xep-0363.html">HTTP
3939- File Upload</link> endpoint will look like this:
4040- </para>
4141- <programlisting>
4242-services.prosody = {
4343- enable = true;
4444- admins = [ "root@example.org" ];
4545- ssl.cert = "/var/lib/acme/example.org/fullchain.pem";
4646- ssl.key = "/var/lib/acme/example.org/key.pem";
4747- virtualHosts."example.org" = {
4848- enabled = true;
4949- domain = "example.org";
5050- ssl.cert = "/var/lib/acme/example.org/fullchain.pem";
5151- ssl.key = "/var/lib/acme/example.org/key.pem";
5252- };
5353- muc = [ {
5454- domain = "conference.example.org";
5555- } ];
5656- uploadHttp = {
5757- domain = "upload.example.org";
5858- };
5959-};
6060-</programlisting>
6161- </section>
6262- <section xml:id="module-services-prosody-letsencrypt">
6363- <title>Let’s Encrypt Configuration</title>
6464- <para>
6565- As you can see in the code snippet from the
6666- <link linkend="module-services-prosody-basic-usage">previous
6767- section</link>, you’ll need a single TLS certificate covering your
6868- main endpoint, the MUC one as well as the HTTP Upload one. We can
6969- generate such a certificate by leveraging the ACME
7070- <link linkend="opt-security.acme.certs._name_.extraDomainNames">extraDomainNames</link>
7171- module option.
7272- </para>
7373- <para>
7474- Provided the setup detailed in the previous section, you’ll need
7575- the following acme configuration to generate a TLS certificate for
7676- the three endponits:
7777- </para>
7878- <programlisting>
7979-security.acme = {
8080- email = "root@example.org";
8181- acceptTerms = true;
8282- certs = {
8383- "example.org" = {
8484- webroot = "/var/www/example.org";
8585- email = "root@example.org";
8686- extraDomainNames = [ "conference.example.org" "upload.example.org" ];
8787- };
8888- };
8989-};
9090-</programlisting>
9191- </section>
9292-</chapter>
···11-<!-- Do not edit this file directly, edit its companion .md instead
22- and regenerate this file using nixos/doc/manual/md-to-db.sh -->
33-<chapter xmlns="http://docbook.org/ns/docbook" xmlns:xlink="http://www.w3.org/1999/xlink" xml:id="module-services-meilisearch">
44- <title>Meilisearch</title>
55- <para>
66- Meilisearch is a lightweight, fast and powerful search engine. Think
77- elastic search with a much smaller footprint.
88- </para>
99- <section xml:id="module-services-meilisearch-quickstart">
1010- <title>Quickstart</title>
1111- <para>
1212- the minimum to start meilisearch is
1313- </para>
1414- <programlisting language="nix">
1515-services.meilisearch.enable = true;
1616-</programlisting>
1717- <para>
1818- this will start the http server included with meilisearch on port
1919- 7700.
2020- </para>
2121- <para>
2222- test with
2323- <literal>curl -X GET 'http://localhost:7700/health'</literal>
2424- </para>
2525- </section>
2626- <section xml:id="module-services-meilisearch-usage">
2727- <title>Usage</title>
2828- <para>
2929- you first need to add documents to an index before you can search
3030- for documents.
3131- </para>
3232- <section xml:id="module-services-meilisearch-quickstart-add">
3333- <title>Add a documents to the <literal>movies</literal>
3434- index</title>
3535- <para>
3636- <literal>curl -X POST 'http://127.0.0.1:7700/indexes/movies/documents' --data '[{"id": "123", "title": "Superman"}, {"id": 234, "title": "Batman"}]'</literal>
3737- </para>
3838- </section>
3939- <section xml:id="module-services-meilisearch-quickstart-search">
4040- <title>Search documents in the <literal>movies</literal>
4141- index</title>
4242- <para>
4343- <literal>curl 'http://127.0.0.1:7700/indexes/movies/search' --data '{ "q": "botman" }'</literal>
4444- (note the typo is intentional and there to demonstrate the typo
4545- tolerant capabilities)
4646- </para>
4747- </section>
4848- </section>
4949- <section xml:id="module-services-meilisearch-defaults">
5050- <title>Defaults</title>
5151- <itemizedlist>
5252- <listitem>
5353- <para>
5454- The default nixos package doesn’t come with the
5555- <link xlink:href="https://docs.meilisearch.com/learn/getting_started/quick_start.html#search">dashboard</link>,
5656- since the dashboard features makes some assets downloads at
5757- compile time.
5858- </para>
5959- </listitem>
6060- <listitem>
6161- <para>
6262- Anonimized Analytics sent to meilisearch are disabled by
6363- default.
6464- </para>
6565- </listitem>
6666- <listitem>
6767- <para>
6868- Default deployment is development mode. It doesn’t require a
6969- secret master key. All routes are not protected and
7070- accessible.
7171- </para>
7272- </listitem>
7373- </itemizedlist>
7474- </section>
7575- <section xml:id="module-services-meilisearch-missing">
7676- <title>Missing</title>
7777- <itemizedlist spacing="compact">
7878- <listitem>
7979- <para>
8080- the snapshot feature is not yet configurable from the module,
8181- it’s just a matter of adding the relevant environment
8282- variables.
8383- </para>
8484- </listitem>
8585- </itemizedlist>
8686- </section>
8787-</chapter>
···11-<!-- Do not edit this file directly, edit its companion .md instead
22- and regenerate this file using nixos/doc/manual/md-to-db.sh -->
33-<chapter xmlns="http://docbook.org/ns/docbook" xmlns:xlink="http://www.w3.org/1999/xlink" xml:id="module-services-akkoma">
44- <title>Akkoma</title>
55- <para>
66- <link xlink:href="https://akkoma.dev/">Akkoma</link> is a
77- lightweight ActivityPub microblogging server forked from Pleroma.
88- </para>
99- <section xml:id="modules-services-akkoma-service-configuration">
1010- <title>Service configuration</title>
1111- <para>
1212- The Elixir configuration file required by Akkoma is generated
1313- automatically from
1414- <link xlink:href="options.html#opt-services.akkoma.config"><option>services.akkoma.config</option></link>.
1515- Secrets must be included from external files outside of the Nix
1616- store by setting the configuration option to an attribute set
1717- containing the attribute <option>_secret</option> – a string
1818- pointing to the file containing the actual value of the option.
1919- </para>
2020- <para>
2121- For the mandatory configuration settings these secrets will be
2222- generated automatically if the referenced file does not exist
2323- during startup, unless disabled through
2424- <link xlink:href="options.html#opt-services.akkoma.initSecrets"><option>services.akkoma.initSecrets</option></link>.
2525- </para>
2626- <para>
2727- The following configuration binds Akkoma to the Unix socket
2828- <literal>/run/akkoma/socket</literal>, expecting to be run behind
2929- a HTTP proxy on <literal>fediverse.example.com</literal>.
3030- </para>
3131- <programlisting language="nix">
3232-services.akkoma.enable = true;
3333-services.akkoma.config = {
3434- ":pleroma" = {
3535- ":instance" = {
3636- name = "My Akkoma instance";
3737- description = "More detailed description";
3838- email = "admin@example.com";
3939- registration_open = false;
4040- };
4141-4242- "Pleroma.Web.Endpoint" = {
4343- url.host = "fediverse.example.com";
4444- };
4545- };
4646-};
4747-</programlisting>
4848- <para>
4949- Please refer to the
5050- <link xlink:href="https://docs.akkoma.dev/stable/configuration/cheatsheet/">configuration
5151- cheat sheet</link> for additional configuration options.
5252- </para>
5353- </section>
5454- <section xml:id="modules-services-akkoma-user-management">
5555- <title>User management</title>
5656- <para>
5757- After the Akkoma service is running, the administration utility
5858- can be used to
5959- <link xlink:href="https://docs.akkoma.dev/stable/administration/CLI_tasks/user/">manage
6060- users</link>. In particular an administrative user can be created
6161- with
6262- </para>
6363- <programlisting>
6464-$ pleroma_ctl user new <nickname> <email> --admin --moderator --password <password>
6565-</programlisting>
6666- </section>
6767- <section xml:id="modules-services-akkoma-proxy-configuration">
6868- <title>Proxy configuration</title>
6969- <para>
7070- Although it is possible to expose Akkoma directly, it is common
7171- practice to operate it behind an HTTP reverse proxy such as nginx.
7272- </para>
7373- <programlisting language="nix">
7474-services.akkoma.nginx = {
7575- enableACME = true;
7676- forceSSL = true;
7777-};
7878-7979-services.nginx = {
8080- enable = true;
8181-8282- clientMaxBodySize = "16m";
8383- recommendedTlsSettings = true;
8484- recommendedOptimisation = true;
8585- recommendedGzipSettings = true;
8686-};
8787-</programlisting>
8888- <para>
8989- Please refer to <xref linkend="module-security-acme" /> for
9090- details on how to provision an SSL/TLS certificate.
9191- </para>
9292- <section xml:id="modules-services-akkoma-media-proxy">
9393- <title>Media proxy</title>
9494- <para>
9595- Without the media proxy function, Akkoma does not store any
9696- remote media like pictures or video locally, and clients have to
9797- fetch them directly from the source server.
9898- </para>
9999- <programlisting language="nix">
100100-# Enable nginx slice module distributed with Tengine
101101-services.nginx.package = pkgs.tengine;
102102-103103-# Enable media proxy
104104-services.akkoma.config.":pleroma".":media_proxy" = {
105105- enabled = true;
106106- proxy_opts.redirect_on_failure = true;
107107-};
108108-109109-# Adjust the persistent cache size as needed:
110110-# Assuming an average object size of 128 KiB, around 1 MiB
111111-# of memory is required for the key zone per GiB of cache.
112112-# Ensure that the cache directory exists and is writable by nginx.
113113-services.nginx.commonHttpConfig = ''
114114- proxy_cache_path /var/cache/nginx/cache/akkoma-media-cache
115115- levels= keys_zone=akkoma_media_cache:16m max_size=16g
116116- inactive=1y use_temp_path=off;
117117-'';
118118-119119-services.akkoma.nginx = {
120120- locations."/proxy" = {
121121- proxyPass = "http://unix:/run/akkoma/socket";
122122-123123- extraConfig = ''
124124- proxy_cache akkoma_media_cache;
125125-126126- # Cache objects in slices of 1 MiB
127127- slice 1m;
128128- proxy_cache_key $host$uri$is_args$args$slice_range;
129129- proxy_set_header Range $slice_range;
130130-131131- # Decouple proxy and upstream responses
132132- proxy_buffering on;
133133- proxy_cache_lock on;
134134- proxy_ignore_client_abort on;
135135-136136- # Default cache times for various responses
137137- proxy_cache_valid 200 1y;
138138- proxy_cache_valid 206 301 304 1h;
139139-140140- # Allow serving of stale items
141141- proxy_cache_use_stale error timeout invalid_header updating;
142142- '';
143143- };
144144-};
145145-</programlisting>
146146- <section xml:id="modules-services-akkoma-prefetch-remote-media">
147147- <title>Prefetch remote media</title>
148148- <para>
149149- The following example enables the
150150- <literal>MediaProxyWarmingPolicy</literal> MRF policy which
151151- automatically fetches all media associated with a post through
152152- the media proxy, as soon as the post is received by the
153153- instance.
154154- </para>
155155- <programlisting language="nix">
156156-services.akkoma.config.":pleroma".":mrf".policies =
157157- map (pkgs.formats.elixirConf { }).lib.mkRaw [
158158- "Pleroma.Web.ActivityPub.MRF.MediaProxyWarmingPolicy"
159159-];
160160-</programlisting>
161161- </section>
162162- <section xml:id="modules-services-akkoma-media-previews">
163163- <title>Media previews</title>
164164- <para>
165165- Akkoma can generate previews for media.
166166- </para>
167167- <programlisting language="nix">
168168-services.akkoma.config.":pleroma".":media_preview_proxy" = {
169169- enabled = true;
170170- thumbnail_max_width = 1920;
171171- thumbnail_max_height = 1080;
172172-};
173173-</programlisting>
174174- </section>
175175- </section>
176176- </section>
177177- <section xml:id="modules-services-akkoma-frontend-management">
178178- <title>Frontend management</title>
179179- <para>
180180- Akkoma will be deployed with the <literal>pleroma-fe</literal> and
181181- <literal>admin-fe</literal> frontends by default. These can be
182182- modified by setting
183183- <link xlink:href="options.html#opt-services.akkoma.frontends"><option>services.akkoma.frontends</option></link>.
184184- </para>
185185- <para>
186186- The following example overrides the primary frontend’s default
187187- configuration using a custom derivation.
188188- </para>
189189- <programlisting language="nix">
190190-services.akkoma.frontends.primary.package = pkgs.runCommand "pleroma-fe" {
191191- config = builtins.toJSON {
192192- expertLevel = 1;
193193- collapseMessageWithSubject = false;
194194- stopGifs = false;
195195- replyVisibility = "following";
196196- webPushHideIfCW = true;
197197- hideScopeNotice = true;
198198- renderMisskeyMarkdown = false;
199199- hideSiteFavicon = true;
200200- postContentType = "text/markdown";
201201- showNavShortcuts = false;
202202- };
203203- nativeBuildInputs = with pkgs; [ jq xorg.lndir ];
204204- passAsFile = [ "config" ];
205205-} ''
206206- mkdir $out
207207- lndir ${pkgs.akkoma-frontends.pleroma-fe} $out
208208-209209- rm $out/static/config.json
210210- jq -s add ${pkgs.akkoma-frontends.pleroma-fe}/static/config.json ${config} \
211211- >$out/static/config.json
212212-'';
213213-</programlisting>
214214- </section>
215215- <section xml:id="modules-services-akkoma-federation-policies">
216216- <title>Federation policies</title>
217217- <para>
218218- Akkoma comes with a number of modules to police federation with
219219- other ActivityPub instances. The most valuable for typical users
220220- is the
221221- <link xlink:href="https://docs.akkoma.dev/stable/configuration/cheatsheet/#mrf_simple"><literal>:mrf_simple</literal></link>
222222- module which allows limiting federation based on instance
223223- hostnames.
224224- </para>
225225- <para>
226226- This configuration snippet provides an example on how these can be
227227- used. Choosing an adequate federation policy is not trivial and
228228- entails finding a balance between connectivity to the rest of the
229229- fediverse and providing a pleasant experience to the users of an
230230- instance.
231231- </para>
232232- <programlisting language="nix">
233233-services.akkoma.config.":pleroma" = with (pkgs.formats.elixirConf { }).lib; {
234234- ":mrf".policies = map mkRaw [
235235- "Pleroma.Web.ActivityPub.MRF.SimplePolicy"
236236- ];
237237-238238- ":mrf_simple" = {
239239- # Tag all media as sensitive
240240- media_nsfw = mkMap {
241241- "nsfw.weird.kinky" = "Untagged NSFW content";
242242- };
243243-244244- # Reject all activities except deletes
245245- reject = mkMap {
246246- "kiwifarms.cc" = "Persistent harassment of users, no moderation";
247247- };
248248-249249- # Force posts to be visible by followers only
250250- followers_only = mkMap {
251251- "beta.birdsite.live" = "Avoid polluting timelines with Twitter posts";
252252- };
253253- };
254254-};
255255-</programlisting>
256256- </section>
257257- <section xml:id="modules-services-akkoma-upload-filters">
258258- <title>Upload filters</title>
259259- <para>
260260- This example strips GPS and location metadata from uploads,
261261- deduplicates them and anonymises the the file name.
262262- </para>
263263- <programlisting language="nix">
264264-services.akkoma.config.":pleroma"."Pleroma.Upload".filters =
265265- map (pkgs.formats.elixirConf { }).lib.mkRaw [
266266- "Pleroma.Upload.Filter.Exiftool"
267267- "Pleroma.Upload.Filter.Dedupe"
268268- "Pleroma.Upload.Filter.AnonymizeFilename"
269269- ];
270270-</programlisting>
271271- </section>
272272- <section xml:id="modules-services-akkoma-migration-pleroma">
273273- <title>Migration from Pleroma</title>
274274- <para>
275275- Pleroma instances can be migrated to Akkoma either by copying the
276276- database and upload data or by pointing Akkoma to the existing
277277- data. The necessary database migrations are run automatically
278278- during startup of the service.
279279- </para>
280280- <para>
281281- The configuration has to be copy‐edited manually.
282282- </para>
283283- <para>
284284- Depending on the size of the database, the initial migration may
285285- take a long time and exceed the startup timeout of the system
286286- manager. To work around this issue one may adjust the startup
287287- timeout
288288- <option>systemd.services.akkoma.serviceConfig.TimeoutStartSec</option>
289289- or simply run the migrations manually:
290290- </para>
291291- <programlisting>
292292-pleroma_ctl migrate
293293-</programlisting>
294294- <section xml:id="modules-services-akkoma-migration-pleroma-copy">
295295- <title>Copying data</title>
296296- <para>
297297- Copying the Pleroma data instead of re‐using it in place may
298298- permit easier reversion to Pleroma, but allows the two data sets
299299- to diverge.
300300- </para>
301301- <para>
302302- First disable Pleroma and then copy its database and upload
303303- data:
304304- </para>
305305- <programlisting>
306306-# Create a copy of the database
307307-nix-shell -p postgresql --run 'createdb -T pleroma akkoma'
308308-309309-# Copy upload data
310310-mkdir /var/lib/akkoma
311311-cp -R --reflink=auto /var/lib/pleroma/uploads /var/lib/akkoma/
312312-</programlisting>
313313- <para>
314314- After the data has been copied, enable the Akkoma service and
315315- verify that the migration has been successful. If no longer
316316- required, the original data may then be deleted:
317317- </para>
318318- <programlisting>
319319-# Delete original database
320320-nix-shell -p postgresql --run 'dropdb pleroma'
321321-322322-# Delete original Pleroma state
323323-rm -r /var/lib/pleroma
324324-</programlisting>
325325- </section>
326326- <section xml:id="modules-services-akkoma-migration-pleroma-reuse">
327327- <title>Re‐using data</title>
328328- <para>
329329- To re‐use the Pleroma data in place, disable Pleroma and enable
330330- Akkoma, pointing it to the Pleroma database and upload
331331- directory.
332332- </para>
333333- <programlisting language="nix">
334334-# Adjust these settings according to the database name and upload directory path used by Pleroma
335335-services.akkoma.config.":pleroma"."Pleroma.Repo".database = "pleroma";
336336-services.akkoma.config.":pleroma".":instance".upload_dir = "/var/lib/pleroma/uploads";
337337-</programlisting>
338338- <para>
339339- Please keep in mind that after the Akkoma service has been
340340- started, any migrations applied by Akkoma have to be rolled back
341341- before the database can be used again with Pleroma. This can be
342342- achieved through <literal>pleroma_ctl ecto.rollback</literal>.
343343- Refer to the
344344- <link xlink:href="https://hexdocs.pm/ecto_sql/Mix.Tasks.Ecto.Rollback.html">Ecto
345345- SQL documentation</link> for details.
346346- </para>
347347- </section>
348348- </section>
349349- <section xml:id="modules-services-akkoma-advanced-deployment">
350350- <title>Advanced deployment options</title>
351351- <section xml:id="modules-services-akkoma-confinement">
352352- <title>Confinement</title>
353353- <para>
354354- The Akkoma systemd service may be confined to a chroot with
355355- </para>
356356- <programlisting language="nix">
357357-services.systemd.akkoma.confinement.enable = true;
358358-</programlisting>
359359- <para>
360360- Confinement of services is not generally supported in NixOS and
361361- therefore disabled by default. Depending on the Akkoma
362362- configuration, the default confinement settings may be
363363- insufficient and lead to subtle errors at run time, requiring
364364- adjustment:
365365- </para>
366366- <para>
367367- Use
368368- <link xlink:href="options.html#opt-systemd.services._name_.confinement.packages"><option>services.systemd.akkoma.confinement.packages</option></link>
369369- to make packages available in the chroot.
370370- </para>
371371- <para>
372372- <option>services.systemd.akkoma.serviceConfig.BindPaths</option>
373373- and
374374- <option>services.systemd.akkoma.serviceConfig.BindReadOnlyPaths</option>
375375- permit access to outside paths through bind mounts. Refer to
376376- <link xlink:href="https://www.freedesktop.org/software/systemd/man/systemd.exec.html#BindPaths="><citerefentry><refentrytitle>systemd.exec</refentrytitle><manvolnum>5</manvolnum></citerefentry></link>
377377- for details.
378378- </para>
379379- </section>
380380- <section xml:id="modules-services-akkoma-distributed-deployment">
381381- <title>Distributed deployment</title>
382382- <para>
383383- Being an Elixir application, Akkoma can be deployed in a
384384- distributed fashion.
385385- </para>
386386- <para>
387387- This requires setting
388388- <link xlink:href="options.html#opt-services.akkoma.dist.address"><option>services.akkoma.dist.address</option></link>
389389- and
390390- <link xlink:href="options.html#opt-services.akkoma.dist.cookie"><option>services.akkoma.dist.cookie</option></link>.
391391- The specifics depend strongly on the deployment environment. For
392392- more information please check the relevant
393393- <link xlink:href="https://www.erlang.org/doc/reference_manual/distributed.html">Erlang
394394- documentation</link>.
395395- </para>
396396- </section>
397397- </section>
398398-</chapter>
···11-<!-- Do not edit this file directly, edit its companion .md instead
22- and regenerate this file using nixos/doc/manual/md-to-db.sh -->
33-<chapter xmlns="http://docbook.org/ns/docbook" xmlns:xlink="http://www.w3.org/1999/xlink" xml:id="module-services-discourse">
44- <title>Discourse</title>
55- <para>
66- <link xlink:href="https://www.discourse.org/">Discourse</link> is a
77- modern and open source discussion platform.
88- </para>
99- <section xml:id="module-services-discourse-basic-usage">
1010- <title>Basic usage</title>
1111- <para>
1212- A minimal configuration using Let’s Encrypt for TLS certificates
1313- looks like this:
1414- </para>
1515- <programlisting>
1616-services.discourse = {
1717- enable = true;
1818- hostname = "discourse.example.com";
1919- admin = {
2020- email = "admin@example.com";
2121- username = "admin";
2222- fullName = "Administrator";
2323- passwordFile = "/path/to/password_file";
2424- };
2525- secretKeyBaseFile = "/path/to/secret_key_base_file";
2626-};
2727-security.acme.email = "me@example.com";
2828-security.acme.acceptTerms = true;
2929-</programlisting>
3030- <para>
3131- Provided a proper DNS setup, you’ll be able to connect to the
3232- instance at <literal>discourse.example.com</literal> and log in
3333- using the credentials provided in
3434- <literal>services.discourse.admin</literal>.
3535- </para>
3636- </section>
3737- <section xml:id="module-services-discourse-tls">
3838- <title>Using a regular TLS certificate</title>
3939- <para>
4040- To set up TLS using a regular certificate and key on file, use the
4141- <xref linkend="opt-services.discourse.sslCertificate" /> and
4242- <xref linkend="opt-services.discourse.sslCertificateKey" />
4343- options:
4444- </para>
4545- <programlisting>
4646-services.discourse = {
4747- enable = true;
4848- hostname = "discourse.example.com";
4949- sslCertificate = "/path/to/ssl_certificate";
5050- sslCertificateKey = "/path/to/ssl_certificate_key";
5151- admin = {
5252- email = "admin@example.com";
5353- username = "admin";
5454- fullName = "Administrator";
5555- passwordFile = "/path/to/password_file";
5656- };
5757- secretKeyBaseFile = "/path/to/secret_key_base_file";
5858-};
5959-</programlisting>
6060- </section>
6161- <section xml:id="module-services-discourse-database">
6262- <title>Database access</title>
6363- <para>
6464- Discourse uses PostgreSQL to store most of its data. A database
6565- will automatically be enabled and a database and role created
6666- unless <xref linkend="opt-services.discourse.database.host" /> is
6767- changed from its default of <literal>null</literal> or
6868- <xref linkend="opt-services.discourse.database.createLocally" />
6969- is set to <literal>false</literal>.
7070- </para>
7171- <para>
7272- External database access can also be configured by setting
7373- <xref linkend="opt-services.discourse.database.host" />,
7474- <xref linkend="opt-services.discourse.database.username" /> and
7575- <xref linkend="opt-services.discourse.database.passwordFile" /> as
7676- appropriate. Note that you need to manually create a database
7777- called <literal>discourse</literal> (or the name you chose in
7878- <xref linkend="opt-services.discourse.database.name" />) and allow
7979- the configured database user full access to it.
8080- </para>
8181- </section>
8282- <section xml:id="module-services-discourse-mail">
8383- <title>Email</title>
8484- <para>
8585- In addition to the basic setup, you’ll want to configure an SMTP
8686- server Discourse can use to send user registration and password
8787- reset emails, among others. You can also optionally let Discourse
8888- receive email, which enables people to reply to threads and
8989- conversations via email.
9090- </para>
9191- <para>
9292- A basic setup which assumes you want to use your configured
9393- <link linkend="opt-services.discourse.hostname">hostname</link> as
9494- email domain can be done like this:
9595- </para>
9696- <programlisting>
9797-services.discourse = {
9898- enable = true;
9999- hostname = "discourse.example.com";
100100- sslCertificate = "/path/to/ssl_certificate";
101101- sslCertificateKey = "/path/to/ssl_certificate_key";
102102- admin = {
103103- email = "admin@example.com";
104104- username = "admin";
105105- fullName = "Administrator";
106106- passwordFile = "/path/to/password_file";
107107- };
108108- mail.outgoing = {
109109- serverAddress = "smtp.emailprovider.com";
110110- port = 587;
111111- username = "user@emailprovider.com";
112112- passwordFile = "/path/to/smtp_password_file";
113113- };
114114- mail.incoming.enable = true;
115115- secretKeyBaseFile = "/path/to/secret_key_base_file";
116116-};
117117-</programlisting>
118118- <para>
119119- This assumes you have set up an MX record for the address you’ve
120120- set in
121121- <link linkend="opt-services.discourse.hostname">hostname</link>
122122- and requires proper SPF, DKIM and DMARC configuration to be done
123123- for the domain you’re sending from, in order for email to be
124124- reliably delivered.
125125- </para>
126126- <para>
127127- If you want to use a different domain for your outgoing email (for
128128- example <literal>example.com</literal> instead of
129129- <literal>discourse.example.com</literal>) you should set
130130- <xref linkend="opt-services.discourse.mail.notificationEmailAddress" />
131131- and
132132- <xref linkend="opt-services.discourse.mail.contactEmailAddress" />
133133- manually.
134134- </para>
135135- <note>
136136- <para>
137137- Setup of TLS for incoming email is currently only configured
138138- automatically when a regular TLS certificate is used, i.e. when
139139- <xref linkend="opt-services.discourse.sslCertificate" /> and
140140- <xref linkend="opt-services.discourse.sslCertificateKey" /> are
141141- set.
142142- </para>
143143- </note>
144144- </section>
145145- <section xml:id="module-services-discourse-settings">
146146- <title>Additional settings</title>
147147- <para>
148148- Additional site settings and backend settings, for which no
149149- explicit NixOS options are provided, can be set in
150150- <xref linkend="opt-services.discourse.siteSettings" /> and
151151- <xref linkend="opt-services.discourse.backendSettings" />
152152- respectively.
153153- </para>
154154- <section xml:id="module-services-discourse-site-settings">
155155- <title>Site settings</title>
156156- <para>
157157- <quote>Site settings</quote> are the settings that can be
158158- changed through the Discourse UI. Their
159159- <emphasis>default</emphasis> values can be set using
160160- <xref linkend="opt-services.discourse.siteSettings" />.
161161- </para>
162162- <para>
163163- Settings are expressed as a Nix attribute set which matches the
164164- structure of the configuration in
165165- <link xlink:href="https://github.com/discourse/discourse/blob/master/config/site_settings.yml">config/site_settings.yml</link>.
166166- To find a setting’s path, you only need to care about the first
167167- two levels; i.e. its category (e.g. <literal>login</literal>)
168168- and name (e.g. <literal>invite_only</literal>).
169169- </para>
170170- <para>
171171- Settings containing secret data should be set to an attribute
172172- set containing the attribute <literal>_secret</literal> - a
173173- string pointing to a file containing the value the option should
174174- be set to. See the example.
175175- </para>
176176- </section>
177177- <section xml:id="module-services-discourse-backend-settings">
178178- <title>Backend settings</title>
179179- <para>
180180- Settings are expressed as a Nix attribute set which matches the
181181- structure of the configuration in
182182- <link xlink:href="https://github.com/discourse/discourse/blob/stable/config/discourse_defaults.conf">config/discourse.conf</link>.
183183- Empty parameters can be defined by setting them to
184184- <literal>null</literal>.
185185- </para>
186186- </section>
187187- <section xml:id="module-services-discourse-settings-example">
188188- <title>Example</title>
189189- <para>
190190- The following example sets the title and description of the
191191- Discourse instance and enables GitHub login in the site
192192- settings, and changes a few request limits in the backend
193193- settings:
194194- </para>
195195- <programlisting>
196196-services.discourse = {
197197- enable = true;
198198- hostname = "discourse.example.com";
199199- sslCertificate = "/path/to/ssl_certificate";
200200- sslCertificateKey = "/path/to/ssl_certificate_key";
201201- admin = {
202202- email = "admin@example.com";
203203- username = "admin";
204204- fullName = "Administrator";
205205- passwordFile = "/path/to/password_file";
206206- };
207207- mail.outgoing = {
208208- serverAddress = "smtp.emailprovider.com";
209209- port = 587;
210210- username = "user@emailprovider.com";
211211- passwordFile = "/path/to/smtp_password_file";
212212- };
213213- mail.incoming.enable = true;
214214- siteSettings = {
215215- required = {
216216- title = "My Cats";
217217- site_description = "Discuss My Cats (and be nice plz)";
218218- };
219219- login = {
220220- enable_github_logins = true;
221221- github_client_id = "a2f6dfe838cb3206ce20";
222222- github_client_secret._secret = /run/keys/discourse_github_client_secret;
223223- };
224224- };
225225- backendSettings = {
226226- max_reqs_per_ip_per_minute = 300;
227227- max_reqs_per_ip_per_10_seconds = 60;
228228- max_asset_reqs_per_ip_per_10_seconds = 250;
229229- max_reqs_per_ip_mode = "warn+block";
230230- };
231231- secretKeyBaseFile = "/path/to/secret_key_base_file";
232232-};
233233-</programlisting>
234234- <para>
235235- In the resulting site settings file, the
236236- <literal>login.github_client_secret</literal> key will be set to
237237- the contents of the
238238- <filename>/run/keys/discourse_github_client_secret</filename>
239239- file.
240240- </para>
241241- </section>
242242- </section>
243243- <section xml:id="module-services-discourse-plugins">
244244- <title>Plugins</title>
245245- <para>
246246- You can install Discourse plugins using the
247247- <xref linkend="opt-services.discourse.plugins" /> option.
248248- Pre-packaged plugins are provided in
249249- <literal><your_discourse_package_here>.plugins</literal>. If
250250- you want the full suite of plugins provided through
251251- <literal>nixpkgs</literal>, you can also set the
252252- <xref linkend="opt-services.discourse.package" /> option to
253253- <literal>pkgs.discourseAllPlugins</literal>.
254254- </para>
255255- <para>
256256- Plugins can be built with the
257257- <literal><your_discourse_package_here>.mkDiscoursePlugin</literal>
258258- function. Normally, it should suffice to provide a
259259- <literal>name</literal> and <literal>src</literal> attribute. If
260260- the plugin has Ruby dependencies, however, they need to be
261261- packaged in accordance with the
262262- <link xlink:href="https://nixos.org/manual/nixpkgs/stable/#developing-with-ruby">Developing
263263- with Ruby</link> section of the Nixpkgs manual and the appropriate
264264- gem options set in <literal>bundlerEnvArgs</literal> (normally
265265- <literal>gemdir</literal> is sufficient). A plugin’s Ruby
266266- dependencies are listed in its <filename>plugin.rb</filename> file
267267- as function calls to <literal>gem</literal>. To construct the
268268- corresponding <filename>Gemfile</filename> manually, run
269269- <command>bundle init</command>, then add the
270270- <literal>gem</literal> lines to it verbatim.
271271- </para>
272272- <para>
273273- Much of the packaging can be done automatically by the
274274- <filename>nixpkgs/pkgs/servers/web-apps/discourse/update.py</filename>
275275- script - just add the plugin to the <literal>plugins</literal>
276276- list in the <literal>update_plugins</literal> function and run the
277277- script:
278278- </para>
279279- <programlisting language="bash">
280280-./update.py update-plugins
281281-</programlisting>
282282- <para>
283283- Some plugins provide
284284- <link linkend="module-services-discourse-site-settings">site
285285- settings</link>. Their defaults can be configured using
286286- <xref linkend="opt-services.discourse.siteSettings" />, just like
287287- regular site settings. To find the names of these settings, look
288288- in the <literal>config/settings.yml</literal> file of the plugin
289289- repo.
290290- </para>
291291- <para>
292292- For example, to add the
293293- <link xlink:href="https://github.com/discourse/discourse-spoiler-alert">discourse-spoiler-alert</link>
294294- and
295295- <link xlink:href="https://github.com/discourse/discourse-solved">discourse-solved</link>
296296- plugins, and disable <literal>discourse-spoiler-alert</literal> by
297297- default:
298298- </para>
299299- <programlisting>
300300-services.discourse = {
301301- enable = true;
302302- hostname = "discourse.example.com";
303303- sslCertificate = "/path/to/ssl_certificate";
304304- sslCertificateKey = "/path/to/ssl_certificate_key";
305305- admin = {
306306- email = "admin@example.com";
307307- username = "admin";
308308- fullName = "Administrator";
309309- passwordFile = "/path/to/password_file";
310310- };
311311- mail.outgoing = {
312312- serverAddress = "smtp.emailprovider.com";
313313- port = 587;
314314- username = "user@emailprovider.com";
315315- passwordFile = "/path/to/smtp_password_file";
316316- };
317317- mail.incoming.enable = true;
318318- plugins = with config.services.discourse.package.plugins; [
319319- discourse-spoiler-alert
320320- discourse-solved
321321- ];
322322- siteSettings = {
323323- plugins = {
324324- spoiler_enabled = false;
325325- };
326326- };
327327- secretKeyBaseFile = "/path/to/secret_key_base_file";
328328-};
329329-</programlisting>
330330- </section>
331331-</chapter>
···11-<!-- Do not edit this file directly, edit its companion .md instead
22- and regenerate this file using nixos/doc/manual/md-to-db.sh -->
33-<chapter xmlns="http://docbook.org/ns/docbook" xmlns:xlink="http://www.w3.org/1999/xlink" xml:id="module-services-grocy">
44- <title>Grocy</title>
55- <para>
66- <link xlink:href="https://grocy.info/">Grocy</link> is a web-based
77- self-hosted groceries & household management solution for your
88- home.
99- </para>
1010- <section xml:id="module-services-grocy-basic-usage">
1111- <title>Basic usage</title>
1212- <para>
1313- A very basic configuration may look like this:
1414- </para>
1515- <programlisting>
1616-{ pkgs, ... }:
1717-{
1818- services.grocy = {
1919- enable = true;
2020- hostName = "grocy.tld";
2121- };
2222-}
2323-</programlisting>
2424- <para>
2525- This configures a simple vhost using
2626- <link linkend="opt-services.nginx.enable">nginx</link> which
2727- listens to <literal>grocy.tld</literal> with fully configured
2828- ACME/LE (this can be disabled by setting
2929- <link linkend="opt-services.grocy.nginx.enableSSL">services.grocy.nginx.enableSSL</link>
3030- to <literal>false</literal>). After the initial setup the
3131- credentials <literal>admin:admin</literal> can be used to login.
3232- </para>
3333- <para>
3434- The application’s state is persisted at
3535- <literal>/var/lib/grocy/grocy.db</literal> in a
3636- <literal>sqlite3</literal> database. The migration is applied when
3737- requesting the <literal>/</literal>-route of the application.
3838- </para>
3939- </section>
4040- <section xml:id="module-services-grocy-settings">
4141- <title>Settings</title>
4242- <para>
4343- The configuration for <literal>grocy</literal> is located at
4444- <literal>/etc/grocy/config.php</literal>. By default, the
4545- following settings can be defined in the NixOS-configuration:
4646- </para>
4747- <programlisting>
4848-{ pkgs, ... }:
4949-{
5050- services.grocy.settings = {
5151- # The default currency in the system for invoices etc.
5252- # Please note that exchange rates aren't taken into account, this
5353- # is just the setting for what's shown in the frontend.
5454- currency = "EUR";
5555-5656- # The display language (and locale configuration) for grocy.
5757- culture = "de";
5858-5959- calendar = {
6060- # Whether or not to show the week-numbers
6161- # in the calendar.
6262- showWeekNumber = true;
6363-6464- # Index of the first day to be shown in the calendar (0=Sunday, 1=Monday,
6565- # 2=Tuesday and so on).
6666- firstDayOfWeek = 2;
6767- };
6868- };
6969-}
7070-</programlisting>
7171- <para>
7272- If you want to alter the configuration file on your own, you can
7373- do this manually with an expression like this:
7474- </para>
7575- <programlisting>
7676-{ lib, ... }:
7777-{
7878- environment.etc."grocy/config.php".text = lib.mkAfter ''
7979- // Arbitrary PHP code in grocy's configuration file
8080- '';
8181-}
8282-</programlisting>
8383- </section>
8484-</chapter>
···11-<!-- Do not edit this file directly, edit its companion .md instead
22- and regenerate this file using nixos/doc/manual/md-to-db.sh -->
33-<chapter xmlns="http://docbook.org/ns/docbook" xmlns:xlink="http://www.w3.org/1999/xlink" xml:id="module-services-keycloak">
44- <title>Keycloak</title>
55- <para>
66- <link xlink:href="https://www.keycloak.org/">Keycloak</link> is an
77- open source identity and access management server with support for
88- <link xlink:href="https://openid.net/connect/">OpenID
99- Connect</link>, <link xlink:href="https://oauth.net/2/">OAUTH
1010- 2.0</link> and
1111- <link xlink:href="https://en.wikipedia.org/wiki/SAML_2.0">SAML
1212- 2.0</link>.
1313- </para>
1414- <section xml:id="module-services-keycloak-admin">
1515- <title>Administration</title>
1616- <para>
1717- An administrative user with the username <literal>admin</literal>
1818- is automatically created in the <literal>master</literal> realm.
1919- Its initial password can be configured by setting
2020- <xref linkend="opt-services.keycloak.initialAdminPassword" /> and
2121- defaults to <literal>changeme</literal>. The password is not
2222- stored safely and should be changed immediately in the admin
2323- panel.
2424- </para>
2525- <para>
2626- Refer to the
2727- <link xlink:href="https://www.keycloak.org/docs/latest/server_admin/index.html">Keycloak
2828- Server Administration Guide</link> for information on how to
2929- administer your Keycloak instance.
3030- </para>
3131- </section>
3232- <section xml:id="module-services-keycloak-database">
3333- <title>Database access</title>
3434- <para>
3535- Keycloak can be used with either PostgreSQL, MariaDB or MySQL.
3636- Which one is used can be configured in
3737- <xref linkend="opt-services.keycloak.database.type" />. The
3838- selected database will automatically be enabled and a database and
3939- role created unless
4040- <xref linkend="opt-services.keycloak.database.host" /> is changed
4141- from its default of <literal>localhost</literal> or
4242- <xref linkend="opt-services.keycloak.database.createLocally" /> is
4343- set to <literal>false</literal>.
4444- </para>
4545- <para>
4646- External database access can also be configured by setting
4747- <xref linkend="opt-services.keycloak.database.host" />,
4848- <xref linkend="opt-services.keycloak.database.name" />,
4949- <xref linkend="opt-services.keycloak.database.username" />,
5050- <xref linkend="opt-services.keycloak.database.useSSL" /> and
5151- <xref linkend="opt-services.keycloak.database.caCert" /> as
5252- appropriate. Note that you need to manually create the database
5353- and allow the configured database user full access to it.
5454- </para>
5555- <para>
5656- <xref linkend="opt-services.keycloak.database.passwordFile" />
5757- must be set to the path to a file containing the password used to
5858- log in to the database. If
5959- <xref linkend="opt-services.keycloak.database.host" /> and
6060- <xref linkend="opt-services.keycloak.database.createLocally" />
6161- are kept at their defaults, the database role
6262- <literal>keycloak</literal> with that password is provisioned on
6363- the local database instance.
6464- </para>
6565- <warning>
6666- <para>
6767- The path should be provided as a string, not a Nix path, since
6868- Nix paths are copied into the world readable Nix store.
6969- </para>
7070- </warning>
7171- </section>
7272- <section xml:id="module-services-keycloak-hostname">
7373- <title>Hostname</title>
7474- <para>
7575- The hostname is used to build the public URL used as base for all
7676- frontend requests and must be configured through
7777- <xref linkend="opt-services.keycloak.settings.hostname" />.
7878- </para>
7979- <note>
8080- <para>
8181- If you’re migrating an old Wildfly based Keycloak instance and
8282- want to keep compatibility with your current clients, you’ll
8383- likely want to set
8484- <xref linkend="opt-services.keycloak.settings.http-relative-path" />
8585- to <literal>/auth</literal>. See the option description for more
8686- details.
8787- </para>
8888- </note>
8989- <para>
9090- <xref linkend="opt-services.keycloak.settings.hostname-strict-backchannel" />
9191- determines whether Keycloak should force all requests to go
9292- through the frontend URL. By default, Keycloak allows backend
9393- requests to instead use its local hostname or IP address and may
9494- also advertise it to clients through its OpenID Connect Discovery
9595- endpoint.
9696- </para>
9797- <para>
9898- For more information on hostname configuration, see the
9999- <link xlink:href="https://www.keycloak.org/server/hostname">Hostname
100100- section of the Keycloak Server Installation and Configuration
101101- Guide</link>.
102102- </para>
103103- </section>
104104- <section xml:id="module-services-keycloak-tls">
105105- <title>Setting up TLS/SSL</title>
106106- <para>
107107- By default, Keycloak won’t accept unsecured HTTP connections
108108- originating from outside its local network.
109109- </para>
110110- <para>
111111- HTTPS support requires a TLS/SSL certificate and a private key,
112112- both
113113- <link xlink:href="https://en.wikipedia.org/wiki/Privacy-Enhanced_Mail">PEM
114114- formatted</link>. Their paths should be set through
115115- <xref linkend="opt-services.keycloak.sslCertificate" /> and
116116- <xref linkend="opt-services.keycloak.sslCertificateKey" />.
117117- </para>
118118- <warning>
119119- <para>
120120- The paths should be provided as a strings, not a Nix paths,
121121- since Nix paths are copied into the world readable Nix store.
122122- </para>
123123- </warning>
124124- </section>
125125- <section xml:id="module-services-keycloak-themes">
126126- <title>Themes</title>
127127- <para>
128128- You can package custom themes and make them visible to Keycloak
129129- through <xref linkend="opt-services.keycloak.themes" />. See the
130130- <link xlink:href="https://www.keycloak.org/docs/latest/server_development/#_themes">Themes
131131- section of the Keycloak Server Development Guide</link> and the
132132- description of the aforementioned NixOS option for more
133133- information.
134134- </para>
135135- </section>
136136- <section xml:id="module-services-keycloak-settings">
137137- <title>Configuration file settings</title>
138138- <para>
139139- Keycloak server configuration parameters can be set in
140140- <xref linkend="opt-services.keycloak.settings" />. These
141141- correspond directly to options in
142142- <filename>conf/keycloak.conf</filename>. Some of the most
143143- important parameters are documented as suboptions, the rest can be
144144- found in the
145145- <link xlink:href="https://www.keycloak.org/server/all-config">All
146146- configuration section of the Keycloak Server Installation and
147147- Configuration Guide</link>.
148148- </para>
149149- <para>
150150- Options containing secret data should be set to an attribute set
151151- containing the attribute <literal>_secret</literal> - a string
152152- pointing to a file containing the value the option should be set
153153- to. See the description of
154154- <xref linkend="opt-services.keycloak.settings" /> for an example.
155155- </para>
156156- </section>
157157- <section xml:id="module-services-keycloak-example-config">
158158- <title>Example configuration</title>
159159- <para>
160160- A basic configuration with some custom settings could look like
161161- this:
162162- </para>
163163- <programlisting>
164164-services.keycloak = {
165165- enable = true;
166166- settings = {
167167- hostname = "keycloak.example.com";
168168- hostname-strict-backchannel = true;
169169- };
170170- initialAdminPassword = "e6Wcm0RrtegMEHl"; # change on first login
171171- sslCertificate = "/run/keys/ssl_cert";
172172- sslCertificateKey = "/run/keys/ssl_key";
173173- database.passwordFile = "/run/keys/db_password";
174174-};
175175-</programlisting>
176176- </section>
177177-</chapter>
···11-<!-- Do not edit this file directly, edit its companion .md instead
22- and regenerate this file using nixos/doc/manual/md-to-db.sh -->
33-<chapter xmlns="http://docbook.org/ns/docbook" xmlns:xlink="http://www.w3.org/1999/xlink" xml:id="module-services-lemmy">
44- <title>Lemmy</title>
55- <para>
66- Lemmy is a federated alternative to reddit in rust.
77- </para>
88- <section xml:id="module-services-lemmy-quickstart">
99- <title>Quickstart</title>
1010- <para>
1111- the minimum to start lemmy is
1212- </para>
1313- <programlisting language="nix">
1414-services.lemmy = {
1515- enable = true;
1616- settings = {
1717- hostname = "lemmy.union.rocks";
1818- database.createLocally = true;
1919- };
2020- caddy.enable = true;
2121-}
2222-</programlisting>
2323- <para>
2424- this will start the backend on port 8536 and the frontend on port
2525- 1234. It will expose your instance with a caddy reverse proxy to
2626- the hostname you’ve provided. Postgres will be initialized on that
2727- same instance automatically.
2828- </para>
2929- </section>
3030- <section xml:id="module-services-lemmy-usage">
3131- <title>Usage</title>
3232- <para>
3333- On first connection you will be asked to define an admin user.
3434- </para>
3535- </section>
3636- <section xml:id="module-services-lemmy-missing">
3737- <title>Missing</title>
3838- <itemizedlist spacing="compact">
3939- <listitem>
4040- <para>
4141- Exposing with nginx is not implemented yet.
4242- </para>
4343- </listitem>
4444- <listitem>
4545- <para>
4646- This has been tested using a local database with a unix socket
4747- connection. Using different database settings will likely
4848- require modifications
4949- </para>
5050- </listitem>
5151- </itemizedlist>
5252- </section>
5353-</chapter>
···11-<!-- Do not edit this file directly, edit its companion .md instead
22- and regenerate this file using nixos/doc/manual/md-to-db.sh -->
33-<chapter xmlns="http://docbook.org/ns/docbook" xmlns:xlink="http://www.w3.org/1999/xlink" xml:id="module-services-matomo">
44- <title>Matomo</title>
55- <para>
66- Matomo is a real-time web analytics application. This module
77- configures php-fpm as backend for Matomo, optionally configuring an
88- nginx vhost as well.
99- </para>
1010- <para>
1111- An automatic setup is not suported by Matomo, so you need to
1212- configure Matomo itself in the browser-based Matomo setup.
1313- </para>
1414- <section xml:id="module-services-matomo-database-setup">
1515- <title>Database Setup</title>
1616- <para>
1717- You also need to configure a MariaDB or MySQL database and -user
1818- for Matomo yourself, and enter those credentials in your browser.
1919- You can use passwordless database authentication via the
2020- UNIX_SOCKET authentication plugin with the following SQL commands:
2121- </para>
2222- <programlisting>
2323-# For MariaDB
2424-INSTALL PLUGIN unix_socket SONAME 'auth_socket';
2525-CREATE DATABASE matomo;
2626-CREATE USER 'matomo'@'localhost' IDENTIFIED WITH unix_socket;
2727-GRANT ALL PRIVILEGES ON matomo.* TO 'matomo'@'localhost';
2828-2929-# For MySQL
3030-INSTALL PLUGIN auth_socket SONAME 'auth_socket.so';
3131-CREATE DATABASE matomo;
3232-CREATE USER 'matomo'@'localhost' IDENTIFIED WITH auth_socket;
3333-GRANT ALL PRIVILEGES ON matomo.* TO 'matomo'@'localhost';
3434-</programlisting>
3535- <para>
3636- Then fill in <literal>matomo</literal> as database user and
3737- database name, and leave the password field blank. This
3838- authentication works by allowing only the
3939- <literal>matomo</literal> unix user to authenticate as the
4040- <literal>matomo</literal> database user (without needing a
4141- password), but no other users. For more information on
4242- passwordless login, see
4343- <link xlink:href="https://mariadb.com/kb/en/mariadb/unix_socket-authentication-plugin/">https://mariadb.com/kb/en/mariadb/unix_socket-authentication-plugin/</link>.
4444- </para>
4545- <para>
4646- Of course, you can use password based authentication as well, e.g.
4747- when the database is not on the same host.
4848- </para>
4949- </section>
5050- <section xml:id="module-services-matomo-archive-processing">
5151- <title>Archive Processing</title>
5252- <para>
5353- This module comes with the systemd service
5454- <literal>matomo-archive-processing.service</literal> and a timer
5555- that automatically triggers archive processing every hour. This
5656- means that you can safely
5757- <link xlink:href="https://matomo.org/docs/setup-auto-archiving/#disable-browser-triggers-for-matomo-archiving-and-limit-matomo-reports-to-updating-every-hour">disable
5858- browser triggers for Matomo archiving</link> at
5959- <literal>Administration > System > General Settings</literal>.
6060- </para>
6161- <para>
6262- With automatic archive processing, you can now also enable to
6363- <link xlink:href="https://matomo.org/docs/privacy/#step-2-delete-old-visitors-logs">delete
6464- old visitor logs</link> at
6565- <literal>Administration > System > Privacy</literal>, but
6666- make sure that you run
6767- <literal>systemctl start matomo-archive-processing.service</literal>
6868- at least once without errors if you have already collected data
6969- before, so that the reports get archived before the source data
7070- gets deleted.
7171- </para>
7272- </section>
7373- <section xml:id="module-services-matomo-backups">
7474- <title>Backup</title>
7575- <para>
7676- You only need to take backups of your MySQL database and the
7777- <filename>/var/lib/matomo/config/config.ini.php</filename> file.
7878- Use a user in the <literal>matomo</literal> group or root to
7979- access the file. For more information, see
8080- <link xlink:href="https://matomo.org/faq/how-to-install/faq_138/">https://matomo.org/faq/how-to-install/faq_138/</link>.
8181- </para>
8282- </section>
8383- <section xml:id="module-services-matomo-issues">
8484- <title>Issues</title>
8585- <itemizedlist spacing="compact">
8686- <listitem>
8787- <para>
8888- Matomo will warn you that the JavaScript tracker is not
8989- writable. This is because it’s located in the read-only nix
9090- store. You can safely ignore this, unless you need a plugin
9191- that needs JavaScript tracker access.
9292- </para>
9393- </listitem>
9494- </itemizedlist>
9595- </section>
9696- <section xml:id="module-services-matomo-other-web-servers">
9797- <title>Using other Web Servers than nginx</title>
9898- <para>
9999- You can use other web servers by forwarding calls for
100100- <filename>index.php</filename> and <filename>piwik.php</filename>
101101- to the
102102- <link linkend="opt-services.phpfpm.pools._name_.socket"><literal>services.phpfpm.pools.<name>.socket</literal></link>
103103- fastcgi unix socket. You can use the nginx configuration in the
104104- module code as a reference to what else should be configured.
105105- </para>
106106- </section>
107107-</chapter>
···11-<!-- Do not edit this file directly, edit its companion .md instead
22- and regenerate this file using nixos/doc/manual/md-to-db.sh -->
33-<chapter xmlns="http://docbook.org/ns/docbook" xmlns:xlink="http://www.w3.org/1999/xlink" xml:id="module-services-nextcloud">
44- <title>Nextcloud</title>
55- <para>
66- <link xlink:href="https://nextcloud.com/">Nextcloud</link> is an
77- open-source, self-hostable cloud platform. The server setup can be
88- automated using
99- <link linkend="opt-services.nextcloud.enable">services.nextcloud</link>.
1010- A desktop client is packaged at
1111- <literal>pkgs.nextcloud-client</literal>.
1212- </para>
1313- <para>
1414- The current default by NixOS is <literal>nextcloud25</literal> which
1515- is also the latest major version available.
1616- </para>
1717- <section xml:id="module-services-nextcloud-basic-usage">
1818- <title>Basic usage</title>
1919- <para>
2020- Nextcloud is a PHP-based application which requires an HTTP server
2121- (<link linkend="opt-services.nextcloud.enable"><literal>services.nextcloud</literal></link>
2222- optionally supports
2323- <link linkend="opt-services.nginx.enable"><literal>services.nginx</literal></link>)
2424- and a database (it’s recommended to use
2525- <link linkend="opt-services.postgresql.enable"><literal>services.postgresql</literal></link>).
2626- </para>
2727- <para>
2828- A very basic configuration may look like this:
2929- </para>
3030- <programlisting>
3131-{ pkgs, ... }:
3232-{
3333- services.nextcloud = {
3434- enable = true;
3535- hostName = "nextcloud.tld";
3636- config = {
3737- dbtype = "pgsql";
3838- dbuser = "nextcloud";
3939- dbhost = "/run/postgresql"; # nextcloud will add /.s.PGSQL.5432 by itself
4040- dbname = "nextcloud";
4141- adminpassFile = "/path/to/admin-pass-file";
4242- adminuser = "root";
4343- };
4444- };
4545-4646- services.postgresql = {
4747- enable = true;
4848- ensureDatabases = [ "nextcloud" ];
4949- ensureUsers = [
5050- { name = "nextcloud";
5151- ensurePermissions."DATABASE nextcloud" = "ALL PRIVILEGES";
5252- }
5353- ];
5454- };
5555-5656- # ensure that postgres is running *before* running the setup
5757- systemd.services."nextcloud-setup" = {
5858- requires = ["postgresql.service"];
5959- after = ["postgresql.service"];
6060- };
6161-6262- networking.firewall.allowedTCPPorts = [ 80 443 ];
6363-}
6464-</programlisting>
6565- <para>
6666- The <literal>hostName</literal> option is used internally to
6767- configure an HTTP server using
6868- <link xlink:href="https://php-fpm.org/"><literal>PHP-FPM</literal></link>
6969- and <literal>nginx</literal>. The <literal>config</literal>
7070- attribute set is used by the imperative installer and all values
7171- are written to an additional file to ensure that changes can be
7272- applied by changing the module’s options.
7373- </para>
7474- <para>
7575- In case the application serves multiple domains (those are checked
7676- with
7777- <link xlink:href="http://php.net/manual/en/reserved.variables.server.php"><literal>$_SERVER['HTTP_HOST']</literal></link>)
7878- it’s needed to add them to
7979- <link linkend="opt-services.nextcloud.config.extraTrustedDomains"><literal>services.nextcloud.config.extraTrustedDomains</literal></link>.
8080- </para>
8181- <para>
8282- Auto updates for Nextcloud apps can be enabled using
8383- <link linkend="opt-services.nextcloud.autoUpdateApps.enable"><literal>services.nextcloud.autoUpdateApps</literal></link>.
8484- </para>
8585- </section>
8686- <section xml:id="module-services-nextcloud-pitfalls-during-upgrade">
8787- <title>Common problems</title>
8888- <itemizedlist>
8989- <listitem>
9090- <para>
9191- <emphasis role="strong">General notes.</emphasis>
9292- Unfortunately Nextcloud appears to be very stateful when it
9393- comes to managing its own configuration. The config file lives
9494- in the home directory of the <literal>nextcloud</literal> user
9595- (by default
9696- <literal>/var/lib/nextcloud/config/config.php</literal>) and
9797- is also used to track several states of the application (e.g.,
9898- whether installed or not).
9999- </para>
100100- <para>
101101- All configuration parameters are also stored in
102102- <filename>/var/lib/nextcloud/config/override.config.php</filename>
103103- which is generated by the module and linked from the store to
104104- ensure that all values from <filename>config.php</filename>
105105- can be modified by the module. However
106106- <filename>config.php</filename> manages the application’s
107107- state and shouldn’t be touched manually because of that.
108108- </para>
109109- <warning>
110110- <para>
111111- Don’t delete <filename>config.php</filename>! This file
112112- tracks the application’s state and a deletion can cause
113113- unwanted side-effects!
114114- </para>
115115- </warning>
116116- <warning>
117117- <para>
118118- Don’t rerun
119119- <literal>nextcloud-occ maintenance:install</literal>! This
120120- command tries to install the application and can cause
121121- unwanted side-effects!
122122- </para>
123123- </warning>
124124- </listitem>
125125- <listitem>
126126- <para>
127127- <emphasis role="strong">Multiple version upgrades.</emphasis>
128128- Nextcloud doesn’t allow to move more than one major-version
129129- forward. E.g., if you’re on <literal>v16</literal>, you cannot
130130- upgrade to <literal>v18</literal>, you need to upgrade to
131131- <literal>v17</literal> first. This is ensured automatically as
132132- long as the
133133- <link linkend="opt-system.stateVersion">stateVersion</link> is
134134- declared properly. In that case the oldest version available
135135- (one major behind the one from the previous NixOS release)
136136- will be selected by default and the module will generate a
137137- warning that reminds the user to upgrade to latest Nextcloud
138138- <emphasis>after</emphasis> that deploy.
139139- </para>
140140- </listitem>
141141- <listitem>
142142- <para>
143143- <emphasis role="strong"><literal>Error: Command "upgrade" is not defined.</literal></emphasis>
144144- This error usually occurs if the initial installation
145145- (<command>nextcloud-occ maintenance:install</command>) has
146146- failed. After that, the application is not installed, but the
147147- upgrade is attempted to be executed. Further context can be
148148- found in
149149- <link xlink:href="https://github.com/NixOS/nixpkgs/issues/111175">NixOS/nixpkgs#111175</link>.
150150- </para>
151151- <para>
152152- First of all, it makes sense to find out what went wrong by
153153- looking at the logs of the installation via
154154- <command>journalctl -u nextcloud-setup</command> and try to
155155- fix the underlying issue.
156156- </para>
157157- <itemizedlist>
158158- <listitem>
159159- <para>
160160- If this occurs on an <emphasis>existing</emphasis> setup,
161161- this is most likely because the maintenance mode is
162162- active. It can be deactivated by running
163163- <command>nextcloud-occ maintenance:mode --off</command>.
164164- It’s advisable though to check the logs first on why the
165165- maintenance mode was activated.
166166- </para>
167167- </listitem>
168168- <listitem>
169169- <warning>
170170- <para>
171171- Only perform the following measures on <emphasis>freshly
172172- installed instances!</emphasis>
173173- </para>
174174- </warning>
175175- <para>
176176- A re-run of the installer can be forced by
177177- <emphasis>deleting</emphasis>
178178- <filename>/var/lib/nextcloud/config/config.php</filename>.
179179- This is the only time advisable because the fresh install
180180- doesn’t have any state that can be lost. In case that
181181- doesn’t help, an entire re-creation can be forced via
182182- <command>rm -rf ~nextcloud/</command>.
183183- </para>
184184- </listitem>
185185- </itemizedlist>
186186- </listitem>
187187- <listitem>
188188- <para>
189189- <emphasis role="strong">Server-side encryption.</emphasis>
190190- Nextcloud supports
191191- <link xlink:href="https://docs.nextcloud.com/server/latest/admin_manual/configuration_files/encryption_configuration.html">server-side
192192- encryption (SSE)</link>. This is not an end-to-end encryption,
193193- but can be used to encrypt files that will be persisted to
194194- external storage such as S3. Please note that this won’t work
195195- anymore when using OpenSSL 3 for PHP’s openssl extension
196196- because this is implemented using the legacy cipher RC4. If
197197- <xref linkend="opt-system.stateVersion" /> is
198198- <emphasis>above</emphasis> <literal>22.05</literal>, this is
199199- disabled by default. To turn it on again and for further
200200- information please refer to
201201- <xref linkend="opt-services.nextcloud.enableBrokenCiphersForSSE" />.
202202- </para>
203203- </listitem>
204204- </itemizedlist>
205205- </section>
206206- <section xml:id="module-services-nextcloud-httpd">
207207- <title>Using an alternative webserver as reverse-proxy (e.g.
208208- <literal>httpd</literal>)</title>
209209- <para>
210210- By default, <literal>nginx</literal> is used as reverse-proxy for
211211- <literal>nextcloud</literal>. However, it’s possible to use e.g.
212212- <literal>httpd</literal> by explicitly disabling
213213- <literal>nginx</literal> using
214214- <xref linkend="opt-services.nginx.enable" /> and fixing the
215215- settings <literal>listen.owner</literal> &
216216- <literal>listen.group</literal> in the
217217- <link linkend="opt-services.phpfpm.pools">corresponding
218218- <literal>phpfpm</literal> pool</link>.
219219- </para>
220220- <para>
221221- An exemplary configuration may look like this:
222222- </para>
223223- <programlisting>
224224-{ config, lib, pkgs, ... }: {
225225- services.nginx.enable = false;
226226- services.nextcloud = {
227227- enable = true;
228228- hostName = "localhost";
229229-230230- /* further, required options */
231231- };
232232- services.phpfpm.pools.nextcloud.settings = {
233233- "listen.owner" = config.services.httpd.user;
234234- "listen.group" = config.services.httpd.group;
235235- };
236236- services.httpd = {
237237- enable = true;
238238- adminAddr = "webmaster@localhost";
239239- extraModules = [ "proxy_fcgi" ];
240240- virtualHosts."localhost" = {
241241- documentRoot = config.services.nextcloud.package;
242242- extraConfig = ''
243243- <Directory "${config.services.nextcloud.package}">
244244- <FilesMatch "\.php$">
245245- <If "-f %{REQUEST_FILENAME}">
246246- SetHandler "proxy:unix:${config.services.phpfpm.pools.nextcloud.socket}|fcgi://localhost/"
247247- </If>
248248- </FilesMatch>
249249- <IfModule mod_rewrite.c>
250250- RewriteEngine On
251251- RewriteBase /
252252- RewriteRule ^index\.php$ - [L]
253253- RewriteCond %{REQUEST_FILENAME} !-f
254254- RewriteCond %{REQUEST_FILENAME} !-d
255255- RewriteRule . /index.php [L]
256256- </IfModule>
257257- DirectoryIndex index.php
258258- Require all granted
259259- Options +FollowSymLinks
260260- </Directory>
261261- '';
262262- };
263263- };
264264-}
265265-</programlisting>
266266- </section>
267267- <section xml:id="installing-apps-php-extensions-nextcloud">
268268- <title>Installing Apps and PHP extensions</title>
269269- <para>
270270- Nextcloud apps are installed statefully through the web interface.
271271- Some apps may require extra PHP extensions to be installed. This
272272- can be configured with the
273273- <xref linkend="opt-services.nextcloud.phpExtraExtensions" />
274274- setting.
275275- </para>
276276- <para>
277277- Alternatively, extra apps can also be declared with the
278278- <xref linkend="opt-services.nextcloud.extraApps" /> setting. When
279279- using this setting, apps can no longer be managed statefully
280280- because this can lead to Nextcloud updating apps that are managed
281281- by Nix. If you want automatic updates it is recommended that you
282282- use web interface to install apps.
283283- </para>
284284- </section>
285285- <section xml:id="module-services-nextcloud-maintainer-info">
286286- <title>Maintainer information</title>
287287- <para>
288288- As stated in the previous paragraph, we must provide a clean
289289- upgrade-path for Nextcloud since it cannot move more than one
290290- major version forward on a single upgrade. This chapter adds some
291291- notes how Nextcloud updates should be rolled out in the future.
292292- </para>
293293- <para>
294294- While minor and patch-level updates are no problem and can be done
295295- directly in the package-expression (and should be backported to
296296- supported stable branches after that), major-releases should be
297297- added in a new attribute (e.g. Nextcloud
298298- <literal>v19.0.0</literal> should be available in
299299- <literal>nixpkgs</literal> as
300300- <literal>pkgs.nextcloud19</literal>). To provide simple upgrade
301301- paths it’s generally useful to backport those as well to stable
302302- branches. As long as the package-default isn’t altered, this won’t
303303- break existing setups. After that, the versioning-warning in the
304304- <literal>nextcloud</literal>-module should be updated to make sure
305305- that the
306306- <link linkend="opt-services.nextcloud.package">package</link>-option
307307- selects the latest version on fresh setups.
308308- </para>
309309- <para>
310310- If major-releases will be abandoned by upstream, we should check
311311- first if those are needed in NixOS for a safe upgrade-path before
312312- removing those. In that case we should keep those packages, but
313313- mark them as insecure in an expression like this (in
314314- <literal><nixpkgs/pkgs/servers/nextcloud/default.nix></literal>):
315315- </para>
316316- <programlisting>
317317-/* ... */
318318-{
319319- nextcloud17 = generic {
320320- version = "17.0.x";
321321- sha256 = "0000000000000000000000000000000000000000000000000000";
322322- eol = true;
323323- };
324324-}
325325-</programlisting>
326326- <para>
327327- Ideally we should make sure that it’s possible to jump two NixOS
328328- versions forward: i.e. the warnings and the logic in the module
329329- should guard a user to upgrade from a Nextcloud on e.g. 19.09 to a
330330- Nextcloud on 20.09.
331331- </para>
332332- </section>
333333-</chapter>
···11-<!-- Do not edit this file directly, edit its companion .md instead
22- and regenerate this file using nixos/doc/manual/md-to-db.sh -->
33-<chapter xmlns="http://docbook.org/ns/docbook" xmlns:xlink="http://www.w3.org/1999/xlink" xml:id="module-services-pict-rs">
44- <title>Pict-rs</title>
55- <para>
66- pict-rs is a a simple image hosting service.
77- </para>
88- <section xml:id="module-services-pict-rs-quickstart">
99- <title>Quickstart</title>
1010- <para>
1111- the minimum to start pict-rs is
1212- </para>
1313- <programlisting language="nix">
1414-services.pict-rs.enable = true;
1515-</programlisting>
1616- <para>
1717- this will start the http server on port 8080 by default.
1818- </para>
1919- </section>
2020- <section xml:id="module-services-pict-rs-usage">
2121- <title>Usage</title>
2222- <para>
2323- pict-rs offers the following endpoints:
2424- </para>
2525- <itemizedlist>
2626- <listitem>
2727- <para>
2828- <literal>POST /image</literal> for uploading an image.
2929- Uploaded content must be valid multipart/form-data with an
3030- image array located within the <literal>images[]</literal> key
3131- </para>
3232- <para>
3333- This endpoint returns the following JSON structure on success
3434- with a 201 Created status
3535- </para>
3636- <programlisting language="json">
3737-{
3838- "files": [
3939- {
4040- "delete_token": "JFvFhqJA98",
4141- "file": "lkWZDRvugm.jpg"
4242- },
4343- {
4444- "delete_token": "kAYy9nk2WK",
4545- "file": "8qFS0QooAn.jpg"
4646- },
4747- {
4848- "delete_token": "OxRpM3sf0Y",
4949- "file": "1hJaYfGE01.jpg"
5050- }
5151- ],
5252- "msg": "ok"
5353-}
5454-</programlisting>
5555- </listitem>
5656- <listitem>
5757- <para>
5858- <literal>GET /image/download?url=...</literal> Download an
5959- image from a remote server, returning the same JSON payload as
6060- the <literal>POST</literal> endpoint
6161- </para>
6262- </listitem>
6363- <listitem>
6464- <para>
6565- <literal>GET /image/original/{file}</literal> for getting a
6666- full-resolution image. <literal>file</literal> here is the
6767- <literal>file</literal> key from the <literal>/image</literal>
6868- endpoint’s JSON
6969- </para>
7070- </listitem>
7171- <listitem>
7272- <para>
7373- <literal>GET /image/details/original/{file}</literal> for
7474- getting the details of a full-resolution image. The returned
7575- JSON is structured like so:
7676- </para>
7777- <programlisting language="json">
7878-{
7979- "width": 800,
8080- "height": 537,
8181- "content_type": "image/webp",
8282- "created_at": [
8383- 2020,
8484- 345,
8585- 67376,
8686- 394363487
8787- ]
8888-}
8989-</programlisting>
9090- </listitem>
9191- <listitem>
9292- <para>
9393- <literal>GET /image/process.{ext}?src={file}&...</literal>
9494- get a file with transformations applied. existing
9595- transformations include
9696- </para>
9797- <itemizedlist spacing="compact">
9898- <listitem>
9999- <para>
100100- <literal>identity=true</literal>: apply no changes
101101- </para>
102102- </listitem>
103103- <listitem>
104104- <para>
105105- <literal>blur={float}</literal>: apply a gaussian blur to
106106- the file
107107- </para>
108108- </listitem>
109109- <listitem>
110110- <para>
111111- <literal>thumbnail={int}</literal>: produce a thumbnail of
112112- the image fitting inside an <literal>{int}</literal> by
113113- <literal>{int}</literal> square using raw pixel sampling
114114- </para>
115115- </listitem>
116116- <listitem>
117117- <para>
118118- <literal>resize={int}</literal>: produce a thumbnail of
119119- the image fitting inside an <literal>{int}</literal> by
120120- <literal>{int}</literal> square using a Lanczos2 filter.
121121- This is slower than sampling but looks a bit better in
122122- some cases
123123- </para>
124124- </listitem>
125125- <listitem>
126126- <para>
127127- <literal>crop={int-w}x{int-h}</literal>: produce a cropped
128128- version of the image with an <literal>{int-w}</literal> by
129129- <literal>{int-h}</literal> aspect ratio. The resulting
130130- crop will be centered on the image. Either the width or
131131- height of the image will remain full-size, depending on
132132- the image’s aspect ratio and the requested aspect ratio.
133133- For example, a 1600x900 image cropped with a 1x1 aspect
134134- ratio will become 900x900. A 1600x1100 image cropped with
135135- a 16x9 aspect ratio will become 1600x900.
136136- </para>
137137- </listitem>
138138- </itemizedlist>
139139- <para>
140140- Supported <literal>ext</literal> file extensions include
141141- <literal>png</literal>, <literal>jpg</literal>, and
142142- <literal>webp</literal>
143143- </para>
144144- <para>
145145- An example of usage could be
146146- </para>
147147- <programlisting>
148148-GET /image/process.jpg?src=asdf.png&thumbnail=256&blur=3.0
149149-</programlisting>
150150- <para>
151151- which would create a 256x256px JPEG thumbnail and blur it
152152- </para>
153153- </listitem>
154154- <listitem>
155155- <para>
156156- <literal>GET /image/details/process.{ext}?src={file}&...</literal>
157157- for getting the details of a processed image. The returned
158158- JSON is the same format as listed for the full-resolution
159159- details endpoint.
160160- </para>
161161- </listitem>
162162- <listitem>
163163- <para>
164164- <literal>DELETE /image/delete/{delete_token}/{file}</literal>
165165- or <literal>GET /image/delete/{delete_token}/{file}</literal>
166166- to delete a file, where <literal>delete_token</literal> and
167167- <literal>file</literal> are from the <literal>/image</literal>
168168- endpoint’s JSON
169169- </para>
170170- </listitem>
171171- </itemizedlist>
172172- </section>
173173- <section xml:id="module-services-pict-rs-missing">
174174- <title>Missing</title>
175175- <itemizedlist spacing="compact">
176176- <listitem>
177177- <para>
178178- Configuring the secure-api-key is not included yet. The
179179- envisioned basic use case is consumption on localhost by other
180180- services without exposing the service to the internet.
181181- </para>
182182- </listitem>
183183- </itemizedlist>
184184- </section>
185185-</chapter>
···11-<!-- Do not edit this file directly, edit its companion .md instead
22- and regenerate this file using nixos/doc/manual/md-to-db.sh -->
33-<chapter xmlns="http://docbook.org/ns/docbook" xmlns:xlink="http://www.w3.org/1999/xlink" xml:id="module-services-plausible">
44- <title>Plausible</title>
55- <para>
66- <link xlink:href="https://plausible.io/">Plausible</link> is a
77- privacy-friendly alternative to Google analytics.
88- </para>
99- <section xml:id="module-services-plausible-basic-usage">
1010- <title>Basic Usage</title>
1111- <para>
1212- At first, a secret key is needed to be generated. This can be done
1313- with e.g.
1414- </para>
1515- <programlisting>
1616-$ openssl rand -base64 64
1717-</programlisting>
1818- <para>
1919- After that, <literal>plausible</literal> can be deployed like
2020- this:
2121- </para>
2222- <programlisting>
2323-{
2424- services.plausible = {
2525- enable = true;
2626- adminUser = {
2727- # activate is used to skip the email verification of the admin-user that's
2828- # automatically created by plausible. This is only supported if
2929- # postgresql is configured by the module. This is done by default, but
3030- # can be turned off with services.plausible.database.postgres.setup.
3131- activate = true;
3232- email = "admin@localhost";
3333- passwordFile = "/run/secrets/plausible-admin-pwd";
3434- };
3535- server = {
3636- baseUrl = "http://analytics.example.org";
3737- # secretKeybaseFile is a path to the file which contains the secret generated
3838- # with openssl as described above.
3939- secretKeybaseFile = "/run/secrets/plausible-secret-key-base";
4040- };
4141- };
4242-}
4343-</programlisting>
4444- </section>
4545-</chapter>
···11-<!-- Do not edit this file directly, edit its companion .md instead
22- and regenerate this file using nixos/doc/manual/md-to-db.sh -->
33-<chapter xmlns="http://docbook.org/ns/docbook" xmlns:xlink="http://www.w3.org/1999/xlink" xml:id="module-services-garage">
44- <title>Garage</title>
55- <para>
66- <link xlink:href="https://garagehq.deuxfleurs.fr/">Garage</link> is
77- an open-source, self-hostable S3 store, simpler than MinIO, for
88- geodistributed stores. The server setup can be automated using
99- <link linkend="opt-services.garage.enable">services.garage</link>. A
1010- client configured to your local Garage instance is available in the
1111- global environment as <literal>garage-manage</literal>.
1212- </para>
1313- <para>
1414- The current default by NixOS is <literal>garage_0_8</literal> which
1515- is also the latest major version available.
1616- </para>
1717- <section xml:id="module-services-garage-upgrade-scenarios">
1818- <title>General considerations on upgrades</title>
1919- <para>
2020- Garage provides a cookbook documentation on how to upgrade:
2121- <link xlink:href="https://garagehq.deuxfleurs.fr/documentation/cookbook/upgrading/">https://garagehq.deuxfleurs.fr/documentation/cookbook/upgrading/</link>
2222- </para>
2323- <warning>
2424- <para>
2525- Garage has two types of upgrades: patch-level upgrades and
2626- minor/major version upgrades.
2727- </para>
2828- <para>
2929- In all cases, you should read the changelog and ideally test the
3030- upgrade on a staging cluster.
3131- </para>
3232- <para>
3333- Checking the health of your cluster can be achieved using
3434- <literal>garage-manage repair</literal>.
3535- </para>
3636- </warning>
3737- <warning>
3838- <para>
3939- Until 1.0 is released, patch-level upgrades are considered as
4040- minor version upgrades. Minor version upgrades are considered as
4141- major version upgrades. i.e. 0.6 to 0.7 is a major version
4242- upgrade.
4343- </para>
4444- </warning>
4545- <itemizedlist spacing="compact">
4646- <listitem>
4747- <para>
4848- <emphasis role="strong">Straightforward upgrades (patch-level
4949- upgrades).</emphasis> Upgrades must be performed one by one,
5050- i.e. for each node, stop it, upgrade it : change
5151- <link linkend="opt-system.stateVersion">stateVersion</link> or
5252- <link linkend="opt-services.garage.package">services.garage.package</link>,
5353- restart it if it was not already by switching.
5454- </para>
5555- </listitem>
5656- <listitem>
5757- <para>
5858- <emphasis role="strong">Multiple version upgrades.</emphasis>
5959- Garage do not provide any guarantee on moving more than one
6060- major-version forward. E.g., if you’re on
6161- <literal>0.7</literal>, you cannot upgrade to
6262- <literal>0.9</literal>. You need to upgrade to
6363- <literal>0.8</literal> first. As long as
6464- <link linkend="opt-system.stateVersion">stateVersion</link> is
6565- declared properly, this is enforced automatically. The module
6666- will issue a warning to remind the user to upgrade to latest
6767- Garage <emphasis>after</emphasis> that deploy.
6868- </para>
6969- </listitem>
7070- </itemizedlist>
7171- </section>
7272- <section xml:id="module-services-garage-advanced-upgrades">
7373- <title>Advanced upgrades (minor/major version upgrades)</title>
7474- <para>
7575- Here are some baseline instructions to handle advanced upgrades in
7676- Garage, when in doubt, please refer to upstream instructions.
7777- </para>
7878- <itemizedlist spacing="compact">
7979- <listitem>
8080- <para>
8181- Disable API and web access to Garage.
8282- </para>
8383- </listitem>
8484- <listitem>
8585- <para>
8686- Perform
8787- <literal>garage-manage repair --all-nodes --yes tables</literal>
8888- and
8989- <literal>garage-manage repair --all-nodes --yes blocks</literal>.
9090- </para>
9191- </listitem>
9292- <listitem>
9393- <para>
9494- Verify the resulting logs and check that data is synced
9595- properly between all nodes. If you have time, do additional
9696- checks (<literal>scrub</literal>,
9797- <literal>block_refs</literal>, etc.).
9898- </para>
9999- </listitem>
100100- <listitem>
101101- <para>
102102- Check if queues are empty by
103103- <literal>garage-manage stats</literal> or through monitoring
104104- tools.
105105- </para>
106106- </listitem>
107107- <listitem>
108108- <para>
109109- Run <literal>systemctl stop garage</literal> to stop the
110110- actual Garage version.
111111- </para>
112112- </listitem>
113113- <listitem>
114114- <para>
115115- Backup the metadata folder of ALL your nodes, e.g. for a
116116- metadata directory (the default one) in
117117- <literal>/var/lib/garage/meta</literal>, you can run
118118- <literal>pushd /var/lib/garage; tar -acf meta-v0.7.tar.zst meta/; popd</literal>.
119119- </para>
120120- </listitem>
121121- <listitem>
122122- <para>
123123- Run the offline migration:
124124- <literal>nix-shell -p garage_0_8 --run "garage offline-repair --yes"</literal>,
125125- this can take some time depending on how many objects are
126126- stored in your cluster.
127127- </para>
128128- </listitem>
129129- <listitem>
130130- <para>
131131- Bump Garage version in your NixOS configuration, either by
132132- changing
133133- <link linkend="opt-system.stateVersion">stateVersion</link> or
134134- bumping
135135- <link linkend="opt-services.garage.package">services.garage.package</link>,
136136- this should restart Garage automatically.
137137- </para>
138138- </listitem>
139139- <listitem>
140140- <para>
141141- Perform
142142- <literal>garage-manage repair --all-nodes --yes tables</literal>
143143- and
144144- <literal>garage-manage repair --all-nodes --yes blocks</literal>.
145145- </para>
146146- </listitem>
147147- <listitem>
148148- <para>
149149- Wait for a full table sync to run.
150150- </para>
151151- </listitem>
152152- </itemizedlist>
153153- <para>
154154- Your upgraded cluster should be in a working state, re-enable API
155155- and web access.
156156- </para>
157157- </section>
158158- <section xml:id="module-services-garage-maintainer-info">
159159- <title>Maintainer information</title>
160160- <para>
161161- As stated in the previous paragraph, we must provide a clean
162162- upgrade-path for Garage since it cannot move more than one major
163163- version forward on a single upgrade. This chapter adds some notes
164164- how Garage updates should be rolled out in the future. This is
165165- inspired from how Nextcloud does it.
166166- </para>
167167- <para>
168168- While patch-level updates are no problem and can be done directly
169169- in the package-expression (and should be backported to supported
170170- stable branches after that), major-releases should be added in a
171171- new attribute (e.g. Garage <literal>v0.8.0</literal> should be
172172- available in <literal>nixpkgs</literal> as
173173- <literal>pkgs.garage_0_8_0</literal>). To provide simple upgrade
174174- paths it’s generally useful to backport those as well to stable
175175- branches. As long as the package-default isn’t altered, this won’t
176176- break existing setups. After that, the versioning-warning in the
177177- <literal>garage</literal>-module should be updated to make sure
178178- that the
179179- <link linkend="opt-services.garage.package">package</link>-option
180180- selects the latest version on fresh setups.
181181- </para>
182182- <para>
183183- If major-releases will be abandoned by upstream, we should check
184184- first if those are needed in NixOS for a safe upgrade-path before
185185- removing those. In that case we shold keep those packages, but
186186- mark them as insecure in an expression like this (in
187187- <literal><nixpkgs/pkgs/tools/filesystem/garage/default.nix></literal>):
188188- </para>
189189- <programlisting>
190190-/* ... */
191191-{
192192- garage_0_7_3 = generic {
193193- version = "0.7.3";
194194- sha256 = "0000000000000000000000000000000000000000000000000000";
195195- eol = true;
196196- };
197197-}
198198-</programlisting>
199199- <para>
200200- Ideally we should make sure that it’s possible to jump two NixOS
201201- versions forward: i.e. the warnings and the logic in the module
202202- should guard a user to upgrade from a Garage on e.g. 22.11 to a
203203- Garage on 23.11.
204204- </para>
205205- </section>
206206-</chapter>
···11-<!-- Do not edit this file directly, edit its companion .md instead
22- and regenerate this file using nixos/doc/manual/md-to-db.sh -->
33-<chapter xmlns="http://docbook.org/ns/docbook" xmlns:xlink="http://www.w3.org/1999/xlink" xml:id="chap-gnome">
44- <title>GNOME Desktop</title>
55- <para>
66- GNOME provides a simple, yet full-featured desktop environment with
77- a focus on productivity. Its Mutter compositor supports both Wayland
88- and X server, and the GNOME Shell user interface is fully
99- customizable by extensions.
1010- </para>
1111- <section xml:id="sec-gnome-enable">
1212- <title>Enabling GNOME</title>
1313- <para>
1414- All of the core apps, optional apps, games, and core developer
1515- tools from GNOME are available.
1616- </para>
1717- <para>
1818- To enable the GNOME desktop use:
1919- </para>
2020- <programlisting>
2121-services.xserver.desktopManager.gnome.enable = true;
2222-services.xserver.displayManager.gdm.enable = true;
2323-</programlisting>
2424- <note>
2525- <para>
2626- While it is not strictly necessary to use GDM as the display
2727- manager with GNOME, it is recommended, as some features such as
2828- screen lock
2929- <link linkend="sec-gnome-faq-can-i-use-lightdm-with-gnome">might
3030- not work</link> without it.
3131- </para>
3232- </note>
3333- <para>
3434- The default applications used in NixOS are very minimal, inspired
3535- by the defaults used in
3636- <link xlink:href="https://gitlab.gnome.org/GNOME/gnome-build-meta/blob/40.0/elements/core/meta-gnome-core-utilities.bst">gnome-build-meta</link>.
3737- </para>
3838- <section xml:id="sec-gnome-without-the-apps">
3939- <title>GNOME without the apps</title>
4040- <para>
4141- If you’d like to only use the GNOME desktop and not the apps,
4242- you can disable them with:
4343- </para>
4444- <programlisting>
4545-services.gnome.core-utilities.enable = false;
4646-</programlisting>
4747- <para>
4848- and none of them will be installed.
4949- </para>
5050- <para>
5151- If you’d only like to omit a subset of the core utilities, you
5252- can use
5353- <xref linkend="opt-environment.gnome.excludePackages" />. Note
5454- that this mechanism can only exclude core utilities, games and
5555- core developer tools.
5656- </para>
5757- </section>
5858- <section xml:id="sec-gnome-disabling-services">
5959- <title>Disabling GNOME services</title>
6060- <para>
6161- It is also possible to disable many of the
6262- <link xlink:href="https://github.com/NixOS/nixpkgs/blob/b8ec4fd2a4edc4e30d02ba7b1a2cc1358f3db1d5/nixos/modules/services/x11/desktop-managers/gnome.nix#L329-L348">core
6363- services</link>. For example, if you do not need indexing files,
6464- you can disable Tracker with:
6565- </para>
6666- <programlisting>
6767-services.gnome.tracker-miners.enable = false;
6868-services.gnome.tracker.enable = false;
6969-</programlisting>
7070- <para>
7171- Note, however, that doing so is not supported and might break
7272- some applications. Notably, GNOME Music cannot work without
7373- Tracker.
7474- </para>
7575- </section>
7676- <section xml:id="sec-gnome-games">
7777- <title>GNOME games</title>
7878- <para>
7979- You can install all of the GNOME games with:
8080- </para>
8181- <programlisting>
8282-services.gnome.games.enable = true;
8383-</programlisting>
8484- </section>
8585- <section xml:id="sec-gnome-core-developer-tools">
8686- <title>GNOME core developer tools</title>
8787- <para>
8888- You can install GNOME core developer tools with:
8989- </para>
9090- <programlisting>
9191-services.gnome.core-developer-tools.enable = true;
9292-</programlisting>
9393- </section>
9494- </section>
9595- <section xml:id="sec-gnome-enable-flashback">
9696- <title>Enabling GNOME Flashback</title>
9797- <para>
9898- GNOME Flashback provides a desktop environment based on the
9999- classic GNOME 2 architecture. You can enable the default GNOME
100100- Flashback session, which uses the Metacity window manager, with:
101101- </para>
102102- <programlisting>
103103-services.xserver.desktopManager.gnome.flashback.enableMetacity = true;
104104-</programlisting>
105105- <para>
106106- It is also possible to create custom sessions that replace
107107- Metacity with a different window manager using
108108- <xref linkend="opt-services.xserver.desktopManager.gnome.flashback.customSessions" />.
109109- </para>
110110- <para>
111111- The following example uses <literal>xmonad</literal> window
112112- manager:
113113- </para>
114114- <programlisting>
115115-services.xserver.desktopManager.gnome.flashback.customSessions = [
116116- {
117117- wmName = "xmonad";
118118- wmLabel = "XMonad";
119119- wmCommand = "${pkgs.haskellPackages.xmonad}/bin/xmonad";
120120- enableGnomePanel = false;
121121- }
122122-];
123123-</programlisting>
124124- </section>
125125- <section xml:id="sec-gnome-icons-and-gtk-themes">
126126- <title>Icons and GTK Themes</title>
127127- <para>
128128- Icon themes and GTK themes don’t require any special option to
129129- install in NixOS.
130130- </para>
131131- <para>
132132- You can add them to
133133- <xref linkend="opt-environment.systemPackages" /> and switch to
134134- them with GNOME Tweaks. If you’d like to do this manually in
135135- dconf, change the values of the following keys:
136136- </para>
137137- <programlisting>
138138-/org/gnome/desktop/interface/gtk-theme
139139-/org/gnome/desktop/interface/icon-theme
140140-</programlisting>
141141- <para>
142142- in <literal>dconf-editor</literal>
143143- </para>
144144- </section>
145145- <section xml:id="sec-gnome-shell-extensions">
146146- <title>Shell Extensions</title>
147147- <para>
148148- Most Shell extensions are packaged under the
149149- <literal>gnomeExtensions</literal> attribute. Some packages that
150150- include Shell extensions, like <literal>gnome.gpaste</literal>,
151151- don’t have their extension decoupled under this attribute.
152152- </para>
153153- <para>
154154- You can install them like any other package:
155155- </para>
156156- <programlisting>
157157-environment.systemPackages = [
158158- gnomeExtensions.dash-to-dock
159159- gnomeExtensions.gsconnect
160160- gnomeExtensions.mpris-indicator-button
161161-];
162162-</programlisting>
163163- <para>
164164- Unfortunately, we lack a way for these to be managed in a
165165- completely declarative way. So you have to enable them manually
166166- with an Extensions application. It is possible to use a
167167- <link linkend="sec-gnome-gsettings-overrides">GSettings
168168- override</link> for this on
169169- <literal>org.gnome.shell.enabled-extensions</literal>, but that
170170- will only influence the default value.
171171- </para>
172172- </section>
173173- <section xml:id="sec-gnome-gsettings-overrides">
174174- <title>GSettings Overrides</title>
175175- <para>
176176- Majority of software building on the GNOME platform use GLib’s
177177- <link xlink:href="https://developer.gnome.org/gio/unstable/GSettings.html">GSettings</link>
178178- system to manage runtime configuration. For our purposes, the
179179- system consists of XML schemas describing the individual
180180- configuration options, stored in the package, and a settings
181181- backend, where the values of the settings are stored. On NixOS,
182182- like on most Linux distributions, dconf database is used as the
183183- backend.
184184- </para>
185185- <para>
186186- <link xlink:href="https://developer.gnome.org/gio/unstable/GSettings.html#id-1.4.19.2.9.25">GSettings
187187- vendor overrides</link> can be used to adjust the default values
188188- for settings of the GNOME desktop and apps by replacing the
189189- default values specified in the XML schemas. Using overrides will
190190- allow you to pre-seed user settings before you even start the
191191- session.
192192- </para>
193193- <warning>
194194- <para>
195195- Overrides really only change the default values for GSettings
196196- keys so if you or an application changes the setting value, the
197197- value set by the override will be ignored. Until
198198- <link xlink:href="https://github.com/NixOS/nixpkgs/issues/54150">NixOS’s
199199- dconf module implements changing values</link>, you will either
200200- need to keep that in mind and clear the setting from the backend
201201- using <literal>dconf reset</literal> command when that happens,
202202- or use the
203203- <link xlink:href="https://nix-community.github.io/home-manager/options.html#opt-dconf.settings">module
204204- from home-manager</link>.
205205- </para>
206206- </warning>
207207- <para>
208208- You can override the default GSettings values using the
209209- <xref linkend="opt-services.xserver.desktopManager.gnome.extraGSettingsOverrides" />
210210- option.
211211- </para>
212212- <para>
213213- Take note that whatever packages you want to override GSettings
214214- for, you need to add them to
215215- <xref linkend="opt-services.xserver.desktopManager.gnome.extraGSettingsOverridePackages" />.
216216- </para>
217217- <para>
218218- You can use <literal>dconf-editor</literal> tool to explore which
219219- GSettings you can set.
220220- </para>
221221- <section xml:id="sec-gnome-gsettings-overrides-example">
222222- <title>Example</title>
223223- <programlisting>
224224-services.xserver.desktopManager.gnome = {
225225- extraGSettingsOverrides = ''
226226- # Change default background
227227- [org.gnome.desktop.background]
228228- picture-uri='file://${pkgs.nixos-artwork.wallpapers.mosaic-blue.gnomeFilePath}'
229229-230230- # Favorite apps in gnome-shell
231231- [org.gnome.shell]
232232- favorite-apps=['org.gnome.Photos.desktop', 'org.gnome.Nautilus.desktop']
233233- '';
234234-235235- extraGSettingsOverridePackages = [
236236- pkgs.gsettings-desktop-schemas # for org.gnome.desktop
237237- pkgs.gnome.gnome-shell # for org.gnome.shell
238238- ];
239239-};
240240-</programlisting>
241241- </section>
242242- </section>
243243- <section xml:id="sec-gnome-faq">
244244- <title>Frequently Asked Questions</title>
245245- <section xml:id="sec-gnome-faq-can-i-use-lightdm-with-gnome">
246246- <title>Can I use LightDM with GNOME?</title>
247247- <para>
248248- Yes you can, and any other display-manager in NixOS.
249249- </para>
250250- <para>
251251- However, it doesn’t work correctly for the Wayland session of
252252- GNOME Shell yet, and won’t be able to lock your screen.
253253- </para>
254254- <para>
255255- See
256256- <link xlink:href="https://github.com/NixOS/nixpkgs/issues/56342">this
257257- issue.</link>
258258- </para>
259259- </section>
260260- </section>
261261-</chapter>
···11-<!-- Do not edit this file directly, edit its companion .md instead
22- and regenerate this file using nixos/doc/manual/md-to-db.sh -->
33-<chapter xmlns="http://docbook.org/ns/docbook" xmlns:xlink="http://www.w3.org/1999/xlink" xml:id="chap-pantheon">
44- <title>Pantheon Desktop</title>
55- <para>
66- Pantheon is the desktop environment created for the elementary OS
77- distribution. It is written from scratch in Vala, utilizing GNOME
88- technologies with GTK and Granite.
99- </para>
1010- <section xml:id="sec-pantheon-enable">
1111- <title>Enabling Pantheon</title>
1212- <para>
1313- All of Pantheon is working in NixOS and the applications should be
1414- available, aside from a few
1515- <link xlink:href="https://github.com/NixOS/nixpkgs/issues/58161">exceptions</link>.
1616- To enable Pantheon, set
1717- </para>
1818- <programlisting>
1919-services.xserver.desktopManager.pantheon.enable = true;
2020-</programlisting>
2121- <para>
2222- This automatically enables LightDM and Pantheon’s LightDM greeter.
2323- If you’d like to disable this, set
2424- </para>
2525- <programlisting>
2626-services.xserver.displayManager.lightdm.greeters.pantheon.enable = false;
2727-services.xserver.displayManager.lightdm.enable = false;
2828-</programlisting>
2929- <para>
3030- but please be aware using Pantheon without LightDM as a display
3131- manager will break screenlocking from the UI. The NixOS module for
3232- Pantheon installs all of Pantheon’s default applications. If you’d
3333- like to not install Pantheon’s apps, set
3434- </para>
3535- <programlisting>
3636-services.pantheon.apps.enable = false;
3737-</programlisting>
3838- <para>
3939- You can also use
4040- <xref linkend="opt-environment.pantheon.excludePackages" /> to
4141- remove any other app (like <literal>elementary-mail</literal>).
4242- </para>
4343- </section>
4444- <section xml:id="sec-pantheon-wingpanel-switchboard">
4545- <title>Wingpanel and Switchboard plugins</title>
4646- <para>
4747- Wingpanel and Switchboard work differently than they do in other
4848- distributions, as far as using plugins. You cannot install a
4949- plugin globally (like with
5050- <option>environment.systemPackages</option>) to start using it.
5151- You should instead be using the following options:
5252- </para>
5353- <itemizedlist spacing="compact">
5454- <listitem>
5555- <para>
5656- <xref linkend="opt-services.xserver.desktopManager.pantheon.extraWingpanelIndicators" />
5757- </para>
5858- </listitem>
5959- <listitem>
6060- <para>
6161- <xref linkend="opt-services.xserver.desktopManager.pantheon.extraSwitchboardPlugs" />
6262- </para>
6363- </listitem>
6464- </itemizedlist>
6565- <para>
6666- to configure the programs with plugs or indicators.
6767- </para>
6868- <para>
6969- The difference in NixOS is both these programs are patched to load
7070- plugins from a directory that is the value of an environment
7171- variable. All of which is controlled in Nix. If you need to
7272- configure the particular packages manually you can override the
7373- packages like:
7474- </para>
7575- <programlisting>
7676-wingpanel-with-indicators.override {
7777- indicators = [
7878- pkgs.some-special-indicator
7979- ];
8080-};
8181-8282-switchboard-with-plugs.override {
8383- plugs = [
8484- pkgs.some-special-plug
8585- ];
8686-};
8787-</programlisting>
8888- <para>
8989- please note that, like how the NixOS options describe these as
9090- extra plugins, this would only add to the default plugins included
9191- with the programs. If for some reason you’d like to configure
9292- which plugins to use exactly, both packages have an argument for
9393- this:
9494- </para>
9595- <programlisting>
9696-wingpanel-with-indicators.override {
9797- useDefaultIndicators = false;
9898- indicators = specialListOfIndicators;
9999-};
100100-101101-switchboard-with-plugs.override {
102102- useDefaultPlugs = false;
103103- plugs = specialListOfPlugs;
104104-};
105105-</programlisting>
106106- <para>
107107- this could be most useful for testing a particular plug-in in
108108- isolation.
109109- </para>
110110- </section>
111111- <section xml:id="sec-pantheon-faq">
112112- <title>FAQ</title>
113113- <variablelist spacing="compact">
114114- <varlistentry>
115115- <term>
116116- <anchor xml:id="sec-pantheon-faq-messed-up-theme" />I have
117117- switched from a different desktop and Pantheon’s theming looks
118118- messed up.
119119- </term>
120120- <listitem>
121121- <para>
122122- Open Switchboard and go to: Administration → About → Restore
123123- Default Settings → Restore Settings. This will reset any
124124- dconf settings to their Pantheon defaults. Note this could
125125- reset certain GNOME specific preferences if that desktop was
126126- used prior.
127127- </para>
128128- </listitem>
129129- </varlistentry>
130130- <varlistentry>
131131- <term>
132132- <anchor xml:id="sec-pantheon-faq-gnome-and-pantheon" />I
133133- cannot enable both GNOME and Pantheon.
134134- </term>
135135- <listitem>
136136- <para>
137137- This is a known
138138- <link xlink:href="https://github.com/NixOS/nixpkgs/issues/64611">issue</link>
139139- and there is no known workaround.
140140- </para>
141141- </listitem>
142142- </varlistentry>
143143- <varlistentry>
144144- <term>
145145- <anchor xml:id="sec-pantheon-faq-appcenter" />Does AppCenter
146146- work, or is it available?
147147- </term>
148148- <listitem>
149149- <para>
150150- AppCenter has been available since 20.03. Starting from
151151- 21.11, the Flatpak backend should work so you can install
152152- some Flatpak applications using it. However, due to missing
153153- appstream metadata, the Packagekit backend does not function
154154- currently. See this
155155- <link xlink:href="https://github.com/NixOS/nixpkgs/issues/15932">issue</link>.
156156- </para>
157157- <para>
158158- If you are using Pantheon, AppCenter should be installed by
159159- default if you have
160160- <link linkend="module-services-flatpak">Flatpak
161161- support</link> enabled. If you also wish to add the
162162- <literal>appcenter</literal> Flatpak remote:
163163- </para>
164164- <programlisting>
165165-$ flatpak remote-add --if-not-exists appcenter https://flatpak.elementary.io/repo.flatpakrepo
166166-</programlisting>
167167- </listitem>
168168- </varlistentry>
169169- </variablelist>
170170- </section>
171171-</chapter>
···11-<!-- Do not edit this file directly, edit its companion .md instead
22- and regenerate this file using nixos/doc/manual/md-to-db.sh -->
33-<chapter xmlns="http://docbook.org/ns/docbook" xmlns:xlink="http://www.w3.org/1999/xlink" xml:id="sec-bootloader-external">
44- <title>External Bootloader Backends</title>
55- <para>
66- NixOS has support for several bootloader backends by default:
77- systemd-boot, grub, uboot, etc. The built-in bootloader backend
88- support is generic and supports most use cases. Some users may
99- prefer to create advanced workflows around managing the bootloader
1010- and bootable entries.
1111- </para>
1212- <para>
1313- You can replace the built-in bootloader support with your own
1414- tooling using the <quote>external</quote> bootloader option.
1515- </para>
1616- <para>
1717- Imagine you have created a new package called FooBoot. FooBoot
1818- provides a program at
1919- <literal>${pkgs.fooboot}/bin/fooboot-install</literal> which takes
2020- the system closure’s path as its only argument and configures the
2121- system’s bootloader.
2222- </para>
2323- <para>
2424- You can enable FooBoot like this:
2525- </para>
2626- <programlisting language="nix">
2727-{ pkgs, ... }: {
2828- boot.loader.external = {
2929- enable = true;
3030- installHook = "${pkgs.fooboot}/bin/fooboot-install";
3131- };
3232-}
3333-</programlisting>
3434- <section xml:id="sec-bootloader-external-developing">
3535- <title>Developing Custom Bootloader Backends</title>
3636- <para>
3737- Bootloaders should use
3838- <link xlink:href="https://github.com/NixOS/rfcs/pull/125">RFC-0125</link>’s
3939- Bootspec format and synthesis tools to identify the key properties
4040- for bootable system generations.
4141- </para>
4242- </section>
4343-</chapter>
+63
pkgs/tools/nix/nixos-render-docs/default.nix
···11+{ lib
22+, stdenv
33+, python3
44+, python3Minimal
55+}:
66+77+let
88+ # python3Minimal can't be overridden with packages on Darwin, due to a missing framework.
99+ # Instead of modifying stdenv, we take the easy way out, since most people on Darwin will
1010+ # just be hacking on the Nixpkgs manual (which also uses make-options-doc).
1111+ python = ((if stdenv.isDarwin then python3 else python3Minimal).override {
1212+ self = python;
1313+ includeSiteCustomize = true;
1414+ });
1515+1616+ # TODO add our own small test suite, maybe add tests for these deps to channels?
1717+ markdown-it-py-no-tests = python.pkgs.markdown-it-py.override {
1818+ disableTests = true;
1919+ };
2020+ mdit-py-plugins-no-tests = python.pkgs.mdit-py-plugins.override {
2121+ markdown-it-py = markdown-it-py-no-tests;
2222+ disableTests = true;
2323+ };
2424+in
2525+2626+python.pkgs.buildPythonApplication {
2727+ pname = "nixos-render-docs";
2828+ version = "0.0";
2929+ format = "pyproject";
3030+3131+ src = lib.cleanSourceWith {
3232+ filter = name: type:
3333+ lib.cleanSourceFilter name type
3434+ && ! (type == "directory"
3535+ && builtins.elem
3636+ (baseNameOf name)
3737+ [
3838+ ".pytest_cache"
3939+ ".mypy_cache"
4040+ "__pycache__"
4141+ ]);
4242+ src = ./src;
4343+ };
4444+4545+ nativeBuildInputs = [
4646+ python.pkgs.setuptools
4747+ python.pkgs.pytestCheckHook
4848+ ];
4949+5050+ propagatedBuildInputs = [
5151+ markdown-it-py-no-tests
5252+ mdit-py-plugins-no-tests
5353+ python.pkgs.frozendict
5454+ ];
5555+5656+ pytestFlagsArray = [ "-vvrP" "tests/" ];
5757+5858+ meta = with lib; {
5959+ description = "Renderer for NixOS manual and option docs";
6060+ license = licenses.mit;
6161+ maintainers = [ ];
6262+ };
6363+}