@hasna/mcps 0.0.23 → 0.0.25
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 +3 -3
- package/bin/index.js +169 -26
- package/bin/mcp.js +23 -15
- package/dist/index.d.ts +2 -0
- package/dist/index.js +146 -12
- package/dist/lib/status.d.ts +89 -0
- package/dist/mcp/index.js +23 -15
- package/package.json +1 -1
package/README.md
CHANGED
|
@@ -33,7 +33,7 @@ mcps --help
|
|
|
33
33
|
- `mcps env list <server-id>`
|
|
34
34
|
- `mcps env ref <server-id> API_KEY=UPSTREAM_API_KEY --source env`
|
|
35
35
|
- `mcps machines list`
|
|
36
|
-
- `mcps machines add --host
|
|
36
|
+
- `mcps machines add --host linux-node-a --platform linux --arch arm64`
|
|
37
37
|
- `mcps machines seed-defaults`
|
|
38
38
|
- `mcps fleet catalog`
|
|
39
39
|
- `mcps fleet health --refresh`
|
|
@@ -45,8 +45,8 @@ Use machine registration plus fleet health/install commands to manage `@hasna/*`
|
|
|
45
45
|
MCP packages across multiple hosts over SSH.
|
|
46
46
|
|
|
47
47
|
```bash
|
|
48
|
-
mcps machines add --host
|
|
49
|
-
mcps machines add --host
|
|
48
|
+
mcps machines add --host linux-node-a --username hasna --platform linux --arch arm64
|
|
49
|
+
mcps machines add --host macos-node-a --platform darwin --arch arm64
|
|
50
50
|
mcps fleet health --refresh
|
|
51
51
|
mcps fleet install --yes --mode missing-or-outdated
|
|
52
52
|
```
|
package/bin/index.js
CHANGED
|
@@ -35599,30 +35599,30 @@ var init_machines = __esm(() => {
|
|
|
35599
35599
|
init_db();
|
|
35600
35600
|
DEFAULT_MACHINE_SEEDS = [
|
|
35601
35601
|
{
|
|
35602
|
-
id: "
|
|
35603
|
-
name: "
|
|
35604
|
-
host: "
|
|
35602
|
+
id: "linux-node-a",
|
|
35603
|
+
name: "linux-node-a",
|
|
35604
|
+
host: "linux-node-a",
|
|
35605
35605
|
platform: "linux",
|
|
35606
35606
|
arch: "arm64"
|
|
35607
35607
|
},
|
|
35608
35608
|
{
|
|
35609
|
-
id: "
|
|
35610
|
-
name: "
|
|
35611
|
-
host: "
|
|
35609
|
+
id: "linux-node-b",
|
|
35610
|
+
name: "linux-node-b",
|
|
35611
|
+
host: "linux-node-b",
|
|
35612
35612
|
platform: "linux",
|
|
35613
35613
|
arch: "arm64"
|
|
35614
35614
|
},
|
|
35615
35615
|
{
|
|
35616
|
-
id: "
|
|
35617
|
-
name: "
|
|
35618
|
-
host: "
|
|
35616
|
+
id: "macos-node-a",
|
|
35617
|
+
name: "macos-node-a",
|
|
35618
|
+
host: "macos-node-a",
|
|
35619
35619
|
platform: "darwin",
|
|
35620
35620
|
arch: "arm64"
|
|
35621
35621
|
},
|
|
35622
35622
|
{
|
|
35623
|
-
id: "
|
|
35624
|
-
name: "
|
|
35625
|
-
host: "
|
|
35623
|
+
id: "macos-node-b",
|
|
35624
|
+
name: "macos-node-b",
|
|
35625
|
+
host: "macos-node-b",
|
|
35626
35626
|
platform: "darwin",
|
|
35627
35627
|
arch: "arm64"
|
|
35628
35628
|
}
|
|
@@ -36446,7 +36446,7 @@ var init_provider_profiles = __esm(() => {
|
|
|
36446
36446
|
var require_package = __commonJS((exports, module) => {
|
|
36447
36447
|
module.exports = {
|
|
36448
36448
|
name: "@hasna/mcps",
|
|
36449
|
-
version: "0.0.
|
|
36449
|
+
version: "0.0.25",
|
|
36450
36450
|
description: "Meta-MCP registry & CLI \u2014 discover, manage, and proxy MCP servers",
|
|
36451
36451
|
type: "module",
|
|
36452
36452
|
repository: {
|
|
@@ -41303,8 +41303,12 @@ function isStdioMode(args = process.argv.slice(2)) {
|
|
|
41303
41303
|
function resolveHttpPort(args = process.argv.slice(2)) {
|
|
41304
41304
|
for (let i = 0;i < args.length; i++) {
|
|
41305
41305
|
const arg = args[i];
|
|
41306
|
-
if (arg === "--port"
|
|
41307
|
-
|
|
41306
|
+
if (arg === "--port") {
|
|
41307
|
+
const value = args[i + 1];
|
|
41308
|
+
if (value === undefined || value === "" || value.startsWith("--")) {
|
|
41309
|
+
throw new Error("Missing value for --port");
|
|
41310
|
+
}
|
|
41311
|
+
return parsePort(value);
|
|
41308
41312
|
}
|
|
41309
41313
|
if (arg.startsWith("--port=")) {
|
|
41310
41314
|
return parsePort(arg.slice("--port=".length));
|
|
@@ -41317,7 +41321,11 @@ function resolveHttpPort(args = process.argv.slice(2)) {
|
|
|
41317
41321
|
return DEFAULT_HTTP_PORT;
|
|
41318
41322
|
}
|
|
41319
41323
|
function parsePort(raw) {
|
|
41320
|
-
const
|
|
41324
|
+
const normalized = raw.trim();
|
|
41325
|
+
if (!/^\d+$/.test(normalized)) {
|
|
41326
|
+
throw new Error(`Invalid port: ${raw}`);
|
|
41327
|
+
}
|
|
41328
|
+
const port = Number(normalized);
|
|
41321
41329
|
if (!Number.isInteger(port) || port < 1 || port > 65535) {
|
|
41322
41330
|
throw new Error(`Invalid port: ${raw}`);
|
|
41323
41331
|
}
|
|
@@ -43902,6 +43910,145 @@ function App() {
|
|
|
43902
43910
|
|
|
43903
43911
|
// src/cli/index.tsx
|
|
43904
43912
|
init_version();
|
|
43913
|
+
|
|
43914
|
+
// src/lib/status.ts
|
|
43915
|
+
init_config2();
|
|
43916
|
+
init_registry();
|
|
43917
|
+
init_sources();
|
|
43918
|
+
init_provider_profiles();
|
|
43919
|
+
init_machines();
|
|
43920
|
+
init_version();
|
|
43921
|
+
import { existsSync as existsSync12 } from "fs";
|
|
43922
|
+
import { join as join14 } from "path";
|
|
43923
|
+
function activeDataDirEnv() {
|
|
43924
|
+
if (process.env["HASNA_MCPS_DATA_DIR"])
|
|
43925
|
+
return "HASNA_MCPS_DATA_DIR";
|
|
43926
|
+
if (process.env["MCPS_DATA_DIR"])
|
|
43927
|
+
return "MCPS_DATA_DIR";
|
|
43928
|
+
return null;
|
|
43929
|
+
}
|
|
43930
|
+
function activeDatabaseEnv() {
|
|
43931
|
+
if (process.env["HASNA_MCPS_DB_PATH"])
|
|
43932
|
+
return "HASNA_MCPS_DB_PATH";
|
|
43933
|
+
if (process.env["MCPS_DB_PATH"])
|
|
43934
|
+
return "MCPS_DB_PATH";
|
|
43935
|
+
return null;
|
|
43936
|
+
}
|
|
43937
|
+
function countBy(items, getValue) {
|
|
43938
|
+
const counts = {};
|
|
43939
|
+
for (const item of items) {
|
|
43940
|
+
const value = getValue(item);
|
|
43941
|
+
if (!value)
|
|
43942
|
+
continue;
|
|
43943
|
+
counts[value] = (counts[value] ?? 0) + 1;
|
|
43944
|
+
}
|
|
43945
|
+
return counts;
|
|
43946
|
+
}
|
|
43947
|
+
function buildMcpsStatus(input) {
|
|
43948
|
+
const enabledServers = input.servers.filter((server) => server.enabled).length;
|
|
43949
|
+
const enabledSources = input.sources.filter((source) => source.enabled).length;
|
|
43950
|
+
const enabledProfiles = input.providerProfiles.filter((profile) => profile.enabled).length;
|
|
43951
|
+
const enabledMachines = input.machines.filter((machine) => machine.enabled).length;
|
|
43952
|
+
const cachedTools = [...input.toolCounts.values()].reduce((sum, count) => sum + count, 0);
|
|
43953
|
+
const serversWithLastError = input.servers.filter((server) => Boolean(server.last_error)).length;
|
|
43954
|
+
const databaseReachable = input.databaseReachable !== false;
|
|
43955
|
+
const status = databaseReachable && serversWithLastError === 0 ? "ok" : "warn";
|
|
43956
|
+
return {
|
|
43957
|
+
service: "mcps",
|
|
43958
|
+
schemaVersion: "1.0",
|
|
43959
|
+
package: {
|
|
43960
|
+
name: "@hasna/mcps",
|
|
43961
|
+
version: input.packageVersion ?? readPackageVersion(import.meta.url)
|
|
43962
|
+
},
|
|
43963
|
+
env: {
|
|
43964
|
+
dataDir: {
|
|
43965
|
+
primary: "HASNA_MCPS_DATA_DIR",
|
|
43966
|
+
fallback: "MCPS_DATA_DIR",
|
|
43967
|
+
active: activeDataDirEnv()
|
|
43968
|
+
},
|
|
43969
|
+
database: {
|
|
43970
|
+
primary: "HASNA_MCPS_DB_PATH",
|
|
43971
|
+
fallback: "MCPS_DB_PATH",
|
|
43972
|
+
active: activeDatabaseEnv()
|
|
43973
|
+
},
|
|
43974
|
+
credentialVaultConfigured: Boolean(process.env["HASNA_MCPS_CREDENTIAL_VAULT_PATH"])
|
|
43975
|
+
},
|
|
43976
|
+
registry: {
|
|
43977
|
+
sources: {
|
|
43978
|
+
total: input.sources.length,
|
|
43979
|
+
enabled: enabledSources,
|
|
43980
|
+
disabled: input.sources.length - enabledSources,
|
|
43981
|
+
byType: countBy(input.sources, (source) => source.type)
|
|
43982
|
+
},
|
|
43983
|
+
providerProfiles: {
|
|
43984
|
+
total: input.providerProfiles.length,
|
|
43985
|
+
enabled: enabledProfiles,
|
|
43986
|
+
disabled: input.providerProfiles.length - enabledProfiles
|
|
43987
|
+
}
|
|
43988
|
+
},
|
|
43989
|
+
cache: {
|
|
43990
|
+
directoryPresent: input.cacheDirectoryPresent,
|
|
43991
|
+
cachedTools,
|
|
43992
|
+
serversWithCachedTools: [...input.toolCounts.values()].filter((count) => count > 0).length
|
|
43993
|
+
},
|
|
43994
|
+
counts: {
|
|
43995
|
+
servers: {
|
|
43996
|
+
total: input.servers.length,
|
|
43997
|
+
enabled: enabledServers,
|
|
43998
|
+
disabled: input.servers.length - enabledServers,
|
|
43999
|
+
byTransport: countBy(input.servers, (server) => server.transport),
|
|
44000
|
+
bySource: countBy(input.servers, (server) => server.source),
|
|
44001
|
+
withLastError: serversWithLastError
|
|
44002
|
+
},
|
|
44003
|
+
machines: {
|
|
44004
|
+
total: input.machines.length,
|
|
44005
|
+
enabled: enabledMachines,
|
|
44006
|
+
disabled: input.machines.length - enabledMachines
|
|
44007
|
+
}
|
|
44008
|
+
},
|
|
44009
|
+
health: {
|
|
44010
|
+
status,
|
|
44011
|
+
databaseReachable,
|
|
44012
|
+
hasRegisteredServers: input.servers.length > 0,
|
|
44013
|
+
hasServerErrors: serversWithLastError > 0
|
|
44014
|
+
},
|
|
44015
|
+
safety: {
|
|
44016
|
+
includesToolConfigs: false,
|
|
44017
|
+
includesCommands: false,
|
|
44018
|
+
includesArgs: false,
|
|
44019
|
+
includesEnvValues: false,
|
|
44020
|
+
includesCredentialRefs: false,
|
|
44021
|
+
includesTokens: false,
|
|
44022
|
+
includesPrivatePaths: false,
|
|
44023
|
+
includesRegistryUrls: false,
|
|
44024
|
+
statusOutputIsMetadataOnly: true
|
|
44025
|
+
}
|
|
44026
|
+
};
|
|
44027
|
+
}
|
|
44028
|
+
function getMcpsStatus() {
|
|
44029
|
+
try {
|
|
44030
|
+
return buildMcpsStatus({
|
|
44031
|
+
servers: listServers(),
|
|
44032
|
+
sources: listSources(),
|
|
44033
|
+
providerProfiles: listProviderProfiles(),
|
|
44034
|
+
machines: listMachines(),
|
|
44035
|
+
toolCounts: getToolCounts(),
|
|
44036
|
+
cacheDirectoryPresent: existsSync12(join14(MCPS_DIR, "cache"))
|
|
44037
|
+
});
|
|
44038
|
+
} catch {
|
|
44039
|
+
return buildMcpsStatus({
|
|
44040
|
+
servers: [],
|
|
44041
|
+
sources: [],
|
|
44042
|
+
providerProfiles: [],
|
|
44043
|
+
machines: [],
|
|
44044
|
+
toolCounts: new Map,
|
|
44045
|
+
cacheDirectoryPresent: false,
|
|
44046
|
+
databaseReachable: false
|
|
44047
|
+
});
|
|
44048
|
+
}
|
|
44049
|
+
}
|
|
44050
|
+
|
|
44051
|
+
// src/cli/index.tsx
|
|
43905
44052
|
var VERSION3 = (() => {
|
|
43906
44053
|
return readPackageVersion(import.meta.url);
|
|
43907
44054
|
})();
|
|
@@ -44593,21 +44740,17 @@ program2.command("info").argument("<id>", "Server ID").description("Show server
|
|
|
44593
44740
|
closeDb();
|
|
44594
44741
|
});
|
|
44595
44742
|
program2.command("status").description("Show registry stats").option("--json", "Output as JSON").action((opts) => {
|
|
44596
|
-
const
|
|
44597
|
-
const enabled = servers.filter((s) => s.enabled).length;
|
|
44598
|
-
const disabled = servers.length - enabled;
|
|
44599
|
-
const toolCounts = getToolCounts();
|
|
44600
|
-
let totalTools = 0;
|
|
44601
|
-
for (const s of servers)
|
|
44602
|
-
totalTools += toolCounts.get(s.id) ?? 0;
|
|
44743
|
+
const status = getMcpsStatus();
|
|
44603
44744
|
if (opts.json) {
|
|
44604
|
-
console.log(JSON.stringify(
|
|
44745
|
+
console.log(JSON.stringify(status, null, 2));
|
|
44605
44746
|
closeDb();
|
|
44606
44747
|
return;
|
|
44607
44748
|
}
|
|
44608
44749
|
console.log(chalk2.bold("Registry Status"));
|
|
44609
|
-
console.log(`
|
|
44610
|
-
console.log(`
|
|
44750
|
+
console.log(` Package: ${status.package.version}`);
|
|
44751
|
+
console.log(` Servers: ${status.counts.servers.total} (${chalk2.green(`${status.counts.servers.enabled} enabled`)}, ${chalk2.red(`${status.counts.servers.disabled} disabled`)})`);
|
|
44752
|
+
console.log(` Sources: ${status.registry.sources.total} (${chalk2.green(`${status.registry.sources.enabled} enabled`)}, ${chalk2.red(`${status.registry.sources.disabled} disabled`)})`);
|
|
44753
|
+
console.log(` Tools: ${status.cache.cachedTools} (cached)`);
|
|
44611
44754
|
closeDb();
|
|
44612
44755
|
});
|
|
44613
44756
|
program2.command("doctor").argument("[id]", "Server ID to check (omit to check all)").description("Diagnose server health \u2014 checks PATH, env vars, connectivity").option("--fix", "Attempt to fix issues automatically").option("--yes", "Approve probing and launching local stdio commands").option("--allow-local-stdio", "Approve probing and launching local stdio commands").option("--allow-risky-command", "Approve high-risk local command patterns").action(async (id, opts) => {
|
package/bin/mcp.js
CHANGED
|
@@ -34898,30 +34898,30 @@ var init_machines = __esm(() => {
|
|
|
34898
34898
|
init_db();
|
|
34899
34899
|
DEFAULT_MACHINE_SEEDS = [
|
|
34900
34900
|
{
|
|
34901
|
-
id: "
|
|
34902
|
-
name: "
|
|
34903
|
-
host: "
|
|
34901
|
+
id: "linux-node-a",
|
|
34902
|
+
name: "linux-node-a",
|
|
34903
|
+
host: "linux-node-a",
|
|
34904
34904
|
platform: "linux",
|
|
34905
34905
|
arch: "arm64"
|
|
34906
34906
|
},
|
|
34907
34907
|
{
|
|
34908
|
-
id: "
|
|
34909
|
-
name: "
|
|
34910
|
-
host: "
|
|
34908
|
+
id: "linux-node-b",
|
|
34909
|
+
name: "linux-node-b",
|
|
34910
|
+
host: "linux-node-b",
|
|
34911
34911
|
platform: "linux",
|
|
34912
34912
|
arch: "arm64"
|
|
34913
34913
|
},
|
|
34914
34914
|
{
|
|
34915
|
-
id: "
|
|
34916
|
-
name: "
|
|
34917
|
-
host: "
|
|
34915
|
+
id: "macos-node-a",
|
|
34916
|
+
name: "macos-node-a",
|
|
34917
|
+
host: "macos-node-a",
|
|
34918
34918
|
platform: "darwin",
|
|
34919
34919
|
arch: "arm64"
|
|
34920
34920
|
},
|
|
34921
34921
|
{
|
|
34922
|
-
id: "
|
|
34923
|
-
name: "
|
|
34924
|
-
host: "
|
|
34922
|
+
id: "macos-node-b",
|
|
34923
|
+
name: "macos-node-b",
|
|
34924
|
+
host: "macos-node-b",
|
|
34925
34925
|
platform: "darwin",
|
|
34926
34926
|
arch: "arm64"
|
|
34927
34927
|
}
|
|
@@ -37682,8 +37682,12 @@ function isStdioMode(args = process.argv.slice(2)) {
|
|
|
37682
37682
|
function resolveHttpPort(args = process.argv.slice(2)) {
|
|
37683
37683
|
for (let i = 0;i < args.length; i++) {
|
|
37684
37684
|
const arg = args[i];
|
|
37685
|
-
if (arg === "--port"
|
|
37686
|
-
|
|
37685
|
+
if (arg === "--port") {
|
|
37686
|
+
const value = args[i + 1];
|
|
37687
|
+
if (value === undefined || value === "" || value.startsWith("--")) {
|
|
37688
|
+
throw new Error("Missing value for --port");
|
|
37689
|
+
}
|
|
37690
|
+
return parsePort(value);
|
|
37687
37691
|
}
|
|
37688
37692
|
if (arg.startsWith("--port=")) {
|
|
37689
37693
|
return parsePort(arg.slice("--port=".length));
|
|
@@ -37696,7 +37700,11 @@ function resolveHttpPort(args = process.argv.slice(2)) {
|
|
|
37696
37700
|
return DEFAULT_HTTP_PORT;
|
|
37697
37701
|
}
|
|
37698
37702
|
function parsePort(raw) {
|
|
37699
|
-
const
|
|
37703
|
+
const normalized = raw.trim();
|
|
37704
|
+
if (!/^\d+$/.test(normalized)) {
|
|
37705
|
+
throw new Error(`Invalid port: ${raw}`);
|
|
37706
|
+
}
|
|
37707
|
+
const port = Number(normalized);
|
|
37700
37708
|
if (!Number.isInteger(port) || port < 1 || port > 65535) {
|
|
37701
37709
|
throw new Error(`Invalid port: ${raw}`);
|
|
37702
37710
|
}
|
package/dist/index.d.ts
CHANGED
|
@@ -14,6 +14,8 @@ export type { McpSource, AddSourceOptions } from "./types.js";
|
|
|
14
14
|
export { addMachine, upsertMachine, listMachines, getMachine, updateMachine, removeMachine, seedDefaultMachines, DEFAULT_MACHINE_SEEDS, } from "./lib/machines.js";
|
|
15
15
|
export { listHasnaMcpCatalog, runFleetHealthCheck, runFleetInstall } from "./lib/fleet.js";
|
|
16
16
|
export { readPackageVersion } from "./lib/version.js";
|
|
17
|
+
export { buildMcpsStatus, getMcpsStatus } from "./lib/status.js";
|
|
18
|
+
export type { McpsStatusContract } from "./lib/status.js";
|
|
17
19
|
export { assertLocalCommandConsent, formatLocalCommandReview, inspectLocalCommand, LocalCommandConsentError, } from "./lib/local-command-consent.js";
|
|
18
20
|
export { CredentialReferenceError, REDACTED_CREDENTIAL_VALUE, credentialRefPlaceholders, isSecretLikeEnvKey, isSecretLikeValue, normalizeCredentialRefs, normalizeCredentialRef, normalizeLiteralEnv, redactEnv, redactServerCredentials, resolveServerEnv, } from "./lib/credentials.js";
|
|
19
21
|
export type { LocalCommandConsent, LocalCommandInput, LocalCommandOperation, LocalCommandReview, LocalCommandRisk, } from "./lib/local-command-consent.js";
|
package/dist/index.js
CHANGED
|
@@ -26857,30 +26857,30 @@ function removeMachine(id) {
|
|
|
26857
26857
|
}
|
|
26858
26858
|
var DEFAULT_MACHINE_SEEDS = [
|
|
26859
26859
|
{
|
|
26860
|
-
id: "
|
|
26861
|
-
name: "
|
|
26862
|
-
host: "
|
|
26860
|
+
id: "linux-node-a",
|
|
26861
|
+
name: "linux-node-a",
|
|
26862
|
+
host: "linux-node-a",
|
|
26863
26863
|
platform: "linux",
|
|
26864
26864
|
arch: "arm64"
|
|
26865
26865
|
},
|
|
26866
26866
|
{
|
|
26867
|
-
id: "
|
|
26868
|
-
name: "
|
|
26869
|
-
host: "
|
|
26867
|
+
id: "linux-node-b",
|
|
26868
|
+
name: "linux-node-b",
|
|
26869
|
+
host: "linux-node-b",
|
|
26870
26870
|
platform: "linux",
|
|
26871
26871
|
arch: "arm64"
|
|
26872
26872
|
},
|
|
26873
26873
|
{
|
|
26874
|
-
id: "
|
|
26875
|
-
name: "
|
|
26876
|
-
host: "
|
|
26874
|
+
id: "macos-node-a",
|
|
26875
|
+
name: "macos-node-a",
|
|
26876
|
+
host: "macos-node-a",
|
|
26877
26877
|
platform: "darwin",
|
|
26878
26878
|
arch: "arm64"
|
|
26879
26879
|
},
|
|
26880
26880
|
{
|
|
26881
|
-
id: "
|
|
26882
|
-
name: "
|
|
26883
|
-
host: "
|
|
26881
|
+
id: "macos-node-b",
|
|
26882
|
+
name: "macos-node-b",
|
|
26883
|
+
host: "macos-node-b",
|
|
26884
26884
|
platform: "darwin",
|
|
26885
26885
|
arch: "arm64"
|
|
26886
26886
|
}
|
|
@@ -27612,6 +27612,138 @@ function readPackageVersion(moduleUrl, fallback = FALLBACK_VERSION) {
|
|
|
27612
27612
|
}
|
|
27613
27613
|
return fallback;
|
|
27614
27614
|
}
|
|
27615
|
+
// src/lib/status.ts
|
|
27616
|
+
init_config2();
|
|
27617
|
+
import { existsSync as existsSync12 } from "fs";
|
|
27618
|
+
import { join as join13 } from "path";
|
|
27619
|
+
init_sources();
|
|
27620
|
+
function activeDataDirEnv() {
|
|
27621
|
+
if (process.env["HASNA_MCPS_DATA_DIR"])
|
|
27622
|
+
return "HASNA_MCPS_DATA_DIR";
|
|
27623
|
+
if (process.env["MCPS_DATA_DIR"])
|
|
27624
|
+
return "MCPS_DATA_DIR";
|
|
27625
|
+
return null;
|
|
27626
|
+
}
|
|
27627
|
+
function activeDatabaseEnv() {
|
|
27628
|
+
if (process.env["HASNA_MCPS_DB_PATH"])
|
|
27629
|
+
return "HASNA_MCPS_DB_PATH";
|
|
27630
|
+
if (process.env["MCPS_DB_PATH"])
|
|
27631
|
+
return "MCPS_DB_PATH";
|
|
27632
|
+
return null;
|
|
27633
|
+
}
|
|
27634
|
+
function countBy(items, getValue) {
|
|
27635
|
+
const counts = {};
|
|
27636
|
+
for (const item of items) {
|
|
27637
|
+
const value = getValue(item);
|
|
27638
|
+
if (!value)
|
|
27639
|
+
continue;
|
|
27640
|
+
counts[value] = (counts[value] ?? 0) + 1;
|
|
27641
|
+
}
|
|
27642
|
+
return counts;
|
|
27643
|
+
}
|
|
27644
|
+
function buildMcpsStatus(input) {
|
|
27645
|
+
const enabledServers = input.servers.filter((server) => server.enabled).length;
|
|
27646
|
+
const enabledSources = input.sources.filter((source) => source.enabled).length;
|
|
27647
|
+
const enabledProfiles = input.providerProfiles.filter((profile) => profile.enabled).length;
|
|
27648
|
+
const enabledMachines = input.machines.filter((machine) => machine.enabled).length;
|
|
27649
|
+
const cachedTools = [...input.toolCounts.values()].reduce((sum, count) => sum + count, 0);
|
|
27650
|
+
const serversWithLastError = input.servers.filter((server) => Boolean(server.last_error)).length;
|
|
27651
|
+
const databaseReachable = input.databaseReachable !== false;
|
|
27652
|
+
const status = databaseReachable && serversWithLastError === 0 ? "ok" : "warn";
|
|
27653
|
+
return {
|
|
27654
|
+
service: "mcps",
|
|
27655
|
+
schemaVersion: "1.0",
|
|
27656
|
+
package: {
|
|
27657
|
+
name: "@hasna/mcps",
|
|
27658
|
+
version: input.packageVersion ?? readPackageVersion(import.meta.url)
|
|
27659
|
+
},
|
|
27660
|
+
env: {
|
|
27661
|
+
dataDir: {
|
|
27662
|
+
primary: "HASNA_MCPS_DATA_DIR",
|
|
27663
|
+
fallback: "MCPS_DATA_DIR",
|
|
27664
|
+
active: activeDataDirEnv()
|
|
27665
|
+
},
|
|
27666
|
+
database: {
|
|
27667
|
+
primary: "HASNA_MCPS_DB_PATH",
|
|
27668
|
+
fallback: "MCPS_DB_PATH",
|
|
27669
|
+
active: activeDatabaseEnv()
|
|
27670
|
+
},
|
|
27671
|
+
credentialVaultConfigured: Boolean(process.env["HASNA_MCPS_CREDENTIAL_VAULT_PATH"])
|
|
27672
|
+
},
|
|
27673
|
+
registry: {
|
|
27674
|
+
sources: {
|
|
27675
|
+
total: input.sources.length,
|
|
27676
|
+
enabled: enabledSources,
|
|
27677
|
+
disabled: input.sources.length - enabledSources,
|
|
27678
|
+
byType: countBy(input.sources, (source) => source.type)
|
|
27679
|
+
},
|
|
27680
|
+
providerProfiles: {
|
|
27681
|
+
total: input.providerProfiles.length,
|
|
27682
|
+
enabled: enabledProfiles,
|
|
27683
|
+
disabled: input.providerProfiles.length - enabledProfiles
|
|
27684
|
+
}
|
|
27685
|
+
},
|
|
27686
|
+
cache: {
|
|
27687
|
+
directoryPresent: input.cacheDirectoryPresent,
|
|
27688
|
+
cachedTools,
|
|
27689
|
+
serversWithCachedTools: [...input.toolCounts.values()].filter((count) => count > 0).length
|
|
27690
|
+
},
|
|
27691
|
+
counts: {
|
|
27692
|
+
servers: {
|
|
27693
|
+
total: input.servers.length,
|
|
27694
|
+
enabled: enabledServers,
|
|
27695
|
+
disabled: input.servers.length - enabledServers,
|
|
27696
|
+
byTransport: countBy(input.servers, (server) => server.transport),
|
|
27697
|
+
bySource: countBy(input.servers, (server) => server.source),
|
|
27698
|
+
withLastError: serversWithLastError
|
|
27699
|
+
},
|
|
27700
|
+
machines: {
|
|
27701
|
+
total: input.machines.length,
|
|
27702
|
+
enabled: enabledMachines,
|
|
27703
|
+
disabled: input.machines.length - enabledMachines
|
|
27704
|
+
}
|
|
27705
|
+
},
|
|
27706
|
+
health: {
|
|
27707
|
+
status,
|
|
27708
|
+
databaseReachable,
|
|
27709
|
+
hasRegisteredServers: input.servers.length > 0,
|
|
27710
|
+
hasServerErrors: serversWithLastError > 0
|
|
27711
|
+
},
|
|
27712
|
+
safety: {
|
|
27713
|
+
includesToolConfigs: false,
|
|
27714
|
+
includesCommands: false,
|
|
27715
|
+
includesArgs: false,
|
|
27716
|
+
includesEnvValues: false,
|
|
27717
|
+
includesCredentialRefs: false,
|
|
27718
|
+
includesTokens: false,
|
|
27719
|
+
includesPrivatePaths: false,
|
|
27720
|
+
includesRegistryUrls: false,
|
|
27721
|
+
statusOutputIsMetadataOnly: true
|
|
27722
|
+
}
|
|
27723
|
+
};
|
|
27724
|
+
}
|
|
27725
|
+
function getMcpsStatus() {
|
|
27726
|
+
try {
|
|
27727
|
+
return buildMcpsStatus({
|
|
27728
|
+
servers: listServers(),
|
|
27729
|
+
sources: listSources(),
|
|
27730
|
+
providerProfiles: listProviderProfiles(),
|
|
27731
|
+
machines: listMachines(),
|
|
27732
|
+
toolCounts: getToolCounts(),
|
|
27733
|
+
cacheDirectoryPresent: existsSync12(join13(MCPS_DIR, "cache"))
|
|
27734
|
+
});
|
|
27735
|
+
} catch {
|
|
27736
|
+
return buildMcpsStatus({
|
|
27737
|
+
servers: [],
|
|
27738
|
+
sources: [],
|
|
27739
|
+
providerProfiles: [],
|
|
27740
|
+
machines: [],
|
|
27741
|
+
toolCounts: new Map,
|
|
27742
|
+
cacheDirectoryPresent: false,
|
|
27743
|
+
databaseReachable: false
|
|
27744
|
+
});
|
|
27745
|
+
}
|
|
27746
|
+
}
|
|
27615
27747
|
|
|
27616
27748
|
// src/index.ts
|
|
27617
27749
|
init_db();
|
|
@@ -27660,6 +27792,7 @@ export {
|
|
|
27660
27792
|
getServer,
|
|
27661
27793
|
getRegistryServer,
|
|
27662
27794
|
getProviderProfile,
|
|
27795
|
+
getMcpsStatus,
|
|
27663
27796
|
getMachine,
|
|
27664
27797
|
getDb,
|
|
27665
27798
|
getCachedTools,
|
|
@@ -27679,6 +27812,7 @@ export {
|
|
|
27679
27812
|
closeDb,
|
|
27680
27813
|
cloneServer,
|
|
27681
27814
|
callTool,
|
|
27815
|
+
buildMcpsStatus,
|
|
27682
27816
|
assertLocalCommandConsent,
|
|
27683
27817
|
addSource,
|
|
27684
27818
|
addServer,
|
|
@@ -0,0 +1,89 @@
|
|
|
1
|
+
import type { McpServerEntry, McpSource, ProviderProfile } from "../types.js";
|
|
2
|
+
type ActiveDataDirEnv = "HASNA_MCPS_DATA_DIR" | "MCPS_DATA_DIR" | null;
|
|
3
|
+
type ActiveDbEnv = "HASNA_MCPS_DB_PATH" | "MCPS_DB_PATH" | null;
|
|
4
|
+
type ContractStatus = "ok" | "warn";
|
|
5
|
+
export interface McpsStatusContract {
|
|
6
|
+
service: "mcps";
|
|
7
|
+
schemaVersion: "1.0";
|
|
8
|
+
package: {
|
|
9
|
+
name: "@hasna/mcps";
|
|
10
|
+
version: string;
|
|
11
|
+
};
|
|
12
|
+
env: {
|
|
13
|
+
dataDir: {
|
|
14
|
+
primary: "HASNA_MCPS_DATA_DIR";
|
|
15
|
+
fallback: "MCPS_DATA_DIR";
|
|
16
|
+
active: ActiveDataDirEnv;
|
|
17
|
+
};
|
|
18
|
+
database: {
|
|
19
|
+
primary: "HASNA_MCPS_DB_PATH";
|
|
20
|
+
fallback: "MCPS_DB_PATH";
|
|
21
|
+
active: ActiveDbEnv;
|
|
22
|
+
};
|
|
23
|
+
credentialVaultConfigured: boolean;
|
|
24
|
+
};
|
|
25
|
+
registry: {
|
|
26
|
+
sources: {
|
|
27
|
+
total: number;
|
|
28
|
+
enabled: number;
|
|
29
|
+
disabled: number;
|
|
30
|
+
byType: Record<string, number>;
|
|
31
|
+
};
|
|
32
|
+
providerProfiles: {
|
|
33
|
+
total: number;
|
|
34
|
+
enabled: number;
|
|
35
|
+
disabled: number;
|
|
36
|
+
};
|
|
37
|
+
};
|
|
38
|
+
cache: {
|
|
39
|
+
directoryPresent: boolean;
|
|
40
|
+
cachedTools: number;
|
|
41
|
+
serversWithCachedTools: number;
|
|
42
|
+
};
|
|
43
|
+
counts: {
|
|
44
|
+
servers: {
|
|
45
|
+
total: number;
|
|
46
|
+
enabled: number;
|
|
47
|
+
disabled: number;
|
|
48
|
+
byTransport: Record<string, number>;
|
|
49
|
+
bySource: Record<string, number>;
|
|
50
|
+
withLastError: number;
|
|
51
|
+
};
|
|
52
|
+
machines: {
|
|
53
|
+
total: number;
|
|
54
|
+
enabled: number;
|
|
55
|
+
disabled: number;
|
|
56
|
+
};
|
|
57
|
+
};
|
|
58
|
+
health: {
|
|
59
|
+
status: ContractStatus;
|
|
60
|
+
databaseReachable: boolean;
|
|
61
|
+
hasRegisteredServers: boolean;
|
|
62
|
+
hasServerErrors: boolean;
|
|
63
|
+
};
|
|
64
|
+
safety: {
|
|
65
|
+
includesToolConfigs: false;
|
|
66
|
+
includesCommands: false;
|
|
67
|
+
includesArgs: false;
|
|
68
|
+
includesEnvValues: false;
|
|
69
|
+
includesCredentialRefs: false;
|
|
70
|
+
includesTokens: false;
|
|
71
|
+
includesPrivatePaths: false;
|
|
72
|
+
includesRegistryUrls: false;
|
|
73
|
+
statusOutputIsMetadataOnly: true;
|
|
74
|
+
};
|
|
75
|
+
}
|
|
76
|
+
export declare function buildMcpsStatus(input: {
|
|
77
|
+
servers: McpServerEntry[];
|
|
78
|
+
sources: McpSource[];
|
|
79
|
+
providerProfiles: ProviderProfile[];
|
|
80
|
+
machines: Array<{
|
|
81
|
+
enabled: boolean;
|
|
82
|
+
}>;
|
|
83
|
+
toolCounts: Map<string, number>;
|
|
84
|
+
cacheDirectoryPresent: boolean;
|
|
85
|
+
databaseReachable?: boolean;
|
|
86
|
+
packageVersion?: string;
|
|
87
|
+
}): McpsStatusContract;
|
|
88
|
+
export declare function getMcpsStatus(): McpsStatusContract;
|
|
89
|
+
export {};
|
package/dist/mcp/index.js
CHANGED
|
@@ -34898,30 +34898,30 @@ var init_machines = __esm(() => {
|
|
|
34898
34898
|
init_db();
|
|
34899
34899
|
DEFAULT_MACHINE_SEEDS = [
|
|
34900
34900
|
{
|
|
34901
|
-
id: "
|
|
34902
|
-
name: "
|
|
34903
|
-
host: "
|
|
34901
|
+
id: "linux-node-a",
|
|
34902
|
+
name: "linux-node-a",
|
|
34903
|
+
host: "linux-node-a",
|
|
34904
34904
|
platform: "linux",
|
|
34905
34905
|
arch: "arm64"
|
|
34906
34906
|
},
|
|
34907
34907
|
{
|
|
34908
|
-
id: "
|
|
34909
|
-
name: "
|
|
34910
|
-
host: "
|
|
34908
|
+
id: "linux-node-b",
|
|
34909
|
+
name: "linux-node-b",
|
|
34910
|
+
host: "linux-node-b",
|
|
34911
34911
|
platform: "linux",
|
|
34912
34912
|
arch: "arm64"
|
|
34913
34913
|
},
|
|
34914
34914
|
{
|
|
34915
|
-
id: "
|
|
34916
|
-
name: "
|
|
34917
|
-
host: "
|
|
34915
|
+
id: "macos-node-a",
|
|
34916
|
+
name: "macos-node-a",
|
|
34917
|
+
host: "macos-node-a",
|
|
34918
34918
|
platform: "darwin",
|
|
34919
34919
|
arch: "arm64"
|
|
34920
34920
|
},
|
|
34921
34921
|
{
|
|
34922
|
-
id: "
|
|
34923
|
-
name: "
|
|
34924
|
-
host: "
|
|
34922
|
+
id: "macos-node-b",
|
|
34923
|
+
name: "macos-node-b",
|
|
34924
|
+
host: "macos-node-b",
|
|
34925
34925
|
platform: "darwin",
|
|
34926
34926
|
arch: "arm64"
|
|
34927
34927
|
}
|
|
@@ -37682,8 +37682,12 @@ function isStdioMode(args = process.argv.slice(2)) {
|
|
|
37682
37682
|
function resolveHttpPort(args = process.argv.slice(2)) {
|
|
37683
37683
|
for (let i = 0;i < args.length; i++) {
|
|
37684
37684
|
const arg = args[i];
|
|
37685
|
-
if (arg === "--port"
|
|
37686
|
-
|
|
37685
|
+
if (arg === "--port") {
|
|
37686
|
+
const value = args[i + 1];
|
|
37687
|
+
if (value === undefined || value === "" || value.startsWith("--")) {
|
|
37688
|
+
throw new Error("Missing value for --port");
|
|
37689
|
+
}
|
|
37690
|
+
return parsePort(value);
|
|
37687
37691
|
}
|
|
37688
37692
|
if (arg.startsWith("--port=")) {
|
|
37689
37693
|
return parsePort(arg.slice("--port=".length));
|
|
@@ -37696,7 +37700,11 @@ function resolveHttpPort(args = process.argv.slice(2)) {
|
|
|
37696
37700
|
return DEFAULT_HTTP_PORT;
|
|
37697
37701
|
}
|
|
37698
37702
|
function parsePort(raw) {
|
|
37699
|
-
const
|
|
37703
|
+
const normalized = raw.trim();
|
|
37704
|
+
if (!/^\d+$/.test(normalized)) {
|
|
37705
|
+
throw new Error(`Invalid port: ${raw}`);
|
|
37706
|
+
}
|
|
37707
|
+
const port = Number(normalized);
|
|
37700
37708
|
if (!Number.isInteger(port) || port < 1 || port > 65535) {
|
|
37701
37709
|
throw new Error(`Invalid port: ${raw}`);
|
|
37702
37710
|
}
|