@lamalibre/create-lamaste 4.0.0 → 4.2.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (66) hide show
  1. package/package.json +2 -2
  2. package/scripts/lamaste-priv +21 -2
  3. package/src/lib/oidc-issuer-key.js +124 -0
  4. package/src/lib/relay-services.js +4 -0
  5. package/src/lib/service-config.js +16 -0
  6. package/vendor/docs/00-introduction/how-it-works.md +2 -2
  7. package/vendor/docs/00-introduction/quickstart.md +5 -5
  8. package/vendor/docs/00-introduction/what-is-lamaste.md +5 -5
  9. package/vendor/docs/01-concepts/authentication.md +45 -1
  10. package/vendor/docs/01-concepts/certificates.md +3 -3
  11. package/vendor/docs/01-concepts/mtls.md +2 -2
  12. package/vendor/docs/01-concepts/security-model.md +1 -1
  13. package/vendor/docs/01-concepts/tickets.md +2 -2
  14. package/vendor/docs/01-concepts/tunneling.md +4 -4
  15. package/vendor/docs/02-guides/agent-setup.md +3 -3
  16. package/vendor/docs/02-guides/certificate-management.md +2 -2
  17. package/vendor/docs/02-guides/cloud-provisioning.md +3 -3
  18. package/vendor/docs/02-guides/desktop-app-setup.md +10 -10
  19. package/vendor/docs/02-guides/installation.md +3 -3
  20. package/vendor/docs/02-guides/onboarding.md +2 -2
  21. package/vendor/docs/02-guides/standalone-plugin-with-tickets.md +2 -2
  22. package/vendor/docs/03-architecture/installer-flow.md +2 -2
  23. package/vendor/docs/03-architecture/installer.md +6 -5
  24. package/vendor/docs/03-architecture/management-flow.md +1 -1
  25. package/vendor/docs/03-architecture/overview.md +5 -5
  26. package/vendor/docs/03-architecture/panel-client.md +6 -6
  27. package/vendor/docs/03-architecture/panel-server.md +2 -2
  28. package/vendor/docs/03-architecture/state-management.md +2 -2
  29. package/vendor/docs/03-architecture/system-overview.md +1 -1
  30. package/vendor/docs/04-api-reference/onboarding.md +1 -1
  31. package/vendor/docs/04-api-reference/overview.md +111 -105
  32. package/vendor/docs/04-api-reference/registry-and-oidc.md +207 -0
  33. package/vendor/docs/05-operations/backup-and-restore.md +1 -1
  34. package/vendor/docs/05-operations/uninstalling.md +1 -1
  35. package/vendor/docs/05-operations/upgrades.md +6 -5
  36. package/vendor/docs/06-reference/config-files.md +103 -45
  37. package/vendor/docs/06-reference/glossary.md +3 -3
  38. package/vendor/docs/06-reference/installer-flags.md +13 -13
  39. package/vendor/docs/06-reference/ports-and-services.md +1 -1
  40. package/vendor/docs/06-reference/troubleshooting.md +8 -8
  41. package/vendor/docs/_index.json +5 -0
  42. package/vendor/docs/gatekeeper-design.md +8 -8
  43. package/vendor/docs/identity-directory-design.md +443 -0
  44. package/vendor/docs/package.json +1 -1
  45. package/vendor/docs/todo/lib-cli-desktop-refactor.md +27 -27
  46. package/vendor/gatekeeper/package.json +1 -1
  47. package/vendor/server/bin/lamaste-server.js +10 -1
  48. package/vendor/server/package.json +4 -3
  49. package/vendor/server/src/commands/plugins.js +200 -158
  50. package/vendor/server/src/commands/registry-credential.js +142 -0
  51. package/vendor/server/src/panel-api.js +86 -39
  52. package/vendor/server-ui/dist/assets/{index-B0nWuUyL.js → index-B5Wp8lu-.js} +26 -26
  53. package/vendor/server-ui/dist/index.html +1 -1
  54. package/vendor/serverd/package.json +5 -2
  55. package/vendor/serverd/src/index.js +11 -0
  56. package/vendor/serverd/src/lib/authelia.js +11 -0
  57. package/vendor/serverd/src/lib/migrations/state/0005_plugin_hosting.sql +3 -0
  58. package/vendor/serverd/src/lib/plugin-oidc.js +233 -0
  59. package/vendor/serverd/src/lib/plugins.js +37 -5
  60. package/vendor/serverd/src/lib/registry-credential.js +145 -0
  61. package/vendor/serverd/src/routes/management/agents.js +81 -0
  62. package/vendor/serverd/src/routes/management/plugins.js +65 -2
  63. package/vendor/serverd/src/routes/management/registry-credential.js +170 -0
  64. package/vendor/serverd/src/routes/management/storage.js +10 -2
  65. package/vendor/serverd/src/routes/management/users.js +31 -0
  66. package/vendor/serverd/src/routes/management.js +2 -0
@@ -4,48 +4,51 @@
4
4
 
5
5
  ## File Overview
6
6
 
