@marcusrbrown/infra 0.23.0 → 0.25.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.
- package/README.md +88 -12
- package/dist/cli.js +14 -11
- package/package.json +2 -2
package/README.md
CHANGED
|
@@ -38,21 +38,40 @@ bunx @marcusrbrown/infra keeweb deploy --local --nginx # include nginx config
|
|
|
38
38
|
bunx @marcusrbrown/infra keeweb open
|
|
39
39
|
```
|
|
40
40
|
|
|
41
|
+
### Agent
|
|
42
|
+
|
|
43
|
+
Configure model credentials for the Fro Bot agent and wire the optional S3 durable-storage handoff.
|
|
44
|
+
|
|
45
|
+
| Subcommand | Description |
|
|
46
|
+
| --- | --- |
|
|
47
|
+
| `agent setup` | Interactive wizard to configure generalized agent model-credential secrets/variables |
|
|
48
|
+
| `agent storage --repo OWNER/REPO --manifest FILE` | Verify the provisioned S3 handoff and wire non-secret GitHub storage variables |
|
|
49
|
+
| `agent storage teardown --repo OWNER/REPO --manifest FILE` | Unwire S3 variables and remove the repo-scoped storage resources |
|
|
50
|
+
|
|
51
|
+
```bash
|
|
52
|
+
bunx @marcusrbrown/infra agent setup
|
|
53
|
+
bunx @marcusrbrown/infra agent setup --repo owner/repo --harness opencode --key sk-existing --force
|
|
54
|
+
bunx @marcusrbrown/infra agent storage --repo owner/repo --manifest handoff.json
|
|
55
|
+
bunx @marcusrbrown/infra agent storage --repo owner/repo --manifest handoff.json --plan # report without mutating
|
|
56
|
+
bunx @marcusrbrown/infra agent storage teardown --repo owner/repo --manifest handoff.json
|
|
57
|
+
```
|
|
58
|
+
|
|
41
59
|
### CLIProxyAPI
|
|
42
60
|
|
|
43
61
|
Manage the CLIProxyAPI proxy on `cliproxy.fro.bot`.
|
|
44
62
|
|
|
45
|
-
| Subcommand
|
|
46
|
-
|
|
|
47
|
-
| `cliproxy status`
|
|
48
|
-
| `cliproxy models`
|
|
49
|
-
| `cliproxy deploy`
|
|
50
|
-
| `cliproxy config`
|
|
51
|
-
| `cliproxy keys`
|
|
52
|
-
| `cliproxy login`
|
|
53
|
-
| `cliproxy monitor`
|
|
54
|
-
| `cliproxy open`
|
|
55
|
-
| `cliproxy
|
|
63
|
+
| Subcommand | Description |
|
|
64
|
+
| ---------------------- | ------------------------------------------------------------------------ |
|
|
65
|
+
| `cliproxy status` | HTTP reachability, usage stats, version |
|
|
66
|
+
| `cliproxy models` | List models served at /v1/models; optional `[provider]` filter |
|
|
67
|
+
| `cliproxy deploy` | Trigger deployment (GitHub Actions by default; `--local` for direct SSH) |
|
|
68
|
+
| `cliproxy config` | Get or set proxy configuration via the management API |
|
|
69
|
+
| `cliproxy keys` | List, add, or remove API keys via the management API |
|
|
70
|
+
| `cliproxy login` | Authenticate a provider (claude or codex) via SSH |
|
|
71
|
+
| `cliproxy monitor` | Probe Anthropic auth and send issue/Discord transition alerts |
|
|
72
|
+
| `cliproxy open` | Open an interactive TUI via SSH |
|
|
73
|
+
| `cliproxy reset-quota` | Reset quota for a CLIProxyAPI auth record |
|
|
74
|
+
| `cliproxy setup` | Interactive wizard to onboard a repo to CLIProxyAPI |
|
|
56
75
|
|
|
57
76
|
```bash
|
|
58
77
|
bunx @marcusrbrown/infra cliproxy status
|
|
@@ -68,10 +87,27 @@ bunx @marcusrbrown/infra cliproxy login claude
|
|
|
68
87
|
bunx @marcusrbrown/infra cliproxy login codex
|
|
69
88
|
bunx @marcusrbrown/infra cliproxy monitor
|
|
70
89
|
bunx @marcusrbrown/infra cliproxy open
|
|
90
|
+
bunx @marcusrbrown/infra cliproxy reset-quota
|
|
71
91
|
bunx @marcusrbrown/infra cliproxy setup
|
|
72
92
|
bunx @marcusrbrown/infra cliproxy setup --repo OWNER/REPO --harness opencode
|
|
73
93
|
```
|
|
74
94
|
|
|
95
|
+
### Broker
|
|
96
|
+
|
|
97
|
+
Manage the OIDC credential broker on `broker.fro.bot`.
|
|
98
|
+
|
|
99
|
+
| Subcommand | Description |
|
|
100
|
+
| --------------- | ------------------------------------------------------------------------ |
|
|
101
|
+
| `broker status` | HTTP reachability via `/healthz` |
|
|
102
|
+
| `broker deploy` | Trigger deployment (GitHub Actions by default; `--local` for direct SSH) |
|
|
103
|
+
| `broker logs` | Stream broker service logs (`--tail N` to limit lines) |
|
|
104
|
+
|
|
105
|
+
```bash
|
|
106
|
+
bunx @marcusrbrown/infra broker status
|
|
107
|
+
bunx @marcusrbrown/infra broker deploy
|
|
108
|
+
bunx @marcusrbrown/infra broker logs --tail 100
|
|
109
|
+
```
|
|
110
|
+
|
|
75
111
|
### Gateway
|
|
76
112
|
|
|
77
113
|
Manage the Fro Bot gateway on `gateway.fro.bot`.
|
|
@@ -108,6 +144,46 @@ bunx @marcusrbrown/infra umami deploy
|
|
|
108
144
|
bunx @marcusrbrown/infra umami logs --tail 50
|
|
109
145
|
```
|
|
110
146
|
|
|
147
|
+
### Dashboard
|
|
148
|
+
|
|
149
|
+
Manage the Fro Bot operator dashboard.
|
|
150
|
+
|
|
151
|
+
| Subcommand | Description |
|
|
152
|
+
| ------------------ | ------------------------------------------------------------------------ |
|
|
153
|
+
| `dashboard status` | SSH health check, `docker compose ps` service states |
|
|
154
|
+
| `dashboard deploy` | Trigger deployment (GitHub Actions by default; `--local` for direct SSH) |
|
|
155
|
+
| `dashboard logs` | Stream dashboard service logs (`--tail N` to limit lines) |
|
|
156
|
+
|
|
157
|
+
```bash
|
|
158
|
+
bunx @marcusrbrown/infra dashboard status
|
|
159
|
+
bunx @marcusrbrown/infra dashboard deploy
|
|
160
|
+
bunx @marcusrbrown/infra dashboard deploy --image-version 2026.06.47 # pin a CalVer release
|
|
161
|
+
bunx @marcusrbrown/infra dashboard logs dashboard --tail 100
|
|
162
|
+
```
|
|
163
|
+
|
|
164
|
+
### VPN
|
|
165
|
+
|
|
166
|
+
Manage the WireGuard VPN egress box.
|
|
167
|
+
|
|
168
|
+
| Subcommand | Description |
|
|
169
|
+
| -------------------------- | ------------------------------------------------------------------------ |
|
|
170
|
+
| `vpn status` | SSH health check, `wg show wg0` interface state |
|
|
171
|
+
| `vpn deploy` | Trigger deployment (GitHub Actions by default; `--local` for direct SSH) |
|
|
172
|
+
| `vpn logs` | Stream WireGuard logs (`--tail N` to limit lines) |
|
|
173
|
+
| `vpn client add <name>` | Generate a keypair, assign a tunnel IP, write the client `.conf` |
|
|
174
|
+
| `vpn client list` | List peers (name, tunnel IP, public key) |
|
|
175
|
+
| `vpn client remove <name>` | Remove a peer |
|
|
176
|
+
|
|
177
|
+
```bash
|
|
178
|
+
bunx @marcusrbrown/infra vpn status
|
|
179
|
+
bunx @marcusrbrown/infra vpn deploy
|
|
180
|
+
bunx @marcusrbrown/infra vpn deploy --force-server-key # rotates the server key, invalidates all client configs
|
|
181
|
+
bunx @marcusrbrown/infra vpn logs --tail 100
|
|
182
|
+
bunx @marcusrbrown/infra vpn client add laptop
|
|
183
|
+
bunx @marcusrbrown/infra vpn client list
|
|
184
|
+
bunx @marcusrbrown/infra vpn client remove laptop
|
|
185
|
+
```
|
|
186
|
+
|
|
111
187
|
### Unified Status
|
|
112
188
|
|
|
113
189
|
```bash
|
|
@@ -117,7 +193,7 @@ bunx @marcusrbrown/infra status --json # machine-readable output
|
|
|
117
193
|
|
|
118
194
|
### MCP Bridge
|
|
119
195
|
|
|
120
|
-
|
|
196
|
+
Starts a stdio MCP server exposing a read-only allowlist of exactly 9 status commands as tools: `gateway status`, `cliproxy status`, `cliproxy models`, `keeweb status`, `umami status`, `dashboard status`, `vpn status`, `broker status`, and unified `status`. Every mutating command is deliberately excluded from the allowlist.
|
|
121
197
|
|
|
122
198
|
```bash
|
|
123
199
|
bunx @marcusrbrown/infra mcp
|
package/dist/cli.js
CHANGED
|
@@ -6950,7 +6950,7 @@ import { goke } from "goke";
|
|
|
6950
6950
|
// package.json
|
|
6951
6951
|
var package_default = {
|
|
6952
6952
|
name: "@marcusrbrown/infra",
|
|
6953
|
-
version: "0.
|
|
6953
|
+
version: "0.25.0",
|
|
6954
6954
|
description: "Infrastructure management CLI \u2014 deploy automation, health checks, and MCP bridge",
|
|
6955
6955
|
keywords: [
|
|
6956
6956
|
"infra",
|
|
@@ -6993,7 +6993,7 @@ var package_default = {
|
|
|
6993
6993
|
},
|
|
6994
6994
|
devDependencies: {
|
|
6995
6995
|
"@marcusrbrown/infra-shared": "workspace:*",
|
|
6996
|
-
"@modelcontextprotocol/sdk": "1.
|
|
6996
|
+
"@modelcontextprotocol/sdk": "1.32.1",
|
|
6997
6997
|
yaml: "2.9.1"
|
|
6998
6998
|
},
|
|
6999
6999
|
engines: {
|
|
@@ -8406,7 +8406,7 @@ var CONTENT_EVENTS = new Set([
|
|
|
8406
8406
|
"discussion_comment"
|
|
8407
8407
|
]);
|
|
8408
8408
|
var VERIFIED_ACTION_SHA_BY_LAYOUT = {
|
|
8409
|
-
"fro-bot/agent@v0.
|
|
8409
|
+
"fro-bot/agent@v0.118.2": "77f2bad7d68ac38279cd0fa28f38b26a0cd15dfb"
|
|
8410
8410
|
};
|
|
8411
8411
|
var REQUIRED_S3_INPUTS = {
|
|
8412
8412
|
"s3-backup": undefined,
|
|
@@ -8849,9 +8849,16 @@ function hasHandoff(job) {
|
|
|
8849
8849
|
const serialized = stringifyUnknown(job);
|
|
8850
8850
|
return /needs\.[\w-]+\.outputs\./.test(serialized) || /actions\/(?:download-artifact|upload-artifact|cache|cache\/restore|cache\/save)@/.test(serialized);
|
|
8851
8851
|
}
|
|
8852
|
+
var STATIC_AWS_CREDENTIAL_PATTERN = /AWS_ACCESS_KEY_ID|AWS_SECRET_ACCESS_KEY|aws-access-key-id|aws-secret-access-key/;
|
|
8853
|
+
function withoutBlankedCredentialKeys(value) {
|
|
8854
|
+
if (Array.isArray(value))
|
|
8855
|
+
return value.map(withoutBlankedCredentialKeys);
|
|
8856
|
+
if (!isMapping(value))
|
|
8857
|
+
return value;
|
|
8858
|
+
return Object.fromEntries(Object.entries(value).filter(([key, entry]) => !(entry === "" && STATIC_AWS_CREDENTIAL_PATTERN.test(key))).map(([key, entry]) => [key, withoutBlankedCredentialKeys(entry)]));
|
|
8859
|
+
}
|
|
8852
8860
|
function hasStaticAwsCredentials(job) {
|
|
8853
|
-
|
|
8854
|
-
return /AWS_ACCESS_KEY_ID|AWS_SECRET_ACCESS_KEY|aws-access-key-id|aws-secret-access-key/.test(serialized);
|
|
8861
|
+
return STATIC_AWS_CREDENTIAL_PATTERN.test(stringifyUnknown(withoutBlankedCredentialKeys(job)));
|
|
8855
8862
|
}
|
|
8856
8863
|
function ancestors(jobId, analyses) {
|
|
8857
8864
|
const visited = new Set;
|
|
@@ -8910,7 +8917,7 @@ function formatStorageWorkflowSnippet() {
|
|
|
8910
8917
|
with:
|
|
8911
8918
|
role-to-assume: \${{ vars.FRO_BOT_S3_ROLE_TO_ASSUME }}
|
|
8912
8919
|
aws-region: \${{ vars.FRO_BOT_S3_REGION }}
|
|
8913
|
-
- uses: fro-bot/agent@
|
|
8920
|
+
- uses: fro-bot/agent@77f2bad7d68ac38279cd0fa28f38b26a0cd15dfb
|
|
8914
8921
|
with:
|
|
8915
8922
|
s3-backup: true
|
|
8916
8923
|
s3-bucket: \${{ vars.FRO_BOT_S3_BUCKET }}
|
|
@@ -8946,10 +8953,6 @@ function environmentResult(environmentValue, branchPoliciesValue) {
|
|
|
8946
8953
|
violations.push("GitHub Environment fro-bot-storage is missing or returned an invalid response.");
|
|
8947
8954
|
return { verified: false, violations };
|
|
8948
8955
|
}
|
|
8949
|
-
const protectionRules = Array.isArray(environmentValue.protection_rules) ? environmentValue.protection_rules : [];
|
|
8950
|
-
const hasReviewer = protectionRules.some((rule) => isMapping(rule) && rule.type === "required_reviewers" && Array.isArray(rule.reviewers) && rule.reviewers.length > 0);
|
|
8951
|
-
if (!hasReviewer)
|
|
8952
|
-
violations.push("GitHub Environment fro-bot-storage has no required reviewer protection rule.");
|
|
8953
8956
|
const branchPolicy = environmentValue.deployment_branch_policy;
|
|
8954
8957
|
if (!isMapping(branchPolicy) || branchPolicy.protected_branches !== false || branchPolicy.custom_branch_policies !== true) {
|
|
8955
8958
|
violations.push("GitHub Environment fro-bot-storage does not use a custom deployment-branch policy.");
|
|
@@ -9135,7 +9138,7 @@ var STORAGE_VARIABLE_NAMES = {
|
|
|
9135
9138
|
prefix: "FRO_BOT_S3_PREFIX",
|
|
9136
9139
|
expectedBucketOwner: "FRO_BOT_S3_EXPECTED_BUCKET_OWNER"
|
|
9137
9140
|
};
|
|
9138
|
-
var KNOWN_KEY_LAYOUT_VERSION = "fro-bot/agent@v0.
|
|
9141
|
+
var KNOWN_KEY_LAYOUT_VERSION = "fro-bot/agent@v0.118.2";
|
|
9139
9142
|
var manifestSchema = z6.object({
|
|
9140
9143
|
owner: z6.string().min(1),
|
|
9141
9144
|
repo: z6.string().min(1),
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@marcusrbrown/infra",
|
|
3
|
-
"version": "0.
|
|
3
|
+
"version": "0.25.0",
|
|
4
4
|
"description": "Infrastructure management CLI — deploy automation, health checks, and MCP bridge",
|
|
5
5
|
"keywords": [
|
|
6
6
|
"infra",
|
|
@@ -43,7 +43,7 @@
|
|
|
43
43
|
},
|
|
44
44
|
"devDependencies": {
|
|
45
45
|
"@marcusrbrown/infra-shared": "workspace:*",
|
|
46
|
-
"@modelcontextprotocol/sdk": "1.
|
|
46
|
+
"@modelcontextprotocol/sdk": "1.32.1",
|
|
47
47
|
"yaml": "2.9.1"
|
|
48
48
|
},
|
|
49
49
|
"engines": {
|