@hoststack.dev/mcp 0.9.0 → 0.9.1
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 +9 -3
- package/dist/hoststack-mcp.js +28 -22
- package/dist/hoststack-mcp.js.map +1 -1
- package/dist/index.d.ts +1 -1
- package/dist/index.js +27 -21
- package/dist/index.js.map +1 -1
- package/manifest.json +1 -1
- package/package.json +2 -2
package/README.md
CHANGED
|
@@ -52,7 +52,13 @@ Add to `~/.cursor/mcp.json` (or via Settings → MCP):
|
|
|
52
52
|
#### Claude Code
|
|
53
53
|
|
|
54
54
|
```bash
|
|
55
|
-
claude mcp add hoststack -- npx -y @hoststack.dev/mcp
|
|
55
|
+
claude mcp add hoststack --env HOSTSTACK_API_KEY=hs_live_... -- npx -y @hoststack.dev/mcp
|
|
56
|
+
```
|
|
57
|
+
|
|
58
|
+
Or — equivalently — use the hosted HTTP transport so credentials live only in your Claude Code config, not on disk:
|
|
59
|
+
|
|
60
|
+
```bash
|
|
61
|
+
claude mcp add --transport http hoststack https://hoststack.dev/api/mcp --header "Authorization: Bearer hs_live_..."
|
|
56
62
|
```
|
|
57
63
|
|
|
58
64
|
#### Any other client (hosted)
|
|
@@ -79,7 +85,7 @@ If `HOSTSTACK_API_KEY` is set in your shell, it gets baked into the snippet; oth
|
|
|
79
85
|
|
|
80
86
|
## Tool inventory
|
|
81
87
|
|
|
82
|
-
|
|
88
|
+
58 tools, grouped by resource:
|
|
83
89
|
|
|
84
90
|
| Category | Read | Write |
|
|
85
91
|
| ----------------- | --------------------------------------------------------------------------------------------------------------------------------- | ------------------------------------------------------------------------------------------------------------------------ |
|
|
@@ -87,7 +93,7 @@ If `HOSTSTACK_API_KEY` is set in your shell, it gets baked into the snippet; oth
|
|
|
87
93
|
| **services** | `list_services`, `get_service`, `get_service_metrics`, `get_service_metrics_history`, `get_service_logs`, `get_service_logs_bulk` | `update_service`, `update_service_config`, `suspend_service`, `resume_service` |
|
|
88
94
|
| **deploys** | `list_deploys`, `get_deploy`, `get_deploy_logs`, `diagnose_deploy` | `trigger_deploy`, `cancel_deploy` |
|
|
89
95
|
| **environments** | `list_environments` | `create_environment`, `delete_environment`, `promote_deploy` |
|
|
90
|
-
| **databases** | `list_databases`, `get_database`
|
|
96
|
+
| **databases** | `list_databases`, `get_database`, `get_database_cluster`, `query_database` | `update_database`, `upgrade_database_to_ha` (use the dashboard for create/delete/credentials) |
|
|
91
97
|
| **volumes** | `list_volumes` | `create_volume`, `update_volume`, `delete_volume` |
|
|
92
98
|
| **domains** | `list_domains` | `add_domain`, `verify_domain`, `remove_domain` |
|
|
93
99
|
| **dns** | `list_dns_zones`, `list_dns_records`, `get_dns_record` | `create_dns_record`, `update_dns_record`, `delete_dns_record` |
|
package/dist/hoststack-mcp.js
CHANGED
|
@@ -834,13 +834,14 @@ defineTool({
|
|
|
834
834
|
name: "trigger_deploy",
|
|
835
835
|
category: "deploys",
|
|
836
836
|
description: [
|
|
837
|
-
"Kick off a new deploy
|
|
837
|
+
"Kick off a new deploy. Defaults to the latest commit on the service branch; pass commit_hash or branch to deploy something else.",
|
|
838
838
|
"",
|
|
839
|
-
'When to use: the user explicitly asks to deploy ("ship it", "redeploy", "kick off a new build"). For services with auto-deploy enabled, a fresh git push already triggers a deploy automatically \u2014 only call this for manual triggers
|
|
839
|
+
'When to use: the user explicitly asks to deploy ("ship it", "redeploy", "kick off a new build"). For services with auto-deploy enabled, a fresh git push already triggers a deploy automatically \u2014 only call this for manual triggers or after a config change.',
|
|
840
840
|
"",
|
|
841
841
|
"Inputs:",
|
|
842
842
|
" - service_id: publicId of the service.",
|
|
843
|
-
" -
|
|
843
|
+
" - commit_hash (optional): build a specific commit instead of HEAD on the configured branch.",
|
|
844
|
+
" - branch (optional): build the tip of a non-default branch.",
|
|
844
845
|
"",
|
|
845
846
|
'Returns: { deploy: Deploy } \u2014 the new deploy record. Status will start as "pending" then transition through "building" \u2192 "deploying" \u2192 "live" or "failed".',
|
|
846
847
|
"",
|
|
@@ -848,12 +849,14 @@ defineTool({
|
|
|
848
849
|
].join("\n"),
|
|
849
850
|
input: {
|
|
850
851
|
service_id: z6.string().describe("Service publicId."),
|
|
851
|
-
|
|
852
|
+
commit_hash: z6.string().max(40).optional().describe("Specific commit to build (default: branch HEAD)."),
|
|
853
|
+
branch: z6.string().max(200).optional().describe("Branch to build (default: service configured branch).")
|
|
852
854
|
},
|
|
853
855
|
handler: async (args2, ctx) => {
|
|
854
856
|
const teamId = await ctx.resolveTeamId();
|
|
855
857
|
const input = {};
|
|
856
|
-
if (args2.
|
|
858
|
+
if (args2.commit_hash !== void 0) input.commitHash = args2.commit_hash;
|
|
859
|
+
if (args2.branch !== void 0) input.branch = args2.branch;
|
|
857
860
|
const response = await ctx.hoststack.deploys.trigger(teamId, args2.service_id, input);
|
|
858
861
|
const data = { deploy: shapeDeploy(response.deploy) };
|
|
859
862
|
const publicId = data.deploy && "publicId" in data.deploy ? data.deploy.publicId : "unknown";
|
|
@@ -896,7 +899,7 @@ defineTool({
|
|
|
896
899
|
name: "get_deploy_logs",
|
|
897
900
|
category: "deploys",
|
|
898
901
|
description: [
|
|
899
|
-
"Fetch the build/deploy logs for a single deploy. Returns the entire log buffer the agent can
|
|
902
|
+
"Fetch the build/deploy logs for a single deploy. Returns the entire log buffer the agent can then search for errors.",
|
|
900
903
|
"",
|
|
901
904
|
"When to use: a deploy failed and you need to read the build output to diagnose. Pair with get_deploy to find a failed deploy_id, then call this. For runtime (post-deploy) logs of the running container, use get_service_logs instead.",
|
|
902
905
|
"",
|
|
@@ -1337,7 +1340,8 @@ defineTool({
|
|
|
1337
1340
|
"",
|
|
1338
1341
|
"Inputs:",
|
|
1339
1342
|
' - hostname: the domain to add (e.g. "api.example.com").',
|
|
1340
|
-
" - service_id
|
|
1343
|
+
" - service_id: publicId of the service to bind the domain to.",
|
|
1344
|
+
" - path_prefix (optional): when set, only requests under this URL prefix route to this service. Use for path-based fan-out (e.g. `/api` to an api service, `/` to a web service on the same hostname).",
|
|
1341
1345
|
"",
|
|
1342
1346
|
"Returns: { domain: Domain } \u2014 includes dnsTargets you must configure (CNAME / A records).",
|
|
1343
1347
|
"",
|
|
@@ -1345,12 +1349,16 @@ defineTool({
|
|
|
1345
1349
|
].join("\n"),
|
|
1346
1350
|
input: {
|
|
1347
1351
|
hostname: z8.string().min(3).max(253).describe("Fully-qualified hostname (e.g. api.example.com)."),
|
|
1348
|
-
service_id: z8.string().
|
|
1352
|
+
service_id: z8.string().describe("Service publicId to bind to."),
|
|
1353
|
+
path_prefix: z8.string().optional().describe('Optional URL prefix for path-based routing (e.g. "/api").')
|
|
1349
1354
|
},
|
|
1350
1355
|
handler: async (args2, ctx) => {
|
|
1351
1356
|
const teamId = await ctx.resolveTeamId();
|
|
1352
|
-
const input = {
|
|
1353
|
-
|
|
1357
|
+
const input = {
|
|
1358
|
+
domain: args2.hostname,
|
|
1359
|
+
serviceId: args2.service_id
|
|
1360
|
+
};
|
|
1361
|
+
if (args2.path_prefix !== void 0) input.pathPrefix = args2.path_prefix;
|
|
1354
1362
|
const response = await ctx.hoststack.domains.add(teamId, input);
|
|
1355
1363
|
const data = { domain: shapeDomain(response.domain) };
|
|
1356
1364
|
return respond({
|
|
@@ -1451,7 +1459,7 @@ defineTool({
|
|
|
1451
1459
|
" - service_id: publicId of the service.",
|
|
1452
1460
|
' - key: env-var name (e.g. "DATABASE_URL").',
|
|
1453
1461
|
" - value: new value (will be encrypted at rest if is_secret=true).",
|
|
1454
|
-
" - is_secret (optional): true marks the value as secret (masked on read).
|
|
1462
|
+
" - is_secret (optional): true marks the value as secret (masked on read). On create, defaults to true for safety. On update, omitting it leaves the existing flag untouched \u2014 pass it explicitly only when you want to change classification.",
|
|
1455
1463
|
"",
|
|
1456
1464
|
'Returns: { envVar: EnvVar, action: "created" | "updated" }.',
|
|
1457
1465
|
"",
|
|
@@ -1465,18 +1473,16 @@ defineTool({
|
|
|
1465
1473
|
},
|
|
1466
1474
|
handler: async (args2, ctx) => {
|
|
1467
1475
|
const teamId = await ctx.resolveTeamId();
|
|
1468
|
-
const isSecret = args2.is_secret ?? true;
|
|
1469
1476
|
const existing = await ctx.hoststack.envVars.list(teamId, args2.service_id);
|
|
1470
1477
|
const match = existing.envVars.find((v) => v.key === args2.key);
|
|
1471
1478
|
if (match) {
|
|
1479
|
+
const updatePayload = { value: args2.value };
|
|
1480
|
+
if (args2.is_secret !== void 0) updatePayload.isSecret = args2.is_secret;
|
|
1472
1481
|
const response2 = await ctx.hoststack.envVars.update(
|
|
1473
1482
|
teamId,
|
|
1474
1483
|
args2.service_id,
|
|
1475
1484
|
String(match.id),
|
|
1476
|
-
|
|
1477
|
-
value: args2.value,
|
|
1478
|
-
isSecret
|
|
1479
|
-
}
|
|
1485
|
+
updatePayload
|
|
1480
1486
|
);
|
|
1481
1487
|
const data2 = {
|
|
1482
1488
|
envVar: shapeEnvVar(response2.envVar),
|
|
@@ -1487,7 +1493,7 @@ defineTool({
|
|
|
1487
1493
|
const response = await ctx.hoststack.envVars.create(teamId, args2.service_id, {
|
|
1488
1494
|
key: args2.key,
|
|
1489
1495
|
value: args2.value,
|
|
1490
|
-
isSecret
|
|
1496
|
+
isSecret: args2.is_secret ?? true
|
|
1491
1497
|
});
|
|
1492
1498
|
const data = {
|
|
1493
1499
|
envVar: shapeEnvVar(response.envVar),
|
|
@@ -1623,7 +1629,7 @@ defineTool({
|
|
|
1623
1629
|
"",
|
|
1624
1630
|
"Returns: { environment: Environment }.",
|
|
1625
1631
|
"",
|
|
1626
|
-
'Example: create_environment({ project_id: "prj_abc", name: "Staging", type: "staging" }) \u2192 { environment: { id: 7, publicId: "
|
|
1632
|
+
'Example: create_environment({ project_id: "prj_abc", name: "Staging", type: "staging" }) \u2192 { environment: { id: 7, publicId: "env_\u2026", name: "Staging", type: "staging" } }'
|
|
1627
1633
|
].join("\n"),
|
|
1628
1634
|
input: {
|
|
1629
1635
|
project_id: z10.string().describe("Project publicId."),
|
|
@@ -1660,7 +1666,7 @@ defineTool({
|
|
|
1660
1666
|
"",
|
|
1661
1667
|
"Returns: { success: true } on success.",
|
|
1662
1668
|
"",
|
|
1663
|
-
'Example: delete_environment({ project_id: "prj_abc", environment_id: "
|
|
1669
|
+
'Example: delete_environment({ project_id: "prj_abc", environment_id: "env_xyz" }) \u2192 { success: true }'
|
|
1664
1670
|
].join("\n"),
|
|
1665
1671
|
input: {
|
|
1666
1672
|
project_id: z10.string().describe("Project publicId."),
|
|
@@ -1692,7 +1698,7 @@ defineTool({
|
|
|
1692
1698
|
"",
|
|
1693
1699
|
"Returns: { deploy: Deploy } \u2014 the new deploy on the target service.",
|
|
1694
1700
|
"",
|
|
1695
|
-
'Example: promote_deploy({ service_id: "svc_staging", deploy_id: "dpl_built", target_environment_id: "
|
|
1701
|
+
'Example: promote_deploy({ service_id: "svc_staging", deploy_id: "dpl_built", target_environment_id: "env_prod" }) \u2192 { deploy: { id: 99, status: "pending", trigger: "rollback", dockerImageId: "sha256:\u2026" } }'
|
|
1696
1702
|
].join("\n"),
|
|
1697
1703
|
input: {
|
|
1698
1704
|
service_id: z10.string().describe("Source service publicId."),
|
|
@@ -2714,7 +2720,7 @@ defineTool({
|
|
|
2714
2720
|
|
|
2715
2721
|
// src/server-factory.ts
|
|
2716
2722
|
var PACKAGE_NAME = "hoststack";
|
|
2717
|
-
var PACKAGE_VERSION = "0.
|
|
2723
|
+
var PACKAGE_VERSION = "0.9.1";
|
|
2718
2724
|
function createMcpServer(options) {
|
|
2719
2725
|
const baseUrl2 = (options.baseUrl ?? "https://hoststack.dev").replace(/\/$/, "");
|
|
2720
2726
|
const hoststack = new HostStack({ apiKey: options.apiKey, baseUrl: baseUrl2 });
|
|
@@ -2779,7 +2785,7 @@ if (printIdx !== -1) {
|
|
|
2779
2785
|
}
|
|
2780
2786
|
if (target === "claude-code") {
|
|
2781
2787
|
process.stdout.write(
|
|
2782
|
-
`claude mcp add hoststack -- npx -y @hoststack.dev/mcp
|
|
2788
|
+
`claude mcp add hoststack --env HOSTSTACK_API_KEY=${apiKeyPlaceholder} -- npx -y @hoststack.dev/mcp
|
|
2783
2789
|
`
|
|
2784
2790
|
);
|
|
2785
2791
|
process.exit(0);
|