forked from
tangled.org/core
fork
Configure Feed
Select the types of activity you want to include in your feed.
Monorepo for Tangled
fork
Configure Feed
Select the types of activity you want to include in your feed.
1{
2 config,
3 lib,
4 ...
5}: let
6 cfg = config.services.tangled.spindle;
7in
8 with lib; {
9 options = {
10 services.tangled.spindle = {
11 enable = mkOption {
12 type = types.bool;
13 default = false;
14 description = "Enable a tangled spindle";
15 };
16 package = mkOption {
17 type = types.package;
18 description = "Package to use for the spindle";
19 };
20
21 server = {
22 listenAddr = mkOption {
23 type = types.str;
24 default = "0.0.0.0:6555";
25 description = "Address to listen on";
26 };
27
28 dbPath = mkOption {
29 type = types.path;
30 default = "/var/lib/spindle/spindle.db";
31 description = "Path to the database file";
32 };
33
34 hostname = mkOption {
35 type = types.str;
36 example = "my.spindle.com";
37 description = "Hostname for the server (required)";
38 };
39
40 plcUrl = mkOption {
41 type = types.str;
42 default = "https://plc.directory";
43 description = "atproto PLC directory";
44 };
45
46 jetstreamEndpoint = mkOption {
47 type = types.str;
48 default = "wss://jetstream1.us-west.bsky.network/subscribe";
49 description = "Jetstream endpoint to subscribe to";
50 };
51
52 dev = mkOption {
53 type = types.bool;
54 default = false;
55 description = "Enable development mode (disables signature verification)";
56 };
57
58 owner = mkOption {
59 type = types.str;
60 example = "did:plc:qfpnj4og54vl56wngdriaxug";
61 description = "DID of owner (required)";
62 };
63
64 maxJobCount = mkOption {
65 type = types.int;
66 default = 2;
67 example = 5;
68 description = "Maximum number of concurrent jobs to run";
69 };
70
71 queueSize = mkOption {
72 type = types.int;
73 default = 100;
74 example = 100;
75 description = "Maximum number of jobs queue up";
76 };
77
78 secrets = {
79 provider = mkOption {
80 type = types.str;
81 default = "sqlite";
82 description = "Backend to use for secret management, valid options are 'sqlite', and 'openbao'.";
83 };
84
85 openbao = {
86 proxyAddr = mkOption {
87 type = types.str;
88 default = "http://127.0.0.1:8200";
89 };
90 mount = mkOption {
91 type = types.str;
92 default = "spindle";
93 };
94 };
95 };
96 };
97
98 pipelines = {
99 nixery = mkOption {
100 type = types.str;
101 default = "nixery.tangled.sh"; # note: this is *not* on tangled.org yet
102 description = "Nixery instance to use";
103 };
104
105 workflowTimeout = mkOption {
106 type = types.str;
107 default = "5m";
108 description = "Timeout for each step of a pipeline";
109 };
110 };
111 };
112 };
113
114 config = mkIf cfg.enable {
115 virtualisation.docker.enable = true;
116
117 systemd.services.spindle = {
118 description = "spindle service";
119 after = ["network.target" "docker.service"];
120 wantedBy = ["multi-user.target"];
121 serviceConfig = {
122 LogsDirectory = "spindle";
123 StateDirectory = "spindle";
124 Environment = [
125 "SPINDLE_SERVER_LISTEN_ADDR=${cfg.server.listenAddr}"
126 "SPINDLE_SERVER_DB_PATH=${cfg.server.dbPath}"
127 "SPINDLE_SERVER_HOSTNAME=${cfg.server.hostname}"
128 "SPINDLE_SERVER_PLC_URL=${cfg.server.plcUrl}"
129 "SPINDLE_SERVER_JETSTREAM_ENDPOINT=${cfg.server.jetstreamEndpoint}"
130 "SPINDLE_SERVER_DEV=${lib.boolToString cfg.server.dev}"
131 "SPINDLE_SERVER_OWNER=${cfg.server.owner}"
132 "SPINDLE_SERVER_MAX_JOB_COUNT=${toString cfg.server.maxJobCount}"
133 "SPINDLE_SERVER_QUEUE_SIZE=${toString cfg.server.queueSize}"
134 "SPINDLE_SERVER_SECRETS_PROVIDER=${cfg.server.secrets.provider}"
135 "SPINDLE_SERVER_SECRETS_OPENBAO_PROXY_ADDR=${cfg.server.secrets.openbao.proxyAddr}"
136 "SPINDLE_SERVER_SECRETS_OPENBAO_MOUNT=${cfg.server.secrets.openbao.mount}"
137 "SPINDLE_NIXERY_PIPELINES_NIXERY=${cfg.pipelines.nixery}"
138 "SPINDLE_NIXERY_PIPELINES_WORKFLOW_TIMEOUT=${cfg.pipelines.workflowTimeout}"
139 ];
140 ExecStart = "${cfg.package}/bin/spindle";
141 Restart = "always";
142 };
143 };
144 };
145 }