+3
-3
flake.lock
+3
-3
flake.lock
···
35
35
"htmx-ws-src": {
36
36
"flake": false,
37
37
"locked": {
38
-
"narHash": "sha256-XbUFiv94ZPB6VVULoTWOsje5Gq1I+IT72lMc4CpUYrY=",
38
+
"narHash": "sha256-2fg6KyEJoO24q0fQqbz9RMaYNPQrMwpZh29tkSqdqGY=",
39
39
"type": "file",
40
-
"url": "https://unpkg.com/htmx.org@2.0.4/dist/ext/ws.js"
40
+
"url": "https://cdn.jsdelivr.net/npm/htmx-ext-ws@2.0.2"
41
41
},
42
42
"original": {
43
43
"type": "file",
44
-
"url": "https://unpkg.com/htmx.org@2.0.4/dist/ext/ws.js"
44
+
"url": "https://cdn.jsdelivr.net/npm/htmx-ext-ws@2.0.2"
45
45
}
46
46
},
47
47
"ibm-plex-mono-src": {
+12
-2
flake.nix
+12
-2
flake.nix
···
12
12
flake = false;
13
13
};
14
14
htmx-ws-src = {
15
-
url = "https://unpkg.com/htmx.org@2.0.4/dist/ext/ws.js";
15
+
# strange errors in consle that i can't really make out
16
+
# url = "https://unpkg.com/htmx.org@2.0.4/dist/ext/ws.js";
17
+
url = "https://cdn.jsdelivr.net/npm/htmx-ext-ws@2.0.2";
16
18
flake = false;
17
19
};
18
20
lucide-src = {
···
64
66
inherit htmx-src htmx-ws-src lucide-src inter-fonts-src ibm-plex-mono-src goModHash gitignoreSource;
65
67
};
66
68
knotDeps = {
69
+
inherit goModHash gitignoreSource;
70
+
};
71
+
spindleDeps = {
67
72
inherit goModHash gitignoreSource;
68
73
};
69
74
mkPackageSet = pkgs: {
70
75
lexgen = pkgs.callPackage ./nix/pkgs/lexgen.nix {inherit indigo;};
71
76
appview = pkgs.callPackage ./nix/pkgs/appview.nix appviewDeps;
72
77
knot = pkgs.callPackage ./nix/pkgs/knot.nix {};
78
+
spindle = pkgs.callPackage ./nix/pkgs/spindle.nix spindleDeps;
73
79
knot-unwrapped = pkgs.callPackage ./nix/pkgs/knot-unwrapped.nix knotDeps;
74
80
sqlite-lib = pkgs.callPackage ./nix/pkgs/sqlite-lib.nix {
75
81
inherit (pkgs) gcc;
···
89
95
lexgen = pkgs.lexgen;
90
96
knot = pkgs.knot;
91
97
knot-unwrapped = pkgs.knot-unwrapped;
98
+
spindle = pkgs.spindle;
92
99
genjwks = pkgs.genjwks;
93
100
sqlite-lib = pkgs.sqlite-lib;
94
101
95
102
pkgsStatic-appview = staticPkgs.appview;
96
103
pkgsStatic-knot = staticPkgs.knot;
97
104
pkgsStatic-knot-unwrapped = staticPkgs.knot-unwrapped;
105
+
pkgsStatic-spindle = staticPkgs.spindle;
98
106
pkgsStatic-sqlite-lib = staticPkgs.sqlite-lib;
99
107
100
108
pkgsCross-gnu64-pkgsStatic-appview = crossPkgs.appview;
101
109
pkgsCross-gnu64-pkgsStatic-knot = crossPkgs.knot;
102
110
pkgsCross-gnu64-pkgsStatic-knot-unwrapped = crossPkgs.knot-unwrapped;
111
+
pkgsCross-gnu64-pkgsStatic-spindle = crossPkgs.spindle;
103
112
});
104
113
defaultPackage = forAllSystems (system: nixpkgsFor.${system}.appview);
105
114
formatter = forAllSystems (system: nixpkgsFor."${system}".alejandra);
···
167
176
168
177
nixosModules.appview = import ./nix/modules/appview.nix {inherit self;};
169
178
nixosModules.knot = import ./nix/modules/knot.nix {inherit self;};
170
-
nixosConfigurations.knotVM = import ./nix/vm.nix {inherit self nixpkgs;};
179
+
nixosModules.spindle = import ./nix/modules/spindle.nix {inherit self;};
180
+
nixosConfigurations.vm = import ./nix/vm.nix {inherit self nixpkgs;};
171
181
};
172
182
}
+2
-4
nix/modules/knot.nix
+2
-4
nix/modules/knot.nix
···
101
101
102
102
system.activationScripts.gitConfig = ''
103
103
mkdir -p "${cfg.repo.scanPath}"
104
-
chown -R ${cfg.gitUser}:${cfg.gitUser} \
105
-
"${cfg.repo.scanPath}"
104
+
chown -R ${cfg.gitUser}:${cfg.gitUser} "${cfg.repo.scanPath}"
106
105
107
106
mkdir -p "${cfg.stateDir}/.config/git"
108
107
cat > "${cfg.stateDir}/.config/git/config" << EOF
···
110
109
name = Git User
111
110
email = git@example.com
112
111
EOF
113
-
chown -R ${cfg.gitUser}:${cfg.gitUser} \
114
-
"${cfg.stateDir}"
112
+
chown -R ${cfg.gitUser}:${cfg.gitUser} "${cfg.stateDir}"
115
113
'';
116
114
117
115
users.users.${cfg.gitUser} = {
+99
nix/modules/spindle.nix
+99
nix/modules/spindle.nix
···
1
+
{self}: {
2
+
config,
3
+
pkgs,
4
+
lib,
5
+
...
6
+
}: let
7
+
cfg = config.services.tangled-spindle;
8
+
in
9
+
with lib; {
10
+
options = {
11
+
services.tangled-spindle = {
12
+
enable = mkOption {
13
+
type = types.bool;
14
+
default = false;
15
+
description = "Enable a tangled spindle";
16
+
};
17
+
18
+
server = {
19
+
listenAddr = mkOption {
20
+
type = types.str;
21
+
default = "0.0.0.0:6555";
22
+
description = "Address to listen on";
23
+
};
24
+
25
+
dbPath = mkOption {
26
+
type = types.path;
27
+
default = "/var/lib/spindle/spindle.db";
28
+
description = "Path to the database file";
29
+
};
30
+
31
+
hostname = mkOption {
32
+
type = types.str;
33
+
example = "spindle.tangled.sh";
34
+
description = "Hostname for the server (required)";
35
+
};
36
+
37
+
jetstreamEndpoint = mkOption {
38
+
type = types.str;
39
+
default = "wss://jetstream1.us-west.bsky.network/subscribe";
40
+
description = "Jetstream endpoint to subscribe to";
41
+
};
42
+
43
+
dev = mkOption {
44
+
type = types.bool;
45
+
default = false;
46
+
description = "Enable development mode (disables signature verification)";
47
+
};
48
+
49
+
owner = mkOption {
50
+
type = types.str;
51
+
example = "did:plc:qfpnj4og54vl56wngdriaxug";
52
+
description = "DID of owner (required)";
53
+
};
54
+
};
55
+
56
+
pipelines = {
57
+
nixery = mkOption {
58
+
type = types.str;
59
+
default = "nixery.tangled.sh";
60
+
description = "Nixery instance to use";
61
+
};
62
+
63
+
stepTimeout = mkOption {
64
+
type = types.str;
65
+
default = "5m";
66
+
description = "Timeout for each step of a pipeline";
67
+
};
68
+
};
69
+
};
70
+
};
71
+
72
+
config = mkIf cfg.enable {
73
+
virtualisation.docker.enable = true;
74
+
75
+
systemd.services.spindle = {
76
+
description = "spindle service";
77
+
after = ["network.target" "docker.service"];
78
+
wantedBy = ["multi-user.target"];
79
+
serviceConfig = {
80
+
LogsDirectory = "spindle";
81
+
StateDirectory = "spindle";
82
+
Environment = [
83
+
"SPINDLE_SERVER_LISTEN_ADDR=${cfg.server.listenAddr}"
84
+
"SPINDLE_SERVER_DB_PATH=${cfg.server.dbPath}"
85
+
"SPINDLE_SERVER_HOSTNAME=${cfg.server.hostname}"
86
+
"SPINDLE_SERVER_JETSTREAM=${cfg.server.jetstreamEndpoint}"
87
+
"SPINDLE_SERVER_DEV=${lib.boolToString cfg.server.dev}"
88
+
"SPINDLE_SERVER_OWNER=${cfg.server.owner}"
89
+
"SPINDLE_PIPELINES_NIXERY=${cfg.pipelines.nixery}"
90
+
"SPINDLE_PIPELINES_STEP_TIMEOUT=${cfg.pipelines.stepTimeout}"
91
+
];
92
+
ExecStart = "${self.packages.${pkgs.system}.spindle}/bin/spindle";
93
+
Restart = "always";
94
+
};
95
+
};
96
+
97
+
networking.firewall.allowedTCPPorts = mkIf cfg.openFirewall [22];
98
+
};
99
+
}
+22
nix/pkgs/spindle.nix
+22
nix/pkgs/spindle.nix
···
1
+
{
2
+
buildGoModule,
3
+
stdenv,
4
+
sqlite-lib,
5
+
goModHash,
6
+
gitignoreSource,
7
+
}:
8
+
buildGoModule {
9
+
pname = "spindle";
10
+
version = "0.1.0";
11
+
src = gitignoreSource ../..;
12
+
13
+
doCheck = false;
14
+
15
+
subPackages = ["cmd/spindle"];
16
+
vendorHash = goModHash;
17
+
tags = "libsqlite3";
18
+
19
+
env.CGO_CFLAGS = "-I ${sqlite-lib}/include ";
20
+
env.CGO_LDFLAGS = "-L ${sqlite-lib}/lib";
21
+
env.CGO_ENABLED = 1;
22
+
}
+35
-3
nix/vm.nix
+35
-3
nix/vm.nix
···
6
6
system = "x86_64-linux";
7
7
modules = [
8
8
self.nixosModules.knot
9
+
self.nixosModules.spindle
9
10
({
10
11
config,
11
12
pkgs,
12
13
...
13
14
}: {
14
-
virtualisation.memorySize = 2048;
15
-
virtualisation.diskSize = 10 * 1024;
16
-
virtualisation.cores = 2;
15
+
virtualisation = {
16
+
memorySize = 2048;
17
+
diskSize = 10 * 1024;
18
+
cores = 2;
19
+
forwardPorts = [
20
+
# ssh
21
+
{
22
+
from = "host";
23
+
host.port = 2222;
24
+
guest.port = 22;
25
+
}
26
+
# knot
27
+
{
28
+
from = "host";
29
+
host.port = 6000;
30
+
guest.port = 6000;
31
+
}
32
+
# spindle
33
+
{
34
+
from = "host";
35
+
host.port = 6555;
36
+
guest.port = 6555;
37
+
}
38
+
];
39
+
};
17
40
services.getty.autologinUser = "root";
18
41
environment.systemPackages = with pkgs; [curl vim git];
19
42
systemd.tmpfiles.rules = let
···
29
52
secretFile = "/var/lib/knot/secret";
30
53
hostname = "localhost:6000";
31
54
listenAddr = "0.0.0.0:6000";
55
+
};
56
+
};
57
+
services.tangled-spindle = {
58
+
enable = true;
59
+
server = {
60
+
owner = "did:plc:qfpnj4og54vl56wngdriaxug";
61
+
hostname = "localhost:6555";
62
+
listenAddr = "0.0.0.0:6555";
63
+
dev = true;
32
64
};
33
65
};
34
66
})