7
- | File | Format | Owner | Mode | Purpose |
8
- | ---------------------------------------------------------- | ---------- | ------------------------ | ---- | ------------------------------------------------------------------------------- |
9
- | `/etc/lamalibre/lamaste/panel.json` | JSON | lamaste:lamaste | 0600 | Panel server configuration |
10
- | `/etc/lamalibre/lamaste/tunnels.json` | JSON | lamaste:lamaste | 0600 | Tunnel definitions |
11
- | `/etc/lamalibre/lamaste/sites.json` | JSON | lamaste:lamaste | 0600 | Static site definitions |
12
- | `/etc/lamalibre/lamaste/chisel-credentials.json` | JSON | lamaste:lamaste | 0600 | Per-agent Chisel credentials (source of truth for the authfile) |
13
- | `/etc/lamalibre/lamaste/chisel-users` | JSON | lamaste:lamaste-chisel | 0640 | Chisel `--authfile`: per-agent credentials and port grants (rendered) |
14
- | `/etc/lamalibre/lamaste/chisel-sentinel` | text | lamaste:lamaste | 0600 | Password of the `lamaste-no-grants` sentinel user |
15
- | `/etc/lamalibre/lamaste/chisel-server.key` | PEM | lamaste:lamaste-chisel | 0640 | Chisel SSH host key (`--keyfile`), generated by the panel at onboarding |
16
- | `/etc/authelia/configuration.yml` | YAML | lamaste:lamaste-authelia | 0640 | Authelia server configuration |
17
- | `/etc/authelia/users.yml` | YAML | lamaste:lamaste-authelia | 0660 | User database (Authelia rewrites it on a password change) |
18
- | `/etc/authelia/.secrets.json` | JSON | lamaste:lamaste-authelia | 0600 | Authelia secrets (panel only) |
19
- | `/etc/lamalibre/lamaste/ticket-scopes.json` | JSON | lamaste:lamaste | 0600 | Ticket scope registry |
20
- | `/etc/lamalibre/lamaste/tickets.json` | JSON | lamaste:lamaste | 0600 | Ticket and session store |
21
- | `/etc/lamalibre/lamaste/invitations.json` | JSON | lamaste:lamaste | 0600 | Pending user invitations |
22
- | `/etc/lamalibre/lamaste/plugins.json` | JSON | lamaste:lamaste | 0600 | Plugin registry |
23
- | `/etc/lamalibre/lamaste/storage-config.json` | JSON | lamaste:lamaste | 0600 | Storage server registry and plugin bindings (credentials AES-256-GCM encrypted) |
24
- | `/etc/lamalibre/lamaste/storage-master.key` | Binary | lamaste:lamaste | 0600 | 32-byte master key for storage credential encryption |
25
- | `/etc/lamalibre/lamaste/groups.json` | JSON | lamaste:lamaste | 0600 | Lamaste group definitions and membership |
26
- | `/etc/lamalibre/lamaste/access-grants.json` | JSON | lamaste:lamaste | 0600 | Generic access grants (principal → resource) |
27
- | `/etc/lamalibre/lamaste/gatekeeper.json` | JSON | lamaste:lamaste | 0600 | Gatekeeper settings (cache TTL, admin contact, logging) |
28
- | `/etc/lamalibre/lamaste/access-request-log.json` | JSON | lamaste:lamaste | 0600 | Optional denied access log |
29
- | `/etc/lamalibre/lamaste/pki/enrollment-tokens.json` | JSON | lamaste:lamaste | 0600 | One-time enrollment tokens for hardware-bound enrollment |
30
- | `/etc/lamalibre/lamaste/pki/revoked.json` | JSON | lamaste:lamaste | 0600 | Revoked certificate serial numbers |
31
- | `/etc/lamalibre/lamaste/pki/agents/registry.json` | JSON | lamaste:lamaste | 0600 | Agent certificate metadata |
32
- | `/etc/nginx/sites-available/lamalibre-lamaste-*` | nginx conf | root:root | 0644 | Vhost configurations (the panel's are installed by `lamaste-priv`) |
33
- | `/etc/nginx/snippets/lamalibre-lamaste-mtls.conf` | nginx conf | root:root | 0644 | mTLS snippet |
34
- | `/etc/nginx/snippets/lamalibre-lamaste-authz-cache.conf` | nginx conf | root:root | 0644 | Gatekeeper proxy_cache zone |
35
- | `/etc/systemd/system/lamalibre-lamaste-gatekeeper.service` | systemd | root:root | 0644 | Gatekeeper systemd unit |
36
- | `/etc/systemd/system/chisel.service` | systemd | root:root | 0644 | Chisel unit, written by `create-lamaste` |
37
- | `/etc/systemd/system/authelia.service` | systemd | root:root | 0644 | Authelia unit, written by `create-lamaste` |
38
- | `~/.lamalibre/lamaste/servers.json` | JSON | user | 0600 | Desktop app server registry |
39
- | `~/.lamalibre/lamaste/agents.json` | JSON | user | 0600 | Multi-agent registry |
40
- | `~/.lamalibre/lamaste/agents/<label>/config.json` | JSON | user | 0600 | Per-agent configuration |
41
- | `~/.lamalibre/lamaste/agents/<label>/client.p12` | PKCS#12 | user | 0600 | Per-agent mTLS certificate |
42
- | `~/.lamalibre/lamaste/agents/<label>/ca.crt` | PEM | user | 0644 | Per-agent CA certificate |
43
- | `~/.lamalibre/lamaste/agents/<label>/chisel.json` | JSON | user | 0600 | Per-agent Chisel credential (source of truth for the service) |
44
- | `~/.lamalibre/lamaste/agents/<label>/chisel.env` | env file | user | 0600 | Linux only: `AUTH=` for the systemd unit's `EnvironmentFile=` |
45
- | `~/.lamalibre/lamaste/agents/<label>/` | directory | user | 0700 | Per-agent data directory |
46
- | `~/.lamalibre/lamaste/agents/<label>/sync-state.json` | JSON | user | 0600 | Outcome of the last `lamaste-agent sync` |
47
- | `~/.lamalibre/lamaste/agents/<label>/logs/` | directory | user | 0700 | Per-agent Chisel and sync log files |
48
- | `~/.lamalibre/lamaste/agent.json` | JSON | user | 0600 | Legacy single-server config |
7
+ | File | Format | Owner | Mode | Purpose |
8
+ | ---------------------------------------------------------- | ---------- | ------------------------ | ---- | --------------------------------------------------------------------------------------------------- |
9
+ | `/etc/lamalibre/lamaste/panel.json` | JSON | lamaste:lamaste | 0600 | Panel server configuration |
10
+ | `/etc/lamalibre/lamaste/tunnels.json` | JSON | lamaste:lamaste | 0600 | Tunnel definitions |
11
+ | `/etc/lamalibre/lamaste/sites.json` | JSON | lamaste:lamaste | 0600 | Static site definitions |
12
+ | `/etc/lamalibre/lamaste/chisel-credentials.json` | JSON | lamaste:lamaste | 0600 | Per-agent Chisel credentials (source of truth for the authfile) |
13
+ | `/etc/lamalibre/lamaste/chisel-users` | JSON | lamaste:lamaste-chisel | 0640 | Chisel `--authfile`: per-agent credentials and port grants (rendered) |
14
+ | `/etc/lamalibre/lamaste/chisel-sentinel` | text | lamaste:lamaste | 0600 | Password of the `lamaste-no-grants` sentinel user |
15
+ | `/etc/lamalibre/lamaste/chisel-server.key` | PEM | lamaste:lamaste-chisel | 0640 | Chisel SSH host key (`--keyfile`), generated by the panel at onboarding |
16
+ | `/etc/authelia/configuration.yml` | YAML | lamaste:lamaste-authelia | 0640 | Authelia server configuration |
17
+ | `/etc/authelia/users.yml` | YAML | lamaste:lamaste-authelia | 0660 | User database (Authelia rewrites it on a password change) |
18
+ | `/etc/authelia/.secrets.json` | JSON | lamaste:lamaste-authelia | 0600 | Authelia secrets (panel only) |
19
+ | `/etc/authelia/oidc-issuer.pem` | PEM | lamaste-authelia | 0600 | RSA-4096 key Authelia signs OIDC tokens with, written by `create-lamaste`; the panel cannot read it |
20
+ | `/etc/lamalibre/lamaste/registry-credential.json` | JSON | lamaste:lamaste | 0600 | The panel's registry (Feria) credential: a pasted token, or the `lamaste-server` OIDC client |
21
+ | `/etc/lamalibre/lamaste/oidc-clients.json` | JSON | lamaste:lamaste | 0600 | Plaintext secrets (and pbkdf2 salts) of confidential OIDC clients |
22
+ | `/etc/lamalibre/lamaste/ticket-scopes.json` | JSON | lamaste:lamaste | 0600 | Ticket scope registry |
23
+ | `/etc/lamalibre/lamaste/tickets.json` | JSON | lamaste:lamaste | 0600 | Ticket and session store |
24
+ | `/etc/lamalibre/lamaste/invitations.json` | JSON | lamaste:lamaste | 0600 | Pending user invitations |
25
+ | `/etc/lamalibre/lamaste/plugins.json` | JSON | lamaste:lamaste | 0600 | Plugin registry |
26
+ | `/etc/lamalibre/lamaste/storage-config.json` | JSON | lamaste:lamaste | 0600 | Storage server registry and plugin bindings (credentials AES-256-GCM encrypted) |
27
+ | `/etc/lamalibre/lamaste/storage-master.key` | Binary | lamaste:lamaste | 0600 | 32-byte master key for storage credential encryption |
28
+ | `/etc/lamalibre/lamaste/groups.json` | JSON | lamaste:lamaste | 0600 | Lamaste group definitions and membership |
29
+ | `/etc/lamalibre/lamaste/access-grants.json` | JSON | lamaste:lamaste | 0600 | Generic access grants (principal → resource) |
30
+ | `/etc/lamalibre/lamaste/gatekeeper.json` | JSON | lamaste:lamaste | 0600 | Gatekeeper settings (cache TTL, admin contact, logging) |
31
+ | `/etc/lamalibre/lamaste/access-request-log.json` | JSON | lamaste:lamaste | 0600 | Optional denied access log |
32
+ | `/etc/lamalibre/lamaste/pki/enrollment-tokens.json` | JSON | lamaste:lamaste | 0600 | One-time enrollment tokens for hardware-bound enrollment |
33
+ | `/etc/lamalibre/lamaste/pki/revoked.json` | JSON | lamaste:lamaste | 0600 | Revoked certificate serial numbers |
34
+ | `/etc/lamalibre/lamaste/pki/agents/registry.json` | JSON | lamaste:lamaste | 0600 | Agent certificate metadata |
35
+ | `/etc/nginx/sites-available/lamalibre-lamaste-*` | nginx conf | root:root | 0644 | Vhost configurations (the panel's are installed by `lamaste-priv`) |
36
+ | `/etc/nginx/snippets/lamalibre-lamaste-mtls.conf` | nginx conf | root:root | 0644 | mTLS snippet |
37
+ | `/etc/nginx/snippets/lamalibre-lamaste-authz-cache.conf` | nginx conf | root:root | 0644 | Gatekeeper proxy_cache zone |
38
+ | `/etc/systemd/system/lamalibre-lamaste-gatekeeper.service` | systemd | root:root | 0644 | Gatekeeper systemd unit |
39
+ | `/etc/systemd/system/chisel.service` | systemd | root:root | 0644 | Chisel unit, written by `create-lamaste` |
40
+ | `/etc/systemd/system/authelia.service` | systemd | root:root | 0644 | Authelia unit, written by `create-lamaste` |
41
+ | `~/.lamalibre/lamaste/servers.json` | JSON | user | 0600 | Desktop app server registry |
42
+ | `~/.lamalibre/lamaste/agents.json` | JSON | user | 0600 | Multi-agent registry |
43
+ | `~/.lamalibre/lamaste/agents/<label>/config.json` | JSON | user | 0600 | Per-agent configuration |
44
+ | `~/.lamalibre/lamaste/agents/<label>/client.p12` | PKCS#12 | user | 0600 | Per-agent mTLS certificate |
45
+ | `~/.lamalibre/lamaste/agents/<label>/ca.crt` | PEM | user | 0644 | Per-agent CA certificate |
46
+ | `~/.lamalibre/lamaste/agents/<label>/chisel.json` | JSON | user | 0600 | Per-agent Chisel credential (source of truth for the service) |
47
+ | `~/.lamalibre/lamaste/agents/<label>/chisel.env` | env file | user | 0600 | Linux only: `AUTH=` for the systemd unit's `EnvironmentFile=` |
48
+ | `~/.lamalibre/lamaste/agents/<label>/` | directory | user | 0700 | Per-agent data directory |
49
+ | `~/.lamalibre/lamaste/agents/<label>/sync-state.json` | JSON | user | 0600 | Outcome of the last `lamaste-agent sync` |
50
+ | `~/.lamalibre/lamaste/agents/<label>/logs/` | directory | user | 0700 | Per-agent Chisel and sync log files |
51
+ | `~/.lamalibre/lamaste/agent.json` | JSON | user | 0600 | Legacy single-server config |
49
52
 
50
53
  ---
51
54
 
@@ -690,11 +693,66 @@ Stores the randomly generated secrets used in the Authelia configuration. Backed
690
693
  {
691
694
  "jwtSecret": "<64-char-random-string>",
692
695
  "sessionSecret": "<64-char-random-string>",
693
- "storageEncryptionKey": "<64-char-random-string>"
696
+ "storageEncryptionKey": "<64-char-random-string>",
697
+ "oidcHmacSecret": "<64-char-random-string>"
694
698
  }
695
699
  ```
696
700
 
697
- **Mode:** 0600, owner `lamaste` (the panel only; Authelia reads the secrets from its configuration). If these values change, all active sessions are invalidated.
701
+ **Mode:** 0600, owner `lamaste` (the panel only; Authelia reads the secrets from its configuration). If these values change, all active sessions are invalidated. `oidcHmacSecret` appears once an OpenID Connect client exists.
702
+
703
+ ---
704
+
705
+ ## `/etc/authelia/oidc-issuer.pem`
706
+
707
+ The RSA-4096 private key (PKCS#8) Authelia signs ID and JWT access tokens with. Generated by `create-lamaste` — on a fresh install and on every redeploy that finds it missing — in a child process running as the `lamaste-authelia` account, so root never writes through `/etc/authelia` (a directory the panel owns). The panel references it from `configuration.yml` as `key: {{ secret "/etc/authelia/oidc-issuer.pem" | mindent 10 "|" | msquote }}`; Authelia expands the expression because its unit sets `X_AUTHELIA_CONFIG_FILTERS=template`.
708
+
709
+ **Mode:** 0600, owner `lamaste-authelia`. The panel cannot read it. If it is missing, the panel refuses to write an OIDC section and says to run the installer again.
710
+
711
+ ---
712
+
713
+ ## `/etc/lamalibre/lamaste/registry-credential.json`
714
+
715
+ The panel's service credential on the Lamalibre npm registry (Feria), used to broker one-hour install tokens for agents (`GET /api/agents/me/registry-credential`) and to revoke a user's tokens when a `feria-*` group is lost.
716
+
717
+ ```json
718
+ {
719
+ "provider": "feria",
720
+ "registryUrl": "https://feria.example.com",
721
+ "scope": "@lamalibre",
722
+ "auth": { "kind": "oidc", "clientId": "lamaste-server" },
723
+ "owner": "ci:auth.example.com/lamaste-server",
724
+ "configuredAt": "2026-10-13T10:00:00.000Z"
725
+ }
726
+ ```
727
+
728
+ `auth` is `{ "kind": "token", "token": "feria_…" }` for a pasted long-lived token, or `{ "kind": "oidc", "clientId": "lamaste-server" }` when the panel authenticates as its own Authelia client (client-credentials grant, Feria login; nothing long-lived stored but the client secret in `oidc-clients.json`). Files written by 4.0 (`token` at the top level) are read as `auth.kind: token`. Set with `lamaste-server registry-credential set --url <registry> (--oidc | --token-stdin)`; never shown back.
729
+
730
+ **Mode:** 0600, owner `lamaste`.
731
+
732
+ ---
733
+
734
+ ## `/etc/lamalibre/lamaste/oidc-clients.json`
735
+
736
+ Secrets of confidential OIDC clients — those plugins declare with `confidential: true`, and the panel's own `lamaste-server`. Authelia's configuration carries only pbkdf2 digests; the salt is stored with the secret so the digest is the same on every render (the panel compares the rendered section to decide whether Authelia must restart).
737
+
738
+ ```json
739
+ {
740
+ "version": 1,
741
+ "clients": {
742
+ "lamaste-server": {
743
+ "plugin": "lamaste",
744
+ "secret": "<43-char-base64url>",
745
+ "salt": "<adapted-base64>",
746
+ "createdAt": "2026-10-13T10:00:00.000Z",
747
+ "rotatedAt": null
748
+ }
749
+ }
750
+ }
751
+ ```
752
+
753
+ A secret is minted when the client first appears (plugin install, or the registry credential set to `oidc`), shown once in that response, rotated with `POST /api/plugins/:name/oidc-clients/:clientId/rotate-secret`, and deleted when the client is gone (plugin uninstalled, credential cleared).
754
+
755
+ **Mode:** 0600, owner `lamaste`.
698
756
 
699
757
  ---
700
758
 
@@ -816,7 +874,7 @@ Service files use per-agent names:
816
874
  - macOS: `com.lamalibre.lamaste.chisel-<label>` (plist label), `~/Library/LaunchAgents/com.lamalibre.lamaste.chisel-<label>.plist` — mode 0600, because it carries `AUTH` in `EnvironmentVariables`
817
875
  - Linux: `lamalibre-lamaste-chisel-<label>` (unit name), `~/.config/systemd/user/lamalibre-lamaste-chisel-<label>.service` — a systemd **user** unit with `EnvironmentFile=` pointing at `chisel.env`; enable lingering (`sudo loginctl enable-linger <user>`) for it to start at boot without a login
818
876
 
819
- Both run `chisel client --max-retry-interval 30s https://tunnel.<domain>:443 R:127.0.0.1:<port>:127.0.0.1:<port> ...` with TLS verification and no credential in argv. They are generated by `@lamalibre/lamaste@4.0.0/agent` (`chisel-service.ts`) and rewritten by `lamaste-agent setup`, `update` and `sync` — do not edit them by hand. An agent carrying no tunnels has its service unloaded (Chisel cannot run without a remote).
877
+ Both run `chisel client --max-retry-interval 30s https://tunnel.<domain>:443 R:127.0.0.1:<port>:127.0.0.1:<port> ...` with TLS verification and no credential in argv. They are generated by `@lamalibre/lamaste@4.2.0/agent` (`chisel-service.ts`) and rewritten by `lamaste-agent setup`, `update` and `sync` — do not edit them by hand. An agent carrying no tunnels has its service unloaded (Chisel cannot run without a remote).
820
878
 
821
879
  The sync timer, which runs `<node> <installed lamaste-agent> sync --label <label> --quiet` (`<node>` is a stable path such as `/opt/homebrew/bin/node` when one on `PATH` resolves to the running binary, so a Node.js upgrade does not break it):
822
880
 
@@ -24,7 +24,7 @@ If you are reading documentation and hit an unfamiliar term, this is the place t
24
24
 
25
25
  **Where it appears:**
26
26
 
27
- - Enrolled from the panel (**Certificates → Enrollment Token**) and `lamaste-agent setup` (installed globally with `npm install -g @lamalibre/lamaste-agent@4.0.0`)
27
+ - Enrolled from the panel (**Certificates → Enrollment Token**) and `lamaste-agent setup` (installed globally with `npm install -g @lamalibre/lamaste-agent@4.2.0`)
28
28
  - Agent registry: `/etc/lamalibre/lamaste/agents.json` on the server; `~/.lamalibre/lamaste/agents/<label>/` on the agent
29
29
  - The **Agent** column and field on the panel's Tunnels page
30
30
 
@@ -242,7 +242,7 @@ See also: [mTLS](#mtls-mutual-tls), [CA](#ca-certificate-authority), [PKCS12](#p
242
242
 
243
243
  **Where it appears:**
244
244
 
245
- - Generated by `lamaste-agent setup` / `update` (implementation in `@lamalibre/lamaste@4.0.0/agent`)
245
+ - Generated by `lamaste-agent setup` / `update` (implementation in `@lamalibre/lamaste@4.2.0/agent`)
246
246
  - Installed to `~/Library/LaunchAgents/com.lamalibre.lamaste.chisel-<label>.plist` on the agent
247
247
  - Manages the Chisel client process lifecycle
248
248
 
@@ -373,7 +373,7 @@ See also: [Client Certificate](#client-certificate), [CA](#ca-certificate-author
373
373
 
374
374
  **Plain English:** A small scheduled job on every agent that checks with the panel every 30 seconds and adjusts the tunnel client when the agent's tunnels changed — so tunnels created, disabled or moved in the panel reach the agent without anyone running a command on it.
375
375
 
376
- **Technical:** Runs `lamaste-agent sync --label <label>`, which fetches `GET /api/tunnels/agent-config` and converges the agent's Chisel client with it (relay URL, credential, pinned binary, granted remotes, running or stopped). It exists because Chisel rejects a client's whole session when one requested remote is not granted: an agent must drop a revoked tunnel promptly or all its other tunnels go dark. Requires a global install of `@lamalibre/lamaste-agent@4.0.0`.
376
+ **Technical:** Runs `lamaste-agent sync --label <label>`, which fetches `GET /api/tunnels/agent-config` and converges the agent's Chisel client with it (relay URL, credential, pinned binary, granted remotes, running or stopped). It exists because Chisel rejects a client's whole session when one requested remote is not granted: an agent must drop a revoked tunnel promptly or all its other tunnels go dark. Requires a global install of `@lamalibre/lamaste-agent@4.2.0`.
377
377
 
378
378
  **Where it appears:**
379
379
 
@@ -1,11 +1,11 @@
1
1
  # Installer Flags
2
2
 
3
- > CLI flags, environment variables, and exit codes for `npx @lamalibre/create-lamaste@4.0.0`.
3
+ > CLI flags, environment variables, and exit codes for `npx @lamalibre/create-lamaste@4.2.0`.
4
4
 
5
5
  ## Usage
6
6
 
7
7
  ```bash
8
- npx @lamalibre/create-lamaste@4.0.0 [flags]
8
+ npx @lamalibre/create-lamaste@4.2.0 [flags]
9
9
  ```
10
10
 
11
11
  The installer runs as root on a fresh Ubuntu 24.04 server. It is completely non-interactive by default — all configuration happens later through the browser-based onboarding wizard.
@@ -26,7 +26,7 @@ The installer runs as root on a fresh Ubuntu 24.04 server. It is completely non-
26
26
  Prints a description of what the installer does, lists all flags, and exits with code 0. Does not modify anything on the system.
27
27
 
28
28
  ```bash
29
- npx @lamalibre/create-lamaste@4.0.0 --help
29
+ npx @lamalibre/create-lamaste@4.2.0 --help
30
30
  ```
31
31
 
32
32
  ### `--yes`, `-y`
@@ -34,7 +34,7 @@ npx @lamalibre/create-lamaste@4.0.0 --help
34
34
  Skips the interactive confirmation prompt that appears before installation begins. Useful for automated deployments or scripts where you cannot press Enter.
35
35
 
36
36
  ```bash
37
- npx @lamalibre/create-lamaste@4.0.0 --yes
37
+ npx @lamalibre/create-lamaste@4.2.0 --yes
38
38
  ```
39
39
 
40
40
  Without this flag, the installer displays a banner listing all changes it will make and waits for the user to press Enter or Ctrl+C.
@@ -51,7 +51,7 @@ Skips all OS hardening tasks:
51
51
  Everything else (Node.js, nginx, mTLS, panel deployment) still runs.
52
52
 
53
53
  ```bash
54
- npx @lamalibre/create-lamaste@4.0.0 --skip-harden
54
+ npx @lamalibre/create-lamaste@4.2.0 --skip-harden
55
55
  ```
56
56
 
57
57
  Use this if you manage your own firewall rules, already have fail2ban configured, or are running on a platform that handles security at a different layer.
@@ -61,7 +61,7 @@ Use this if you manage your own firewall rules, already have fail2ban configured
61
61
  Allows the installer to run on a machine with a private or non-routable IP address (e.g., `192.168.x.x`, `10.x.x.x`). By default, the installer requires a public IP.
62
62
 
63
63
  ```bash
64
- npx @lamalibre/create-lamaste@4.0.0 --dev
64
+ npx @lamalibre/create-lamaste@4.2.0 --dev
65
65
  ```
66
66
 
67
67
  This is useful for:
@@ -76,7 +76,7 @@ When `--dev` is active, the installer prints the detected IP with a note: `(dev
76
76
  Forces the installer to run the complete installation pipeline, ignoring skip guards that would normally detect an existing installation. This is useful when an installation is in an inconsistent state and you want to ensure all components are fully deployed.
77
77
 
78
78
  ```bash
79
- npx @lamalibre/create-lamaste@4.0.0 --force-full
79
+ npx @lamalibre/create-lamaste@4.2.0 --force-full
80
80
  ```
81
81
 
82
82
  Use this if:
@@ -90,7 +90,7 @@ Use this if:
90
90
  Prints a step-by-step guide for manually removing Lamaste from the server, then exits with code 0. Does not modify anything on the system.
91
91
 
92
92
  ```bash
93
- npx @lamalibre/create-lamaste@4.0.0 --uninstall
93
+ npx @lamalibre/create-lamaste@4.2.0 --uninstall
94
94
  ```
95
95
 
96
96
  The printed guide first points to the automated removal, `sudo lamaste-server uninstall`, then covers:
@@ -207,25 +207,25 @@ Components that are always redeployed on re-run:
207
207
 
208
208
  ```bash
209
209
  ssh root@203.0.113.42
210
- npx @lamalibre/create-lamaste@4.0.0
210
+ npx @lamalibre/create-lamaste@4.2.0
211
211
  ```
212
212
 
213
213
  **Automated install (no confirmation prompt):**
214
214
 
215
215
  ```bash
216
- npx @lamalibre/create-lamaste@4.0.0 --yes
216
+ npx @lamalibre/create-lamaste@4.2.0 --yes
217
217
  ```
218
218
 
219
219
  **Install without OS hardening:**
220
220
 
221
221
  ```bash
222
- npx @lamalibre/create-lamaste@4.0.0 --yes --skip-harden
222
+ npx @lamalibre/create-lamaste@4.2.0 --yes --skip-harden
223
223
  ```
224
224
 
225
225
  **Test in a local VM:**
226
226
 
227
227
  ```bash
228
- npx @lamalibre/create-lamaste@4.0.0 --dev
228
+ npx @lamalibre/create-lamaste@4.2.0 --dev
229
229
  ```
230
230
 
231
231
  **Update an existing installation:**
@@ -237,7 +237,7 @@ npx @lamalibre/create-lamaste@latest --yes
237
237
  **View the uninstall guide:**
238
238
 
239
239
  ```bash
240
- npx @lamalibre/create-lamaste@4.0.0 --uninstall
240
+ npx @lamalibre/create-lamaste@4.2.0 --uninstall
241
241
  ```
242
242
 
243
243
  ## Quick Reference
@@ -34,7 +34,7 @@ A tunnel's port is also a loopback port on the relay: its vhost proxies to `127.
34
34
  | 9292 | IP-based panel listener |
35
35
  | 9294 | Gatekeeper |
36
36
 
37
- A tunnel on one of them would publish that internal service on a public hostname. For the panel that is an administrator takeover, not a leak: the panel trusts the client-certificate headers nginx sets. `RESERVED_TUNNEL_PORTS` in `@lamalibre/lamaste@4.0.0` is enforced by the request schema, inside the tunnel workflow, and again when the Chisel grants are rendered. Tunnel ports must also be 1024–65535.
37
+ A tunnel on one of them would publish that internal service on a public hostname. For the panel that is an administrator takeover, not a leak: the panel trusts the client-certificate headers nginx sets. `RESERVED_TUNNEL_PORTS` in `@lamalibre/lamaste@4.2.0` is enforced by the request schema, inside the tunnel workflow, and again when the Chisel grants are rendered. Tunnel ports must also be 1024–65535.
38
38
 
39
39
  ## Systemd Units
40
40
 
@@ -217,7 +217,7 @@ The agent's sync timer applies tunnel changes within about 30 seconds. If that d
217
217
  lamaste-agent update # apply now and (re)install the sync timer
218
218
  ```
219
219
 
220
- `update` needs the agent installed globally (`npm install -g @lamalibre/lamaste-agent@4.0.0`); an agent originally set up with `npx` must be installed first.
220
+ `update` needs the agent installed globally (`npm install -g @lamalibre/lamaste-agent@4.2.0`); an agent originally set up with `npx` must be installed first.
221
221
 
222
222
  **Cause 3: The agent does not carry the tunnel.**
223
223
 
@@ -320,7 +320,7 @@ ls -la /usr/local/bin/authelia
320
320
  | Missing `panel.json` | `Config file not found` | Re-run installer or create the file manually |
321
321
  | Invalid JSON in `panel.json` | `contains invalid JSON` | Fix the JSON syntax |
322
322
  | Port 3100 in use | `EADDRINUSE` | Find and stop the conflicting process: `sudo ss -tlnp sport = :3100` |
323
- | Missing Node.js modules | `Cannot find module` | Re-run the installer (`npx @lamalibre/create-lamaste@4.0.0 --yes`); `/opt/lamalibre/lamaste` is root-owned and redeployed as a whole |
323
+ | Missing Node.js modules | `Cannot find module` | Re-run the installer (`npx @lamalibre/create-lamaste@4.2.0 --yes`); `/opt/lamalibre/lamaste` is root-owned and redeployed as a whole |
324
324
  | Permission denied writing state | `EACCES` under `/etc/lamalibre/lamaste` | Re-run the installer; the redeploy re-applies the ownership of the config and PKI directories |
325
325
 
326
326
  ### chisel fails to start
@@ -329,7 +329,7 @@ ls -la /usr/local/bin/authelia
329
329
 
330
330
  | Cause | Log Message | Fix |
331
331
  | -------------------------- | ------------------------------------------------------------------------------------- | --------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- |
332
- | Binary missing | `exec format error` or `not found` | Re-run the installer (`npx @lamalibre/create-lamaste@4.0.0 --yes`) — it installs the pinned, checksum-verified release for the server's architecture; the panel cannot install binaries |
332
+ | Binary missing | `exec format error` or `not found` | Re-run the installer (`npx @lamalibre/create-lamaste@4.2.0 --yes`) — it installs the pinned, checksum-verified release for the server's architecture; the panel cannot install binaries |
333
333
  | Not the pinned release | (panel log) `The installed chisel is not the pinned release — run create-lamaste ...` | Re-run the installer. Until then the panel restarts Chisel on every authfile change |
334
334
  | Authfile or key unreadable | `permission denied` on `chisel-users` or `chisel-server.key` | Both must be `0640 lamaste:lamaste-chisel` and the unit `Group=lamaste-chisel`; restart the panel, which re-applies the authfile's. If the group, the unit or the key's ownership is wrong, re-run the installer in redeploy mode |
335
335
  | Stopped by the panel | (panel log) `Chisel stopped: ...`; unit disabled, `chisel-failed-closed` present | Reconciliation failed closed; see [Tunnel Client Cannot Connect](#tunnel-client-cannot-connect), Cause 1 |
@@ -343,7 +343,7 @@ ls -la /usr/local/bin/authelia
343
343
  | --------------------------- | --------------------------------------- | --------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- |
344
344
  | Invalid `configuration.yml` | `configuration: error` | Check YAML syntax with `authelia validate-configuration --config /etc/authelia/configuration.yml` |
345
345
  | Missing `users.yml` | `cannot open file` | Create an initial users file (see [Config Files](config-files.md)) |
346
- | Binary missing | `not found` | Re-run the installer (`npx @lamalibre/create-lamaste@4.0.0 --yes`); it installs the pinned release |
346
+ | Binary missing | `not found` | Re-run the installer (`npx @lamalibre/create-lamaste@4.2.0 --yes`); it installs the pinned release |
347
347
  | Wrong permissions | `permission denied` | Authelia runs as `lamaste-authelia`: `/etc/authelia` must be `lamaste:lamaste-authelia 2770`, `configuration.yml` `0640`, `users.yml` `0660`, `db.sqlite3` owned by `lamaste-authelia`. Re-run the installer to re-apply (a root-owned `/etc/authelia` from an older version is converted), or see [Config Files](config-files.md#file-permissions-table) |
348
348
  | Database newer than binary | storage schema version error at startup | A newer Authelia ran against this database and was replaced by an older one; the installer never downgrades an installed Authelia, so reinstall that newer release by hand |
349
349
 
@@ -516,14 +516,14 @@ sudo systemctl restart authelia
516
516
 
517
517
  ## Onboarding Fails: "Chisel is not installed" / "Authelia is not installed"
518
518
 
519
- **Symptom:** The **Starting Chisel** or **Configuring Authelia** provisioning task fails with "Chisel is not installed. Run `npx @lamalibre/create-lamaste@4.0.0` on the server to repair the installation." (or the same for Authelia).
519
+ **Symptom:** The **Starting Chisel** or **Configuring Authelia** provisioning task fails with "Chisel is not installed. Run `npx @lamalibre/create-lamaste@4.2.0` on the server to repair the installation." (or the same for Authelia).
520
520
 
521
521
  **Cause:** Onboarding downloads nothing: the installer installs both binaries (pinned releases), their systemd units and the `lamaste-authelia` account. The binary at `/usr/local/bin/chisel` or `/usr/local/bin/authelia` is missing — the installer was interrupted, or the file was removed.
522
522
 
523
523
  **Fix:** Re-run the installer on the server, then start provisioning again from the wizard:
524
524
 
525
525
  ```bash
526
- npx @lamalibre/create-lamaste@4.0.0 --yes
526
+ npx @lamalibre/create-lamaste@4.2.0 --yes
527
527
  ```
528
528
 
529
529
  If provisioning then fails writing Authelia's configuration with `/etc/authelia is not writable by the panel — run create-lamaste to repair the installation`, the directory's ownership is wrong; the same command repairs it.
@@ -538,7 +538,7 @@ If provisioning then fails writing Authelia's configuration with `/etc/authelia
538
538
 
539
539
  **Fix:**
540
540
 
541
- 1. Re-run the installer so the helper matches the panel: `npx @lamalibre/create-lamaste@4.0.0 --yes`
541
+ 1. Re-run the installer so the helper matches the panel: `npx @lamalibre/create-lamaste@4.2.0 --yes`
542
542
  2. If it persists on a current install, it is a bug: the vhost generators (`packages/server/daemon/src/lib/nginx.js`) and the allow-list (`packages/provisioners/server/scripts/lamaste-priv`) must change together — `npm test` checks every generated vhost against the allow-list. Do not work around it by editing files in `/etc/nginx` by hand.
543
543
 
544
544
  `sudo: a password is required` for `lamaste-priv` means the helper or the sudoers file is missing or outdated: re-run the installer.
@@ -621,7 +621,7 @@ df -h /
621
621
 
622
622
  **Cause 3: The web root is not writable by the panel (`EACCES`).**
623
623
 
624
- The panel writes `/var/www/lamaste` itself: it must be `lamaste:www-data`, directories `2750`, files `0640`. An install from before this layout had it owned by `www-data`. Re-run the installer (`npx @lamalibre/create-lamaste@4.0.0 --yes`); the redeploy converts the tree.
624
+ The panel writes `/var/www/lamaste` itself: it must be `lamaste:www-data`, directories `2750`, files `0640`. An install from before this layout had it owned by `www-data`. Re-run the installer (`npx @lamalibre/create-lamaste@4.2.0 --yes`); the redeploy converts the tree.
625
625
 
626
626
  ---
627
627
 
@@ -191,6 +191,11 @@
191
191
  "title": "Gatekeeper API",
192
192
  "slug": "api-gatekeeper",
193
193
  "file": "04-api-reference/gatekeeper.md"
194
+ },
195
+ {
196
+ "title": "Registry Credential & OIDC Clients",
197
+ "slug": "api-registry-and-oidc",
198
+ "file": "04-api-reference/registry-and-oidc.md"
194
199
  }
195
200
  ]
196
201
  },
@@ -2,9 +2,9 @@
2
2
 
3
3
  ## Overview
4
4
 
5
- `@lamalibre/lamaste-gatekeeper@4.0.0` is a standalone authorization package for Lamaste. It manages **groups** and **grants**, enforces tunnel access control via a lightweight Fastify service, and serves user-friendly "request access" pages when access is denied.
5
+ `@lamalibre/lamaste-gatekeeper@4.2.0` is a standalone authorization package for Lamaste. It manages **groups** and **grants**, enforces tunnel access control via a lightweight Fastify service, and serves user-friendly "request access" pages when access is denied.
6
6
 
7
- It follows the same architectural pattern as `@lamalibre/lamaste-tickets@4.0.0` — a solid library at the core, with a service, CLI, and desktop as consumers.
7
+ It follows the same architectural pattern as `@lamalibre/lamaste-tickets@4.2.0` — a solid library at the core, with a service, CLI, and desktop as consumers.
8
8
 
9
9
  ---
10
10
 
@@ -204,7 +204,7 @@ The grant system is resource-agnostic. It doesn't know what a "tunnel" or "plugi
204
204
 
205
205
  ```js
206
206
  import { createGroup, listGroups, getGroup, updateGroup, deleteGroup,
207
- addMembers, removeMembers, getGroupsForUser } from '@lamalibre/lamaste-gatekeeper@4.0.0';
207
+ addMembers, removeMembers, getGroupsForUser } from '@lamalibre/lamaste-gatekeeper@4.2.0';
208
208
 
209
209
  createGroup(name, { description?, createdBy? })
210
210
  // → { name, description, members: [], createdAt, createdBy }
@@ -240,7 +240,7 @@ getGroupsForUser(username)
240
240
  ### Grants
241
241
 
242
242
  ```js
243
- import { createGrant, listGrants, getGrant, revokeGrant } from '@lamalibre/lamaste-gatekeeper@4.0.0';
243
+ import { createGrant, listGrants, getGrant, revokeGrant } from '@lamalibre/lamaste-gatekeeper@4.2.0';
244
244
 
245
245
  createGrant({ principalType, principalId, resourceType, resourceId, context? })
246
246
  // → grant object
@@ -267,7 +267,7 @@ revokeGrant(grantId)
267
267
  ### Authorization
268
268
 
269
269
  ```js
270
- import { checkAccess } from '@lamalibre/lamaste-gatekeeper@4.0.0';
270
+ import { checkAccess } from '@lamalibre/lamaste-gatekeeper@4.2.0';
271
271
 
272
272
  checkAccess(username, resourceType, resourceId);
273
273
  // 1. Find direct user grants: principalType='user', principalId=username
@@ -282,7 +282,7 @@ checkAccess(username, resourceType, resourceId);
282
282
  ### Templates
283
283
 
284
284
  ```js
285
- import { getAccessRequestTemplates } from '@lamalibre/lamaste-gatekeeper@4.0.0';
285
+ import { getAccessRequestTemplates } from '@lamalibre/lamaste-gatekeeper@4.2.0';
286
286
 
287
287
  getAccessRequestTemplates(username, resourceName, { adminContact?, domain? })
288
288
  // → {
@@ -861,14 +861,14 @@ On first startup, gatekeeper checks for legacy files:
861
861
 
862
862
  ### Panel-Server Refactoring
863
863
 
864
- - `lib/user-access.js` → delegates to gatekeeper library (import from `@lamalibre/lamaste-gatekeeper@4.0.0`)
864
+ - `lib/user-access.js` → delegates to gatekeeper library (import from `@lamalibre/lamaste-gatekeeper@4.2.0`)
865
865
  - `lib/access-control-sync.js` → removed (gatekeeper handles authorization at nginx layer, no more Authelia config rewriting for per-user access rules)
866
866
  - `routes/user-access.js` → simplified, delegates grant CRUD to gatekeeper
867
867
  - Tunnel creation/update routes → call gatekeeper for access mode changes
868
868
 
869
869
  ### Installer Updates (create-lamaste)
870
870
 
871
- - Install `@lamalibre/lamaste-gatekeeper@4.0.0` package
871
+ - Install `@lamalibre/lamaste-gatekeeper@4.2.0` package
872
872
  - Create `/etc/lamalibre/lamaste/groups.json` (empty initial state)
873
873
  - Create `/etc/lamalibre/lamaste/access-grants.json` (empty or migrated)
874
874
  - Create `lamalibre-lamaste-gatekeeper.service` systemd unit