@kya-os/create-mcpi-app 1.7.35 → 1.7.37
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/.turbo/turbo-test$colon$coverage.log +168 -305
- package/.turbo/turbo-test.log +146 -323
- package/dist/.tsbuildinfo +1 -1
- package/dist/helpers/fetch-cloudflare-mcpi-template.d.ts.map +1 -1
- package/dist/helpers/fetch-cloudflare-mcpi-template.js +62 -90
- package/dist/helpers/fetch-cloudflare-mcpi-template.js.map +1 -1
- package/dist/index.js +18 -12
- package/dist/index.js.map +1 -1
- package/package.json +3 -3
- package/src/helpers/fetch-cloudflare-mcpi-template.ts +74 -122
- package/src/index.ts +66 -26
- package/test-cloudflare/src/index.ts +1 -0
- package/test-cloudflare/tsconfig.json +4 -10
- package/coverage/base.css +0 -224
- package/coverage/block-navigation.js +0 -87
- package/coverage/clover.xml +0 -268
- package/coverage/config-builder.ts.html +0 -580
- package/coverage/coverage-final.json +0 -7
- package/coverage/favicon.png +0 -0
- package/coverage/fetch-cloudflare-mcpi-template.ts.html +0 -7345
- package/coverage/generate-config.ts.html +0 -442
- package/coverage/generate-identity.ts.html +0 -574
- package/coverage/index.html +0 -191
- package/coverage/install.ts.html +0 -322
- package/coverage/prettify.css +0 -1
- package/coverage/prettify.js +0 -2
- package/coverage/sort-arrow-sprite.png +0 -0
- package/coverage/sorter.js +0 -210
- package/coverage/validate-project-structure.ts.html +0 -466
|
@@ -79,6 +79,7 @@ export async function fetchCloudflareMcpiTemplate(
|
|
|
79
79
|
"test:coverage": "vitest run --coverage",
|
|
80
80
|
},
|
|
81
81
|
dependencies: {
|
|
82
|
+
"@kya-os/contracts": "^1.5.1",
|
|
82
83
|
"@kya-os/mcp-i-cloudflare": "^1.3.2",
|
|
83
84
|
"@modelcontextprotocol/sdk": "^1.19.1",
|
|
84
85
|
agents: "^0.2.8",
|
|
@@ -1003,7 +1004,7 @@ export class ${pascalClassName}MCP extends McpAgent {
|
|
|
1003
1004
|
return undefined;
|
|
1004
1005
|
}
|
|
1005
1006
|
|
|
1006
|
-
const toolProtectionConfig:
|
|
1007
|
+
const toolProtectionConfig: import('@kya-os/mcp-i-core').ToolProtectionServiceConfig = {
|
|
1007
1008
|
apiUrl: runtimeConfig.toolProtection.agentShield?.apiUrl || env.AGENTSHIELD_API_URL || 'https://kya.vouched.id',
|
|
1008
1009
|
apiKey: apiKey,
|
|
1009
1010
|
projectId: runtimeConfig.toolProtection.agentShield?.projectId || env.AGENTSHIELD_PROJECT_ID,
|
|
@@ -1804,23 +1805,22 @@ XMCP_I_SESSION_TTL = "1800"
|
|
|
1804
1805
|
|
|
1805
1806
|
# AgentShield Integration (https://kya.vouched.id)
|
|
1806
1807
|
AGENTSHIELD_API_URL = "https://kya.vouched.id"
|
|
1807
|
-
# AGENTSHIELD_API_KEY - MUST be declared here for .dev.vars to work
|
|
1808
|
-
# Development: Values in .dev.vars will override this empty string
|
|
1809
|
-
# Production: Use wrangler secret put AGENTSHIELD_API_KEY
|
|
1810
|
-
AGENTSHIELD_API_KEY = ""
|
|
1811
1808
|
# AGENTSHIELD_PROJECT_ID - Your project ID from AgentShield dashboard (e.g., "batman-txh0ae")
|
|
1812
1809
|
# Required for project-scoped tool protection configuration (recommended)
|
|
1813
1810
|
# Find it in your dashboard URL: https://kya.vouched.id/dashboard/projects/{PROJECT_ID}
|
|
1814
1811
|
# Or in your project settings
|
|
1815
|
-
# This is not sensitive, so it's safe to keep a value here
|
|
1812
|
+
# This is not sensitive, so it's safe to keep a value here
|
|
1816
1813
|
AGENTSHIELD_PROJECT_ID = "${projectId || ""}"
|
|
1817
|
-
# ADMIN_API_KEY - Used for protected admin endpoints (e.g., /admin/clear-cache)
|
|
1818
|
-
# Set to same value as AGENTSHIELD_API_KEY by default
|
|
1819
|
-
# Development: Values in .dev.vars will override this empty string
|
|
1820
|
-
# Production: Use wrangler secret put ADMIN_API_KEY
|
|
1821
|
-
ADMIN_API_KEY = ""
|
|
1822
1814
|
MCPI_ENV = "development"
|
|
1823
1815
|
|
|
1816
|
+
# Secrets (NOT declared here - see instructions below)
|
|
1817
|
+
# For local development: Add secrets to .dev.vars file
|
|
1818
|
+
# For production: Use wrangler secret put COMMAND_NAME
|
|
1819
|
+
# $ wrangler secret put MCP_IDENTITY_PRIVATE_KEY
|
|
1820
|
+
# $ wrangler secret put AGENTSHIELD_API_KEY
|
|
1821
|
+
# $ wrangler secret put ADMIN_API_KEY
|
|
1822
|
+
# Note: .dev.vars is git-ignored and contains actual secret values for local dev
|
|
1823
|
+
|
|
1824
1824
|
# Optional: MCP Server URL for tool discovery
|
|
1825
1825
|
# Uncomment to explicitly set your MCP server URL (auto-detected if not set)
|
|
1826
1826
|
# MCP_SERVER_URL = "https://your-worker.workers.dev/mcp"
|
|
@@ -1847,11 +1847,12 @@ MCPI_ENV = "development"
|
|
|
1847
1847
|
# Agent DID (public identifier - safe to commit)
|
|
1848
1848
|
MCP_IDENTITY_AGENT_DID = "${identity.did}"
|
|
1849
1849
|
|
|
1850
|
-
#
|
|
1851
|
-
|
|
1852
|
-
|
|
1853
|
-
|
|
1854
|
-
|
|
1850
|
+
# Public identity key (safe to commit - not sensitive)
|
|
1851
|
+
MCP_IDENTITY_PUBLIC_KEY = "${identity.publicKey}"
|
|
1852
|
+
|
|
1853
|
+
# Private identity key (SECRET - NOT declared here)
|
|
1854
|
+
# For local development: Add to .dev.vars file
|
|
1855
|
+
# For production: Use wrangler secret put MCP_IDENTITY_PRIVATE_KEY
|
|
1855
1856
|
|
|
1856
1857
|
# ALLOWED_ORIGINS for CORS (update for production)
|
|
1857
1858
|
ALLOWED_ORIGINS = "https://claude.ai,https://app.anthropic.com"
|
|
@@ -1862,36 +1863,26 @@ DO_SHARD_COUNT = "10" # Number of shards if using shard strategy
|
|
|
1862
1863
|
|
|
1863
1864
|
`;
|
|
1864
1865
|
|
|
1865
|
-
//
|
|
1866
|
-
//
|
|
1867
|
-
|
|
1868
|
-
|
|
1866
|
+
// Remove any secret declarations from [vars] (they should not be here)
|
|
1867
|
+
// Secrets go in .dev.vars for local dev, wrangler secret put for production
|
|
1868
|
+
wranglerTomlContent = wranglerTomlContent.replace(
|
|
1869
|
+
/^\s*MCP_IDENTITY_PRIVATE_KEY\s*=.*$/gm,
|
|
1870
|
+
`# MCP_IDENTITY_PRIVATE_KEY - SECRET (not declared here, see .dev.vars or wrangler secret put)`
|
|
1871
|
+
);
|
|
1872
|
+
wranglerTomlContent = wranglerTomlContent.replace(
|
|
1873
|
+
/^\s*AGENTSHIELD_API_KEY\s*=.*$/gm,
|
|
1874
|
+
`# AGENTSHIELD_API_KEY - SECRET (not declared here, see .dev.vars or wrangler secret put)`
|
|
1875
|
+
);
|
|
1876
|
+
wranglerTomlContent = wranglerTomlContent.replace(
|
|
1877
|
+
/^\s*ADMIN_API_KEY\s*=.*$/gm,
|
|
1878
|
+
`# ADMIN_API_KEY - SECRET (not declared here, see .dev.vars or wrangler secret put)`
|
|
1879
|
+
);
|
|
1869
1880
|
|
|
1870
|
-
//
|
|
1871
|
-
if (/MCP_IDENTITY_PRIVATE_KEY\s*=/.test(wranglerTomlContent)) {
|
|
1872
|
-
wranglerTomlContent = wranglerTomlContent.replace(
|
|
1873
|
-
/MCP_IDENTITY_PRIVATE_KEY\s*=\s*"[^"]*"/,
|
|
1874
|
-
`MCP_IDENTITY_PRIVATE_KEY = ""`
|
|
1875
|
-
);
|
|
1876
|
-
}
|
|
1881
|
+
// Update public key if it exists (safe to keep in [vars])
|
|
1877
1882
|
if (/MCP_IDENTITY_PUBLIC_KEY\s*=/.test(wranglerTomlContent)) {
|
|
1878
1883
|
wranglerTomlContent = wranglerTomlContent.replace(
|
|
1879
1884
|
/MCP_IDENTITY_PUBLIC_KEY\s*=\s*"[^"]*"/,
|
|
1880
|
-
`MCP_IDENTITY_PUBLIC_KEY = ""`
|
|
1881
|
-
);
|
|
1882
|
-
}
|
|
1883
|
-
|
|
1884
|
-
// Ensure API keys are empty strings (not actual values)
|
|
1885
|
-
if (/AGENTSHIELD_API_KEY\s*=/.test(wranglerTomlContent)) {
|
|
1886
|
-
wranglerTomlContent = wranglerTomlContent.replace(
|
|
1887
|
-
/AGENTSHIELD_API_KEY\s*=\s*"[^"]*"/,
|
|
1888
|
-
`AGENTSHIELD_API_KEY = ""`
|
|
1889
|
-
);
|
|
1890
|
-
}
|
|
1891
|
-
if (/ADMIN_API_KEY\s*=/.test(wranglerTomlContent)) {
|
|
1892
|
-
wranglerTomlContent = wranglerTomlContent.replace(
|
|
1893
|
-
/ADMIN_API_KEY\s*=\s*"[^"]*"/,
|
|
1894
|
-
`ADMIN_API_KEY = ""`
|
|
1885
|
+
`MCP_IDENTITY_PUBLIC_KEY = "${identity.publicKey}"`
|
|
1895
1886
|
);
|
|
1896
1887
|
}
|
|
1897
1888
|
|
|
@@ -1907,82 +1898,21 @@ DO_SHARD_COUNT = "10" # Number of shards if using shard strategy
|
|
|
1907
1898
|
);
|
|
1908
1899
|
}
|
|
1909
1900
|
|
|
1910
|
-
// Check if
|
|
1911
|
-
// (They may have been added by the initial template)
|
|
1912
|
-
const hasAgentshieldApiKey = /AGENTSHIELD_API_KEY\s*=/.test(
|
|
1913
|
-
wranglerTomlContent
|
|
1914
|
-
);
|
|
1915
|
-
const hasAgentshieldProjectId = /AGENTSHIELD_PROJECT_ID\s*=/.test(
|
|
1916
|
-
wranglerTomlContent
|
|
1917
|
-
);
|
|
1918
|
-
const hasAdminApiKey = /ADMIN_API_KEY\s*=/.test(wranglerTomlContent);
|
|
1901
|
+
// Check if non-secret variables already exist in wrangler.toml
|
|
1919
1902
|
const hasIdentityDid = /MCP_IDENTITY_AGENT_DID\s*=/.test(
|
|
1920
1903
|
wranglerTomlContent
|
|
1921
1904
|
);
|
|
1922
|
-
const hasIdentityPrivateKey = /MCP_IDENTITY_PRIVATE_KEY\s*=/.test(
|
|
1923
|
-
wranglerTomlContent
|
|
1924
|
-
);
|
|
1925
1905
|
const hasIdentityPublicKey = /MCP_IDENTITY_PUBLIC_KEY\s*=/.test(
|
|
1926
1906
|
wranglerTomlContent
|
|
1927
1907
|
);
|
|
1928
1908
|
|
|
1929
|
-
//
|
|
1930
|
-
|
|
1931
|
-
const apiKeyVarsParts: string[] = [];
|
|
1932
|
-
|
|
1933
|
-
if (
|
|
1934
|
-
!hasAgentshieldApiKey ||
|
|
1935
|
-
!hasAgentshieldProjectId ||
|
|
1936
|
-
!hasAdminApiKey
|
|
1937
|
-
) {
|
|
1938
|
-
apiKeyVarsParts.push(
|
|
1939
|
-
`# API keys - MUST be declared here for .dev.vars to work!`
|
|
1940
|
-
);
|
|
1941
|
-
apiKeyVarsParts.push(
|
|
1942
|
-
`# Development: Values in .dev.vars will override these empty strings`
|
|
1943
|
-
);
|
|
1944
|
-
apiKeyVarsParts.push(
|
|
1945
|
-
`# Production: Use wrangler secret put to set these`
|
|
1946
|
-
);
|
|
1947
|
-
}
|
|
1948
|
-
|
|
1949
|
-
if (!hasAgentshieldApiKey) {
|
|
1950
|
-
apiKeyVarsParts.push(`AGENTSHIELD_API_KEY = ""`);
|
|
1951
|
-
}
|
|
1952
|
-
if (!hasAdminApiKey) {
|
|
1953
|
-
apiKeyVarsParts.push(`ADMIN_API_KEY = ""`);
|
|
1954
|
-
}
|
|
1955
|
-
// Only add AGENTSHIELD_PROJECT_ID if it doesn't exist
|
|
1956
|
-
// If projectId is provided, it will be set above (lines 1897-1907)
|
|
1957
|
-
// If not provided, we still need to declare it for .dev.vars to work
|
|
1958
|
-
if (!hasAgentshieldProjectId) {
|
|
1959
|
-
apiKeyVarsParts.push(
|
|
1960
|
-
`AGENTSHIELD_PROJECT_ID = "${projectId || ""}"`
|
|
1961
|
-
);
|
|
1962
|
-
}
|
|
1963
|
-
|
|
1964
|
-
const apiKeyVars =
|
|
1965
|
-
apiKeyVarsParts.length > 0
|
|
1966
|
-
? `\n${apiKeyVarsParts.join("\n")}\n`
|
|
1967
|
-
: "";
|
|
1968
|
-
|
|
1969
|
-
// Only insert identity vars and API key vars if they don't already exist in [vars]
|
|
1970
|
-
// If they already exist, we've already updated them above to ensure they're empty strings
|
|
1971
|
-
// Note: API keys are already in initial template, so we mainly check for identity vars
|
|
1972
|
-
// But we also check for API keys in case they were removed from template
|
|
1973
|
-
const needsInsertion =
|
|
1974
|
-
!hasIdentityDid ||
|
|
1975
|
-
!hasIdentityPrivateKey ||
|
|
1976
|
-
!hasIdentityPublicKey ||
|
|
1977
|
-
(!hasAgentshieldApiKey && apiKeyVarsParts.length > 0) ||
|
|
1978
|
-
(!hasAdminApiKey && apiKeyVarsParts.length > 0) ||
|
|
1979
|
-
(!hasAgentshieldProjectId && apiKeyVarsParts.length > 0);
|
|
1909
|
+
// Only insert identity vars if they don't already exist
|
|
1910
|
+
const needsInsertion = !hasIdentityDid || !hasIdentityPublicKey;
|
|
1980
1911
|
|
|
1981
1912
|
if (needsInsertion) {
|
|
1982
1913
|
wranglerTomlContent =
|
|
1983
1914
|
wranglerTomlContent.slice(0, insertPosition) +
|
|
1984
1915
|
identityVars +
|
|
1985
|
-
apiKeyVars +
|
|
1986
1916
|
wranglerTomlContent.slice(insertPosition);
|
|
1987
1917
|
}
|
|
1988
1918
|
|
|
@@ -1990,25 +1920,24 @@ DO_SHARD_COUNT = "10" # Number of shards if using shard strategy
|
|
|
1990
1920
|
fs.writeFileSync(wranglerPath, wranglerTomlContent);
|
|
1991
1921
|
|
|
1992
1922
|
// Create .dev.vars file for local development (git-ignored)
|
|
1923
|
+
// Only contains SECRETS (not public keys or project IDs)
|
|
1993
1924
|
const devVarsPath = path.join(projectPath, ".dev.vars");
|
|
1994
1925
|
const devVarsContent = `# Local development secrets (DO NOT COMMIT)
|
|
1995
1926
|
# This file is git-ignored and contains sensitive data
|
|
1996
1927
|
#
|
|
1997
1928
|
# HOW IT WORKS:
|
|
1998
|
-
# 1.
|
|
1999
|
-
# 2. This file (.dev.vars)
|
|
1929
|
+
# 1. Secrets are NOT declared in wrangler.toml [vars] (avoids conflicts)
|
|
1930
|
+
# 2. This file (.dev.vars) provides secrets for local development
|
|
2000
1931
|
# 3. Production uses: wrangler secret put VARIABLE_NAME
|
|
1932
|
+
#
|
|
1933
|
+
# Non-secrets (MCP_IDENTITY_PUBLIC_KEY, AGENTSHIELD_PROJECT_ID) are in wrangler.toml
|
|
2001
1934
|
|
|
2002
|
-
#
|
|
1935
|
+
# Private identity key (generated by create-mcpi-app)
|
|
2003
1936
|
MCP_IDENTITY_PRIVATE_KEY="${identity.privateKey}"
|
|
2004
|
-
MCP_IDENTITY_PUBLIC_KEY="${identity.publicKey}"
|
|
2005
1937
|
|
|
2006
1938
|
# AgentShield API key (get from https://kya.vouched.id/dashboard)
|
|
2007
1939
|
AGENTSHIELD_API_KEY="${apikey || ""}"${apikey ? " # Provided via --apikey flag" : ""}
|
|
2008
1940
|
|
|
2009
|
-
# AgentShield Project ID (from dashboard URL: /dashboard/projects/{PROJECT_ID})
|
|
2010
|
-
AGENTSHIELD_PROJECT_ID="${projectId || ""}"${projectId ? " # Provided via --project flag" : ""}
|
|
2011
|
-
|
|
2012
1941
|
# Admin API key for protected endpoints (set to same value as AGENTSHIELD_API_KEY)
|
|
2013
1942
|
ADMIN_API_KEY="${apikey || ""}"${apikey ? " # Set to same value as AGENTSHIELD_API_KEY" : ""}
|
|
2014
1943
|
`;
|
|
@@ -2021,15 +1950,17 @@ ADMIN_API_KEY="${apikey || ""}"${apikey ? " # Set to same value as AGENTSHIELD_
|
|
|
2021
1950
|
);
|
|
2022
1951
|
const devVarsExampleContent = `# Copy this file to .dev.vars and fill in your values
|
|
2023
1952
|
# DO NOT commit .dev.vars to version control
|
|
1953
|
+
#
|
|
1954
|
+
# NOTE: Only secrets go here. Non-secrets (MCP_IDENTITY_PUBLIC_KEY, AGENTSHIELD_PROJECT_ID)
|
|
1955
|
+
# are in wrangler.toml [vars] and can be committed safely.
|
|
2024
1956
|
|
|
2025
|
-
#
|
|
1957
|
+
# Private identity key (generate with: npx @kya-os/create-mcpi-app regenerate-identity)
|
|
2026
1958
|
MCP_IDENTITY_PRIVATE_KEY="your-private-key-here"
|
|
2027
|
-
MCP_IDENTITY_PUBLIC_KEY="your-public-key-here"
|
|
2028
1959
|
|
|
2029
|
-
# AgentShield API key (get from https://
|
|
1960
|
+
# AgentShield API key (get from https://kya.vouched.id/dashboard)
|
|
2030
1961
|
AGENTSHIELD_API_KEY="your-api-key-here"
|
|
2031
1962
|
|
|
2032
|
-
# Admin API key for protected endpoints
|
|
1963
|
+
# Admin API key for protected endpoints (set to same value as AGENTSHIELD_API_KEY)
|
|
2033
1964
|
ADMIN_API_KEY="your-admin-key-here"
|
|
2034
1965
|
`;
|
|
2035
1966
|
fs.writeFileSync(devVarsExamplePath, devVarsExampleContent);
|
|
@@ -2047,18 +1978,22 @@ ADMIN_API_KEY="your-admin-key-here"
|
|
|
2047
1978
|
console.log();
|
|
2048
1979
|
console.log(chalk.yellow("🔒 Production Security:"));
|
|
2049
1980
|
console.log(
|
|
2050
|
-
chalk.dim("
|
|
1981
|
+
chalk.dim(" Secrets are NOT in wrangler.toml (cleaner approach)")
|
|
2051
1982
|
);
|
|
2052
1983
|
console.log(
|
|
2053
|
-
chalk.
|
|
1984
|
+
chalk.dim(" For production, set secrets using wrangler:")
|
|
2054
1985
|
);
|
|
2055
1986
|
console.log(
|
|
2056
|
-
chalk.cyan("
|
|
1987
|
+
chalk.cyan(" $ wrangler secret put MCP_IDENTITY_PRIVATE_KEY")
|
|
2057
1988
|
);
|
|
2058
1989
|
console.log(
|
|
2059
|
-
chalk.cyan("
|
|
1990
|
+
chalk.cyan(" $ wrangler secret put AGENTSHIELD_API_KEY")
|
|
1991
|
+
);
|
|
1992
|
+
console.log(chalk.cyan(" $ wrangler secret put ADMIN_API_KEY"));
|
|
1993
|
+
console.log();
|
|
1994
|
+
console.log(
|
|
1995
|
+
chalk.dim(" Tip: Copy values from .dev.vars when prompted")
|
|
2060
1996
|
);
|
|
2061
|
-
console.log(chalk.cyan(" $ wrangler secret put ADMIN_API_KEY"));
|
|
2062
1997
|
console.log();
|
|
2063
1998
|
}
|
|
2064
1999
|
} catch (error: any) {
|
|
@@ -2182,6 +2117,22 @@ ${packageManager === "npm" ? "npm run" : packageManager} dev
|
|
|
2182
2117
|
|
|
2183
2118
|
### 4. Deploy
|
|
2184
2119
|
|
|
2120
|
+
#### Production Deployment
|
|
2121
|
+
|
|
2122
|
+
Secrets are **not** declared in \`wrangler.toml\` to avoid conflicts. Set them using:
|
|
2123
|
+
|
|
2124
|
+
\`\`\`bash
|
|
2125
|
+
wrangler secret put MCP_IDENTITY_PRIVATE_KEY
|
|
2126
|
+
wrangler secret put AGENTSHIELD_API_KEY
|
|
2127
|
+
wrangler secret put ADMIN_API_KEY
|
|
2128
|
+
\`\`\`
|
|
2129
|
+
|
|
2130
|
+
**Tip:** Copy values from your \`.dev.vars\` file when prompted.
|
|
2131
|
+
|
|
2132
|
+
**Note:** \`MCP_IDENTITY_PUBLIC_KEY\` and \`AGENTSHIELD_PROJECT_ID\` are not secrets and are already in \`wrangler.toml\` with values.
|
|
2133
|
+
|
|
2134
|
+
Now deploy:
|
|
2135
|
+
|
|
2185
2136
|
\`\`\`bash
|
|
2186
2137
|
${packageManager === "npm" ? "npm run" : packageManager} deploy
|
|
2187
2138
|
\`\`\`
|
|
@@ -2439,3 +2390,4 @@ Or simply don't configure the \`AGENTSHIELD_API_KEY\` environment variable.
|
|
|
2439
2390
|
throw error;
|
|
2440
2391
|
}
|
|
2441
2392
|
}
|
|
2393
|
+
|
package/src/index.ts
CHANGED
|
@@ -15,8 +15,10 @@ import {
|
|
|
15
15
|
validateProjectName,
|
|
16
16
|
validateDirectoryAvailability,
|
|
17
17
|
} from "./utils/validate-project-name.js";
|
|
18
|
-
import {
|
|
19
|
-
|
|
18
|
+
import {
|
|
19
|
+
resetIdentity,
|
|
20
|
+
regenerateIdentity,
|
|
21
|
+
} from "./helpers/identity-manager.js";
|
|
20
22
|
|
|
21
23
|
checkNodeVersion();
|
|
22
24
|
|
|
@@ -44,10 +46,7 @@ const program = new Command()
|
|
|
44
46
|
.option("--use-pnpm", "Use pnpm as package manager")
|
|
45
47
|
.option("--skip-install", "Skip installing dependencies", false)
|
|
46
48
|
.option("--skip-identity", "Skip identity generation", false)
|
|
47
|
-
.option(
|
|
48
|
-
"--no-identity",
|
|
49
|
-
"Create plain MCP project without identity features"
|
|
50
|
-
)
|
|
49
|
+
.option("--no-identity", "Create plain MCP project without identity features")
|
|
51
50
|
.option("--vercel", "Add Vercel support for deployment", false)
|
|
52
51
|
.option("--http", "Enable HTTP transport", false)
|
|
53
52
|
.option("--stdio", "Enable STDIO transport", false)
|
|
@@ -55,11 +54,18 @@ const program = new Command()
|
|
|
55
54
|
.option("--mcpi-version <version>", "Specify MCP-I version (e.g., ^1.2.7)")
|
|
56
55
|
.option("--no-animation", "Skip the black hole animation", false)
|
|
57
56
|
.option("--fast", "Use shorter animation duration", false)
|
|
58
|
-
.option(
|
|
57
|
+
.option(
|
|
58
|
+
"--platform <name>",
|
|
59
|
+
"Deployment platform: node (default), cloudflare",
|
|
60
|
+
"node"
|
|
61
|
+
)
|
|
59
62
|
.option("--mode <name>", "Server mode: mcp-i (default), verifier", "mcp-i")
|
|
60
63
|
.option("--template <name>", "[DEPRECATED] Use --platform and --mode instead")
|
|
61
64
|
.option("--apikey <key>", "AgentShield API key for Cloudflare deployment")
|
|
62
|
-
.option(
|
|
65
|
+
.option(
|
|
66
|
+
"--project <id>",
|
|
67
|
+
"AgentShield Project ID for Cloudflare deployment (enables project-scoped tool protection)"
|
|
68
|
+
)
|
|
63
69
|
.action(async (projectDir, options) => {
|
|
64
70
|
console.log(chalk.bold(`\ncreate-mcpi-app@${packageJson.version}`));
|
|
65
71
|
|
|
@@ -122,7 +128,11 @@ const program = new Command()
|
|
|
122
128
|
|
|
123
129
|
// Backward compatibility: map --template to --platform/--mode
|
|
124
130
|
if (options.template) {
|
|
125
|
-
console.log(
|
|
131
|
+
console.log(
|
|
132
|
+
chalk.yellow(
|
|
133
|
+
"⚠️ --template is deprecated. Use --platform and --mode instead."
|
|
134
|
+
)
|
|
135
|
+
);
|
|
126
136
|
if (options.template === "cloudflare") {
|
|
127
137
|
platform = "cloudflare";
|
|
128
138
|
mode = "verifier";
|
|
@@ -144,7 +154,9 @@ const program = new Command()
|
|
|
144
154
|
);
|
|
145
155
|
|
|
146
156
|
if (!isValid) {
|
|
147
|
-
console.error(
|
|
157
|
+
console.error(
|
|
158
|
+
chalk.red(`\n❌ Invalid platform/mode combination: ${platform}/${mode}`)
|
|
159
|
+
);
|
|
148
160
|
console.log(chalk.yellow("\nSupported combinations:"));
|
|
149
161
|
console.log(chalk.cyan(" - node + mcp-i (default)"));
|
|
150
162
|
console.log(chalk.cyan(" - cloudflare + mcp-i"));
|
|
@@ -212,7 +224,11 @@ const program = new Command()
|
|
|
212
224
|
}
|
|
213
225
|
|
|
214
226
|
// Vercel deployment option (only for Node.js platform)
|
|
215
|
-
if (
|
|
227
|
+
if (
|
|
228
|
+
!options.vercel &&
|
|
229
|
+
transports.includes("http") &&
|
|
230
|
+
platform === "node"
|
|
231
|
+
) {
|
|
216
232
|
const vercelAnswers = await inquirer.prompt([
|
|
217
233
|
{
|
|
218
234
|
type: "confirm",
|
|
@@ -349,15 +365,27 @@ const program = new Command()
|
|
|
349
365
|
}
|
|
350
366
|
console.log();
|
|
351
367
|
console.log("2. Create KV namespaces (creates both NONCE and PROOF):");
|
|
352
|
-
console.log(
|
|
353
|
-
|
|
368
|
+
console.log(
|
|
369
|
+
` ${chalk.cyan(`${packageManager === "npm" ? "npm run" : packageManager} kv:create`)}`
|
|
370
|
+
);
|
|
371
|
+
console.log(
|
|
372
|
+
chalk.gray(
|
|
373
|
+
" Copy both namespace IDs from output and update wrangler.toml"
|
|
374
|
+
)
|
|
375
|
+
);
|
|
354
376
|
console.log();
|
|
355
377
|
console.log("3. Test locally:");
|
|
356
|
-
console.log(
|
|
378
|
+
console.log(
|
|
379
|
+
` ${chalk.cyan(`${packageManager === "npm" ? "npm run" : packageManager} dev`)}`
|
|
380
|
+
);
|
|
357
381
|
console.log();
|
|
358
382
|
console.log("4. Deploy to Cloudflare:");
|
|
359
|
-
console.log(
|
|
360
|
-
|
|
383
|
+
console.log(
|
|
384
|
+
` ${chalk.cyan("npx wrangler login")} ${chalk.gray("(first time only)")}`
|
|
385
|
+
);
|
|
386
|
+
console.log(
|
|
387
|
+
` ${chalk.cyan(`${packageManager === "npm" ? "npm run" : packageManager} deploy`)}`
|
|
388
|
+
);
|
|
361
389
|
} else {
|
|
362
390
|
// Default MCP-I server instructions
|
|
363
391
|
// Show agent management with claim URL first
|
|
@@ -449,30 +477,42 @@ const program = new Command()
|
|
|
449
477
|
|
|
450
478
|
// Add subcommand for resetting identity
|
|
451
479
|
program
|
|
452
|
-
.command(
|
|
453
|
-
.description(
|
|
454
|
-
.option(
|
|
480
|
+
.command("reset-identity")
|
|
481
|
+
.description("Reset the current project's identity (removes identity files)")
|
|
482
|
+
.option(
|
|
483
|
+
"-d, --dir <directory>",
|
|
484
|
+
"Project directory (defaults to current directory)"
|
|
485
|
+
)
|
|
455
486
|
.action(async (options) => {
|
|
456
487
|
try {
|
|
457
|
-
const projectPath = options.dir
|
|
488
|
+
const projectPath = options.dir
|
|
489
|
+
? path.resolve(process.cwd(), options.dir)
|
|
490
|
+
: process.cwd();
|
|
458
491
|
await resetIdentity(projectPath);
|
|
459
492
|
} catch (error) {
|
|
460
|
-
console.error(chalk.red(
|
|
493
|
+
console.error(chalk.red("Failed to reset identity:"), error);
|
|
461
494
|
process.exit(1);
|
|
462
495
|
}
|
|
463
496
|
});
|
|
464
497
|
|
|
465
498
|
// Add subcommand for regenerating identity
|
|
466
499
|
program
|
|
467
|
-
.command(
|
|
468
|
-
.description(
|
|
469
|
-
|
|
500
|
+
.command("regenerate-identity")
|
|
501
|
+
.description(
|
|
502
|
+
"Regenerate the current project's identity (creates new DID and keys)"
|
|
503
|
+
)
|
|
504
|
+
.option(
|
|
505
|
+
"-d, --dir <directory>",
|
|
506
|
+
"Project directory (defaults to current directory)"
|
|
507
|
+
)
|
|
470
508
|
.action(async (options) => {
|
|
471
509
|
try {
|
|
472
|
-
const projectPath = options.dir
|
|
510
|
+
const projectPath = options.dir
|
|
511
|
+
? path.resolve(process.cwd(), options.dir)
|
|
512
|
+
: process.cwd();
|
|
473
513
|
await regenerateIdentity(projectPath);
|
|
474
514
|
} catch (error) {
|
|
475
|
-
console.error(chalk.red(
|
|
515
|
+
console.error(chalk.red("Failed to regenerate identity:"), error);
|
|
476
516
|
process.exit(1);
|
|
477
517
|
}
|
|
478
518
|
});
|
|
@@ -2,21 +2,15 @@
|
|
|
2
2
|
"compilerOptions": {
|
|
3
3
|
"target": "ES2022",
|
|
4
4
|
"module": "ES2022",
|
|
5
|
-
"lib": [
|
|
6
|
-
"ES2022"
|
|
7
|
-
],
|
|
8
|
-
"types": [
|
|
9
|
-
"@cloudflare/workers-types"
|
|
10
|
-
],
|
|
5
|
+
"lib": ["ES2022"],
|
|
11
6
|
"moduleResolution": "bundler",
|
|
12
7
|
"resolveJsonModule": true,
|
|
13
8
|
"allowSyntheticDefaultImports": true,
|
|
14
9
|
"esModuleInterop": true,
|
|
15
10
|
"strict": true,
|
|
16
11
|
"skipLibCheck": true,
|
|
17
|
-
"forceConsistentCasingInFileNames": true
|
|
12
|
+
"forceConsistentCasingInFileNames": true,
|
|
13
|
+
"noEmit": true
|
|
18
14
|
},
|
|
19
|
-
"include": [
|
|
20
|
-
"src/**/*"
|
|
21
|
-
]
|
|
15
|
+
"include": ["src/**/*", "tests/**/*"]
|
|
22
16
|
}
|