1{
2 config,
3 lib,
4 pkgs,
5 ...
6}:
7let
8 cfg = config.services.localtimed;
9in
10{
11 imports = [ (lib.mkRenamedOptionModule [ "services" "localtime" ] [ "services" "localtimed" ]) ];
12
13 options = {
14 services.localtimed = {
15 enable = lib.mkOption {
16 type = lib.types.bool;
17 default = false;
18 description = ''
19 Enable `localtimed`, a simple daemon for keeping the
20 system timezone up-to-date based on the current location. It uses
21 geoclue2 to determine the current location.
22
23 To avoid silent overriding by the service, if you have explicitly set a
24 timezone, either remove it or ensure that it is set with a lower priority
25 than the default value using `lib.mkDefault` or `lib.mkOverride`. This is
26 to make the choice deliberate. An error will be presented otherwise.
27 '';
28 };
29 package = lib.mkPackageOption pkgs "localtime" { };
30 geoclue2Package = lib.mkPackageOption pkgs "Geoclue2" { default = "geoclue2-with-demo-agent"; };
31 };
32 };
33
34 config = lib.mkIf cfg.enable {
35 # This will give users an error if they have set an explicit time
36 # zone, rather than having the service silently override it.
37 time.timeZone = null;
38
39 services.geoclue2.appConfig.localtimed = {
40 isAllowed = true;
41 isSystem = true;
42 users = [ (toString config.ids.uids.localtimed) ];
43 };
44
45 # Install the polkit rules.
46 environment.systemPackages = [ cfg.package ];
47
48 systemd.services.localtimed = {
49 wantedBy = [ "multi-user.target" ];
50 partOf = [ "localtimed-geoclue-agent.service" ];
51 after = [ "localtimed-geoclue-agent.service" ];
52 serviceConfig = {
53 ExecStart = "${cfg.package}/bin/localtimed";
54 Restart = "on-failure";
55 Type = "exec";
56 User = "localtimed";
57 };
58 };
59
60 systemd.services.localtimed-geoclue-agent = {
61 wantedBy = [ "multi-user.target" ];
62 partOf = [ "geoclue.service" ];
63 after = [ "geoclue.service" ];
64 serviceConfig = {
65 ExecStart = "${cfg.geoclue2Package}/libexec/geoclue-2.0/demos/agent";
66 Restart = "on-failure";
67 Type = "exec";
68 User = "localtimed";
69 };
70 };
71
72 users = {
73 users.localtimed = {
74 uid = config.ids.uids.localtimed;
75 group = "localtimed";
76 };
77 groups.localtimed.gid = config.ids.gids.localtimed;
78 };
79 };
80}