1{ config, lib, pkgs, ... }:
2
3with lib;
4
5let
6
7 cfg = config.services.emacs;
8
9 editorScript = pkgs.writeScriptBin "emacseditor" ''
10 #!${pkgs.runtimeShell}
11 if [ -z "$1" ]; then
12 exec ${cfg.package}/bin/emacsclient --create-frame --alternate-editor ${cfg.package}/bin/emacs
13 else
14 exec ${cfg.package}/bin/emacsclient --alternate-editor ${cfg.package}/bin/emacs "$@"
15 fi
16 '';
17
18desktopApplicationFile = pkgs.writeTextFile {
19 name = "emacsclient.desktop";
20 destination = "/share/applications/emacsclient.desktop";
21 text = ''
22[Desktop Entry]
23Name=Emacsclient
24GenericName=Text Editor
25Comment=Edit text
26MimeType=text/english;text/plain;text/x-makefile;text/x-c++hdr;text/x-c++src;text/x-chdr;text/x-csrc;text/x-java;text/x-moc;text/x-pascal;text/x-tcl;text/x-tex;application/x-shellscript;text/x-c;text/x-c++;
27Exec=emacseditor %F
28Icon=emacs
29Type=Application
30Terminal=false
31Categories=Development;TextEditor;
32StartupWMClass=Emacs
33Keywords=Text;Editor;
34'';
35};
36
37in {
38
39 options.services.emacs = {
40 enable = mkOption {
41 type = types.bool;
42 default = false;
43 description = ''
44 Whether to enable a user service for the Emacs daemon. Use <literal>emacsclient</literal> to connect to the
45 daemon. If <literal>true</literal>, <varname>services.emacs.install</varname> is
46 considered <literal>true</literal>, whatever its value.
47 '';
48 };
49
50 install = mkOption {
51 type = types.bool;
52 default = false;
53 description = ''
54 Whether to install a user service for the Emacs daemon. Once
55 the service is started, use emacsclient to connect to the
56 daemon.
57
58 The service must be manually started for each user with
59 "systemctl --user start emacs" or globally through
60 <varname>services.emacs.enable</varname>.
61 '';
62 };
63
64
65 package = mkOption {
66 type = types.package;
67 default = pkgs.emacs;
68 defaultText = "pkgs.emacs";
69 description = ''
70 emacs derivation to use.
71 '';
72 };
73
74 defaultEditor = mkOption {
75 type = types.bool;
76 default = false;
77 description = ''
78 When enabled, configures emacsclient to be the default editor
79 using the EDITOR environment variable.
80 '';
81 };
82 };
83
84 config = mkIf (cfg.enable || cfg.install) {
85 systemd.user.services.emacs = {
86 description = "Emacs: the extensible, self-documenting text editor";
87
88 serviceConfig = {
89 Type = "forking";
90 ExecStart = "${pkgs.bash}/bin/bash -c 'source ${config.system.build.setEnvironment}; exec ${cfg.package}/bin/emacs --daemon'";
91 ExecStop = "${cfg.package}/bin/emacsclient --eval (kill-emacs)";
92 Restart = "always";
93 };
94 } // optionalAttrs cfg.enable { wantedBy = [ "default.target" ]; };
95
96 environment.systemPackages = [ cfg.package editorScript desktopApplicationFile ];
97
98 environment.variables = {
99 # This is required so that GTK applications launched from Emacs
100 # get properly themed:
101 GTK_DATA_PREFIX = "${config.system.path}";
102 } // (if cfg.defaultEditor then {
103 EDITOR = mkOverride 900 "${editorScript}/bin/emacseditor";
104 } else {});
105 };
106
107 meta.doc = ./emacs.xml;
108}