@sentientui/mcp 0.8.1 → 0.8.2
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/dist/{chunk-TLBLOBSB.js → chunk-GLL5CMBY.js} +41 -59
- package/dist/index.cjs +41 -62
- package/dist/index.js +1 -1
- package/dist/lib.cjs +44 -63
- package/dist/lib.js +1 -1
- package/package.json +1 -1
|
@@ -47,7 +47,6 @@ var ApiClient = class {
|
|
|
47
47
|
};
|
|
48
48
|
|
|
49
49
|
// src/server.ts
|
|
50
|
-
import { createRequire } from "module";
|
|
51
50
|
import { McpServer } from "@modelcontextprotocol/sdk/server/mcp.js";
|
|
52
51
|
|
|
53
52
|
// src/tools/projects.ts
|
|
@@ -56,7 +55,10 @@ import { z as z2 } from "zod";
|
|
|
56
55
|
// src/tools/common.ts
|
|
57
56
|
import { z } from "zod";
|
|
58
57
|
var projectIdSchema = z.string().uuid().describe("The project UUID");
|
|
59
|
-
function apiErrorGuidance(err) {
|
|
58
|
+
function apiErrorGuidance(err, extra) {
|
|
59
|
+
if (extra && Object.prototype.hasOwnProperty.call(extra, err.message)) {
|
|
60
|
+
return extra[err.message];
|
|
61
|
+
}
|
|
60
62
|
switch (err.message) {
|
|
61
63
|
case "insufficient_scope":
|
|
62
64
|
return "This action needs an account login. Connect via the hosted MCP URL (https://api.sentient-ui.com/mcp) and sign in \u2014 a project-scoped server key (sk_\u2026) or anonymous demo token cannot do this.";
|
|
@@ -75,13 +77,13 @@ function apiErrorGuidance(err) {
|
|
|
75
77
|
}
|
|
76
78
|
return null;
|
|
77
79
|
}
|
|
78
|
-
function withApiErrorGuidance(fn) {
|
|
80
|
+
function withApiErrorGuidance(fn, extra) {
|
|
79
81
|
return async (args) => {
|
|
80
82
|
try {
|
|
81
83
|
return await fn(args);
|
|
82
84
|
} catch (err) {
|
|
83
85
|
if (err instanceof ApiError) {
|
|
84
|
-
const guidance = apiErrorGuidance(err);
|
|
86
|
+
const guidance = apiErrorGuidance(err, extra);
|
|
85
87
|
if (guidance) {
|
|
86
88
|
return { content: [{ type: "text", text: guidance }], isError: true };
|
|
87
89
|
}
|
|
@@ -92,22 +94,10 @@ function withApiErrorGuidance(fn) {
|
|
|
92
94
|
}
|
|
93
95
|
|
|
94
96
|
// src/tools/projects.ts
|
|
95
|
-
|
|
96
|
-
|
|
97
|
-
|
|
98
|
-
|
|
99
|
-
case "demo_read_only":
|
|
100
|
-
return "Demo mode is read-only. Create a SentientUI account and sign in to make projects.";
|
|
101
|
-
case "insufficient_role":
|
|
102
|
-
return "Your account role cannot create projects \u2014 this needs the account owner or an admin.";
|
|
103
|
-
case "project_limit_reached":
|
|
104
|
-
return "You've reached your plan's project limit. Upgrade your plan or remove an existing project, then try again.";
|
|
105
|
-
case "name_required":
|
|
106
|
-
return "A project name is required to create a project.";
|
|
107
|
-
default:
|
|
108
|
-
return null;
|
|
109
|
-
}
|
|
110
|
-
}
|
|
97
|
+
var CREATE_PROJECT_GUIDANCE = {
|
|
98
|
+
project_limit_reached: "You've reached your plan's project limit. Upgrade your plan or remove an existing project, then try again.",
|
|
99
|
+
name_required: "A project name is required to create a project."
|
|
100
|
+
};
|
|
111
101
|
function registerProjectTools(server, client) {
|
|
112
102
|
server.registerTool(
|
|
113
103
|
"create_project",
|
|
@@ -133,41 +123,31 @@ function registerProjectTools(server, client) {
|
|
|
133
123
|
openWorldHint: false
|
|
134
124
|
}
|
|
135
125
|
},
|
|
136
|
-
async ({ name, contextType, framework, websiteUrl }) => {
|
|
137
|
-
|
|
138
|
-
|
|
126
|
+
withApiErrorGuidance(async ({ name, contextType, framework, websiteUrl }) => {
|
|
127
|
+
const created = await client.post("/projects", {
|
|
128
|
+
name,
|
|
129
|
+
contextType,
|
|
130
|
+
framework,
|
|
131
|
+
origin: websiteUrl
|
|
132
|
+
});
|
|
133
|
+
const resolvedContextType = contextType != null ? contextType : "saas";
|
|
134
|
+
return {
|
|
135
|
+
content: [{
|
|
136
|
+
type: "text",
|
|
137
|
+
text: [
|
|
138
|
+
`Created project "${name}" (id: ${created.id}, type: ${resolvedContextType}).`,
|
|
139
|
+
`Public key: ${created.apiKey}`,
|
|
140
|
+
`Next: install @sentientui/react with this key. Ask me to pull the setup guide (get_integration_guide) and I'll wrap your first component.`
|
|
141
|
+
].join("\n")
|
|
142
|
+
}],
|
|
143
|
+
structuredContent: {
|
|
144
|
+
projectId: created.id,
|
|
145
|
+
publicKey: created.apiKey,
|
|
139
146
|
name,
|
|
140
|
-
contextType
|
|
141
|
-
framework,
|
|
142
|
-
origin: websiteUrl
|
|
143
|
-
});
|
|
144
|
-
const resolvedContextType = contextType != null ? contextType : "saas";
|
|
145
|
-
return {
|
|
146
|
-
content: [{
|
|
147
|
-
type: "text",
|
|
148
|
-
text: [
|
|
149
|
-
`Created project "${name}" (id: ${created.id}, type: ${resolvedContextType}).`,
|
|
150
|
-
`Public key: ${created.apiKey}`,
|
|
151
|
-
`Next: install @sentientui/react with this key. Ask me to pull the setup guide (get_integration_guide) and I'll wrap your first component.`
|
|
152
|
-
].join("\n")
|
|
153
|
-
}],
|
|
154
|
-
structuredContent: {
|
|
155
|
-
projectId: created.id,
|
|
156
|
-
publicKey: created.apiKey,
|
|
157
|
-
name,
|
|
158
|
-
contextType: resolvedContextType
|
|
159
|
-
}
|
|
160
|
-
};
|
|
161
|
-
} catch (err) {
|
|
162
|
-
if (err instanceof ApiError) {
|
|
163
|
-
const guidance = createProjectGuidance(err);
|
|
164
|
-
if (guidance) {
|
|
165
|
-
return { content: [{ type: "text", text: guidance }], isError: true };
|
|
166
|
-
}
|
|
147
|
+
contextType: resolvedContextType
|
|
167
148
|
}
|
|
168
|
-
|
|
169
|
-
|
|
170
|
-
}
|
|
149
|
+
};
|
|
150
|
+
}, CREATE_PROJECT_GUIDANCE)
|
|
171
151
|
);
|
|
172
152
|
server.registerTool(
|
|
173
153
|
"list_projects",
|
|
@@ -919,13 +899,16 @@ function registerVariantWriteTools(server, client) {
|
|
|
919
899
|
description: "Create a NO-CODE managed text variant for a component (content stored in SentientUI, rendered by <AdaptiveText>). Use this ONLY for text-only variants the user wants without a code change. For variants that will live in the codebase (full components \u2014 copy, markup, styling), use get_variant_brief and write the variant in code instead; those auto-register on deploy and do not need create_variant. Requires a paid plan (server keys are Starter+; anonymous demo tokens are read-only).",
|
|
920
900
|
inputSchema: {
|
|
921
901
|
projectId: projectIdSchema,
|
|
922
|
-
componentId: z9.string().describe("The component ID to add a variant to"),
|
|
923
|
-
displayName: z9.string().describe("Human-readable name for the new variant"),
|
|
924
|
-
content: z9.string().optional().describe("The text content for this managed variant (rendered by <AdaptiveText>). Generate it from get_variant_brief context; omit only to create an empty placeholder to fill in from the dashboard.")
|
|
902
|
+
componentId: z9.string().min(1).max(200).describe("The component ID to add a variant to"),
|
|
903
|
+
displayName: z9.string().min(1).max(200).describe("Human-readable name for the new variant"),
|
|
904
|
+
content: z9.string().max(1e4).optional().describe("The text content for this managed variant (rendered by <AdaptiveText>). Generate it from get_variant_brief context; omit only to create an empty placeholder to fill in from the dashboard.")
|
|
925
905
|
},
|
|
926
906
|
outputSchema: {
|
|
927
907
|
variantId: z9.string().describe("The new variant ID"),
|
|
928
|
-
displayName
|
|
908
|
+
// API returns `body.displayName ?? null`, so a successful create can
|
|
909
|
+
// carry a null name — match that contract or outputSchema validation
|
|
910
|
+
// would reject an otherwise-successful response.
|
|
911
|
+
displayName: z9.string().nullable(),
|
|
929
912
|
componentId: z9.string(),
|
|
930
913
|
state: z9.literal("draft").describe("New managed variants start in draft state"),
|
|
931
914
|
hasContent: z9.boolean().describe("Whether text content was provided at creation")
|
|
@@ -1419,8 +1402,7 @@ function registerIntegrationGuideTools(server) {
|
|
|
1419
1402
|
}
|
|
1420
1403
|
|
|
1421
1404
|
// src/server.ts
|
|
1422
|
-
var
|
|
1423
|
-
var { version: PKG_VERSION } = createRequire(import_meta.url)("../package.json");
|
|
1405
|
+
var PKG_VERSION = true ? "0.8.2" : "0.0.0-dev";
|
|
1424
1406
|
function createMcpServer(client) {
|
|
1425
1407
|
const server = new McpServer(
|
|
1426
1408
|
{
|
package/dist/index.cjs
CHANGED
|
@@ -1,10 +1,6 @@
|
|
|
1
1
|
#!/usr/bin/env node
|
|
2
2
|
"use strict";
|
|
3
3
|
|
|
4
|
-
// ../../node_modules/.pnpm/tsup@8.5.1_jiti@1.21.7_postcss@8.5.14_tsx@4.22.1_typescript@5.9.3_yaml@2.9.0/node_modules/tsup/assets/cjs_shims.js
|
|
5
|
-
var getImportMetaUrl = () => typeof document === "undefined" ? new URL(`file:${__filename}`).href : document.currentScript && document.currentScript.tagName.toUpperCase() === "SCRIPT" ? document.currentScript.src : new URL("main.js", document.baseURI).href;
|
|
6
|
-
var importMetaUrl = /* @__PURE__ */ getImportMetaUrl();
|
|
7
|
-
|
|
8
4
|
// src/index.ts
|
|
9
5
|
var import_stdio = require("@modelcontextprotocol/sdk/server/stdio.js");
|
|
10
6
|
|
|
@@ -55,7 +51,6 @@ var ApiClient = class {
|
|
|
55
51
|
};
|
|
56
52
|
|
|
57
53
|
// src/server.ts
|
|
58
|
-
var import_node_module = require("module");
|
|
59
54
|
var import_mcp = require("@modelcontextprotocol/sdk/server/mcp.js");
|
|
60
55
|
|
|
61
56
|
// src/tools/projects.ts
|
|
@@ -64,7 +59,10 @@ var import_zod2 = require("zod");
|
|
|
64
59
|
// src/tools/common.ts
|
|
65
60
|
var import_zod = require("zod");
|
|
66
61
|
var projectIdSchema = import_zod.z.string().uuid().describe("The project UUID");
|
|
67
|
-
function apiErrorGuidance(err) {
|
|
62
|
+
function apiErrorGuidance(err, extra) {
|
|
63
|
+
if (extra && Object.prototype.hasOwnProperty.call(extra, err.message)) {
|
|
64
|
+
return extra[err.message];
|
|
65
|
+
}
|
|
68
66
|
switch (err.message) {
|
|
69
67
|
case "insufficient_scope":
|
|
70
68
|
return "This action needs an account login. Connect via the hosted MCP URL (https://api.sentient-ui.com/mcp) and sign in \u2014 a project-scoped server key (sk_\u2026) or anonymous demo token cannot do this.";
|
|
@@ -83,13 +81,13 @@ function apiErrorGuidance(err) {
|
|
|
83
81
|
}
|
|
84
82
|
return null;
|
|
85
83
|
}
|
|
86
|
-
function withApiErrorGuidance(fn) {
|
|
84
|
+
function withApiErrorGuidance(fn, extra) {
|
|
87
85
|
return async (args) => {
|
|
88
86
|
try {
|
|
89
87
|
return await fn(args);
|
|
90
88
|
} catch (err) {
|
|
91
89
|
if (err instanceof ApiError) {
|
|
92
|
-
const guidance = apiErrorGuidance(err);
|
|
90
|
+
const guidance = apiErrorGuidance(err, extra);
|
|
93
91
|
if (guidance) {
|
|
94
92
|
return { content: [{ type: "text", text: guidance }], isError: true };
|
|
95
93
|
}
|
|
@@ -100,22 +98,10 @@ function withApiErrorGuidance(fn) {
|
|
|
100
98
|
}
|
|
101
99
|
|
|
102
100
|
// src/tools/projects.ts
|
|
103
|
-
|
|
104
|
-
|
|
105
|
-
|
|
106
|
-
|
|
107
|
-
case "demo_read_only":
|
|
108
|
-
return "Demo mode is read-only. Create a SentientUI account and sign in to make projects.";
|
|
109
|
-
case "insufficient_role":
|
|
110
|
-
return "Your account role cannot create projects \u2014 this needs the account owner or an admin.";
|
|
111
|
-
case "project_limit_reached":
|
|
112
|
-
return "You've reached your plan's project limit. Upgrade your plan or remove an existing project, then try again.";
|
|
113
|
-
case "name_required":
|
|
114
|
-
return "A project name is required to create a project.";
|
|
115
|
-
default:
|
|
116
|
-
return null;
|
|
117
|
-
}
|
|
118
|
-
}
|
|
101
|
+
var CREATE_PROJECT_GUIDANCE = {
|
|
102
|
+
project_limit_reached: "You've reached your plan's project limit. Upgrade your plan or remove an existing project, then try again.",
|
|
103
|
+
name_required: "A project name is required to create a project."
|
|
104
|
+
};
|
|
119
105
|
function registerProjectTools(server, client) {
|
|
120
106
|
server.registerTool(
|
|
121
107
|
"create_project",
|
|
@@ -141,41 +127,31 @@ function registerProjectTools(server, client) {
|
|
|
141
127
|
openWorldHint: false
|
|
142
128
|
}
|
|
143
129
|
},
|
|
144
|
-
async ({ name, contextType, framework, websiteUrl }) => {
|
|
145
|
-
|
|
146
|
-
|
|
130
|
+
withApiErrorGuidance(async ({ name, contextType, framework, websiteUrl }) => {
|
|
131
|
+
const created = await client.post("/projects", {
|
|
132
|
+
name,
|
|
133
|
+
contextType,
|
|
134
|
+
framework,
|
|
135
|
+
origin: websiteUrl
|
|
136
|
+
});
|
|
137
|
+
const resolvedContextType = contextType != null ? contextType : "saas";
|
|
138
|
+
return {
|
|
139
|
+
content: [{
|
|
140
|
+
type: "text",
|
|
141
|
+
text: [
|
|
142
|
+
`Created project "${name}" (id: ${created.id}, type: ${resolvedContextType}).`,
|
|
143
|
+
`Public key: ${created.apiKey}`,
|
|
144
|
+
`Next: install @sentientui/react with this key. Ask me to pull the setup guide (get_integration_guide) and I'll wrap your first component.`
|
|
145
|
+
].join("\n")
|
|
146
|
+
}],
|
|
147
|
+
structuredContent: {
|
|
148
|
+
projectId: created.id,
|
|
149
|
+
publicKey: created.apiKey,
|
|
147
150
|
name,
|
|
148
|
-
contextType
|
|
149
|
-
framework,
|
|
150
|
-
origin: websiteUrl
|
|
151
|
-
});
|
|
152
|
-
const resolvedContextType = contextType != null ? contextType : "saas";
|
|
153
|
-
return {
|
|
154
|
-
content: [{
|
|
155
|
-
type: "text",
|
|
156
|
-
text: [
|
|
157
|
-
`Created project "${name}" (id: ${created.id}, type: ${resolvedContextType}).`,
|
|
158
|
-
`Public key: ${created.apiKey}`,
|
|
159
|
-
`Next: install @sentientui/react with this key. Ask me to pull the setup guide (get_integration_guide) and I'll wrap your first component.`
|
|
160
|
-
].join("\n")
|
|
161
|
-
}],
|
|
162
|
-
structuredContent: {
|
|
163
|
-
projectId: created.id,
|
|
164
|
-
publicKey: created.apiKey,
|
|
165
|
-
name,
|
|
166
|
-
contextType: resolvedContextType
|
|
167
|
-
}
|
|
168
|
-
};
|
|
169
|
-
} catch (err) {
|
|
170
|
-
if (err instanceof ApiError) {
|
|
171
|
-
const guidance = createProjectGuidance(err);
|
|
172
|
-
if (guidance) {
|
|
173
|
-
return { content: [{ type: "text", text: guidance }], isError: true };
|
|
174
|
-
}
|
|
151
|
+
contextType: resolvedContextType
|
|
175
152
|
}
|
|
176
|
-
|
|
177
|
-
|
|
178
|
-
}
|
|
153
|
+
};
|
|
154
|
+
}, CREATE_PROJECT_GUIDANCE)
|
|
179
155
|
);
|
|
180
156
|
server.registerTool(
|
|
181
157
|
"list_projects",
|
|
@@ -927,13 +903,16 @@ function registerVariantWriteTools(server, client) {
|
|
|
927
903
|
description: "Create a NO-CODE managed text variant for a component (content stored in SentientUI, rendered by <AdaptiveText>). Use this ONLY for text-only variants the user wants without a code change. For variants that will live in the codebase (full components \u2014 copy, markup, styling), use get_variant_brief and write the variant in code instead; those auto-register on deploy and do not need create_variant. Requires a paid plan (server keys are Starter+; anonymous demo tokens are read-only).",
|
|
928
904
|
inputSchema: {
|
|
929
905
|
projectId: projectIdSchema,
|
|
930
|
-
componentId: import_zod9.z.string().describe("The component ID to add a variant to"),
|
|
931
|
-
displayName: import_zod9.z.string().describe("Human-readable name for the new variant"),
|
|
932
|
-
content: import_zod9.z.string().optional().describe("The text content for this managed variant (rendered by <AdaptiveText>). Generate it from get_variant_brief context; omit only to create an empty placeholder to fill in from the dashboard.")
|
|
906
|
+
componentId: import_zod9.z.string().min(1).max(200).describe("The component ID to add a variant to"),
|
|
907
|
+
displayName: import_zod9.z.string().min(1).max(200).describe("Human-readable name for the new variant"),
|
|
908
|
+
content: import_zod9.z.string().max(1e4).optional().describe("The text content for this managed variant (rendered by <AdaptiveText>). Generate it from get_variant_brief context; omit only to create an empty placeholder to fill in from the dashboard.")
|
|
933
909
|
},
|
|
934
910
|
outputSchema: {
|
|
935
911
|
variantId: import_zod9.z.string().describe("The new variant ID"),
|
|
936
|
-
displayName
|
|
912
|
+
// API returns `body.displayName ?? null`, so a successful create can
|
|
913
|
+
// carry a null name — match that contract or outputSchema validation
|
|
914
|
+
// would reject an otherwise-successful response.
|
|
915
|
+
displayName: import_zod9.z.string().nullable(),
|
|
937
916
|
componentId: import_zod9.z.string(),
|
|
938
917
|
state: import_zod9.z.literal("draft").describe("New managed variants start in draft state"),
|
|
939
918
|
hasContent: import_zod9.z.boolean().describe("Whether text content was provided at creation")
|
|
@@ -1427,7 +1406,7 @@ function registerIntegrationGuideTools(server) {
|
|
|
1427
1406
|
}
|
|
1428
1407
|
|
|
1429
1408
|
// src/server.ts
|
|
1430
|
-
var
|
|
1409
|
+
var PKG_VERSION = true ? "0.8.2" : "0.0.0-dev";
|
|
1431
1410
|
function createMcpServer(client) {
|
|
1432
1411
|
const server = new import_mcp.McpServer(
|
|
1433
1412
|
{
|
package/dist/index.js
CHANGED
package/dist/lib.cjs
CHANGED
|
@@ -27,17 +27,15 @@ __export(lib_exports, {
|
|
|
27
27
|
});
|
|
28
28
|
module.exports = __toCommonJS(lib_exports);
|
|
29
29
|
|
|
30
|
-
// ../../node_modules/.pnpm/tsup@8.5.1_jiti@1.21.7_postcss@8.5.14_tsx@4.22.1_typescript@5.9.3_yaml@2.9.0/node_modules/tsup/assets/cjs_shims.js
|
|
31
|
-
var getImportMetaUrl = () => typeof document === "undefined" ? new URL(`file:${__filename}`).href : document.currentScript && document.currentScript.tagName.toUpperCase() === "SCRIPT" ? document.currentScript.src : new URL("main.js", document.baseURI).href;
|
|
32
|
-
var importMetaUrl = /* @__PURE__ */ getImportMetaUrl();
|
|
33
|
-
|
|
34
30
|
// src/server.ts
|
|
35
|
-
var import_node_module = require("module");
|
|
36
31
|
var import_mcp = require("@modelcontextprotocol/sdk/server/mcp.js");
|
|
37
32
|
|
|
38
33
|
// src/tools/projects.ts
|
|
39
34
|
var import_zod2 = require("zod");
|
|
40
35
|
|
|
36
|
+
// src/tools/common.ts
|
|
37
|
+
var import_zod = require("zod");
|
|
38
|
+
|
|
41
39
|
// src/api-client.ts
|
|
42
40
|
var ApiError = class extends Error {
|
|
43
41
|
constructor(status, message) {
|
|
@@ -85,9 +83,11 @@ var ApiClient = class {
|
|
|
85
83
|
};
|
|
86
84
|
|
|
87
85
|
// src/tools/common.ts
|
|
88
|
-
var import_zod = require("zod");
|
|
89
86
|
var projectIdSchema = import_zod.z.string().uuid().describe("The project UUID");
|
|
90
|
-
function apiErrorGuidance(err) {
|
|
87
|
+
function apiErrorGuidance(err, extra) {
|
|
88
|
+
if (extra && Object.prototype.hasOwnProperty.call(extra, err.message)) {
|
|
89
|
+
return extra[err.message];
|
|
90
|
+
}
|
|
91
91
|
switch (err.message) {
|
|
92
92
|
case "insufficient_scope":
|
|
93
93
|
return "This action needs an account login. Connect via the hosted MCP URL (https://api.sentient-ui.com/mcp) and sign in \u2014 a project-scoped server key (sk_\u2026) or anonymous demo token cannot do this.";
|
|
@@ -106,13 +106,13 @@ function apiErrorGuidance(err) {
|
|
|
106
106
|
}
|
|
107
107
|
return null;
|
|
108
108
|
}
|
|
109
|
-
function withApiErrorGuidance(fn) {
|
|
109
|
+
function withApiErrorGuidance(fn, extra) {
|
|
110
110
|
return async (args) => {
|
|
111
111
|
try {
|
|
112
112
|
return await fn(args);
|
|
113
113
|
} catch (err) {
|
|
114
114
|
if (err instanceof ApiError) {
|
|
115
|
-
const guidance = apiErrorGuidance(err);
|
|
115
|
+
const guidance = apiErrorGuidance(err, extra);
|
|
116
116
|
if (guidance) {
|
|
117
117
|
return { content: [{ type: "text", text: guidance }], isError: true };
|
|
118
118
|
}
|
|
@@ -123,22 +123,10 @@ function withApiErrorGuidance(fn) {
|
|
|
123
123
|
}
|
|
124
124
|
|
|
125
125
|
// src/tools/projects.ts
|
|
126
|
-
|
|
127
|
-
|
|
128
|
-
|
|
129
|
-
|
|
130
|
-
case "demo_read_only":
|
|
131
|
-
return "Demo mode is read-only. Create a SentientUI account and sign in to make projects.";
|
|
132
|
-
case "insufficient_role":
|
|
133
|
-
return "Your account role cannot create projects \u2014 this needs the account owner or an admin.";
|
|
134
|
-
case "project_limit_reached":
|
|
135
|
-
return "You've reached your plan's project limit. Upgrade your plan or remove an existing project, then try again.";
|
|
136
|
-
case "name_required":
|
|
137
|
-
return "A project name is required to create a project.";
|
|
138
|
-
default:
|
|
139
|
-
return null;
|
|
140
|
-
}
|
|
141
|
-
}
|
|
126
|
+
var CREATE_PROJECT_GUIDANCE = {
|
|
127
|
+
project_limit_reached: "You've reached your plan's project limit. Upgrade your plan or remove an existing project, then try again.",
|
|
128
|
+
name_required: "A project name is required to create a project."
|
|
129
|
+
};
|
|
142
130
|
function registerProjectTools(server, client) {
|
|
143
131
|
server.registerTool(
|
|
144
132
|
"create_project",
|
|
@@ -164,41 +152,31 @@ function registerProjectTools(server, client) {
|
|
|
164
152
|
openWorldHint: false
|
|
165
153
|
}
|
|
166
154
|
},
|
|
167
|
-
async ({ name, contextType, framework, websiteUrl }) => {
|
|
168
|
-
|
|
169
|
-
|
|
155
|
+
withApiErrorGuidance(async ({ name, contextType, framework, websiteUrl }) => {
|
|
156
|
+
const created = await client.post("/projects", {
|
|
157
|
+
name,
|
|
158
|
+
contextType,
|
|
159
|
+
framework,
|
|
160
|
+
origin: websiteUrl
|
|
161
|
+
});
|
|
162
|
+
const resolvedContextType = contextType != null ? contextType : "saas";
|
|
163
|
+
return {
|
|
164
|
+
content: [{
|
|
165
|
+
type: "text",
|
|
166
|
+
text: [
|
|
167
|
+
`Created project "${name}" (id: ${created.id}, type: ${resolvedContextType}).`,
|
|
168
|
+
`Public key: ${created.apiKey}`,
|
|
169
|
+
`Next: install @sentientui/react with this key. Ask me to pull the setup guide (get_integration_guide) and I'll wrap your first component.`
|
|
170
|
+
].join("\n")
|
|
171
|
+
}],
|
|
172
|
+
structuredContent: {
|
|
173
|
+
projectId: created.id,
|
|
174
|
+
publicKey: created.apiKey,
|
|
170
175
|
name,
|
|
171
|
-
contextType
|
|
172
|
-
framework,
|
|
173
|
-
origin: websiteUrl
|
|
174
|
-
});
|
|
175
|
-
const resolvedContextType = contextType != null ? contextType : "saas";
|
|
176
|
-
return {
|
|
177
|
-
content: [{
|
|
178
|
-
type: "text",
|
|
179
|
-
text: [
|
|
180
|
-
`Created project "${name}" (id: ${created.id}, type: ${resolvedContextType}).`,
|
|
181
|
-
`Public key: ${created.apiKey}`,
|
|
182
|
-
`Next: install @sentientui/react with this key. Ask me to pull the setup guide (get_integration_guide) and I'll wrap your first component.`
|
|
183
|
-
].join("\n")
|
|
184
|
-
}],
|
|
185
|
-
structuredContent: {
|
|
186
|
-
projectId: created.id,
|
|
187
|
-
publicKey: created.apiKey,
|
|
188
|
-
name,
|
|
189
|
-
contextType: resolvedContextType
|
|
190
|
-
}
|
|
191
|
-
};
|
|
192
|
-
} catch (err) {
|
|
193
|
-
if (err instanceof ApiError) {
|
|
194
|
-
const guidance = createProjectGuidance(err);
|
|
195
|
-
if (guidance) {
|
|
196
|
-
return { content: [{ type: "text", text: guidance }], isError: true };
|
|
197
|
-
}
|
|
176
|
+
contextType: resolvedContextType
|
|
198
177
|
}
|
|
199
|
-
|
|
200
|
-
|
|
201
|
-
}
|
|
178
|
+
};
|
|
179
|
+
}, CREATE_PROJECT_GUIDANCE)
|
|
202
180
|
);
|
|
203
181
|
server.registerTool(
|
|
204
182
|
"list_projects",
|
|
@@ -950,13 +928,16 @@ function registerVariantWriteTools(server, client) {
|
|
|
950
928
|
description: "Create a NO-CODE managed text variant for a component (content stored in SentientUI, rendered by <AdaptiveText>). Use this ONLY for text-only variants the user wants without a code change. For variants that will live in the codebase (full components \u2014 copy, markup, styling), use get_variant_brief and write the variant in code instead; those auto-register on deploy and do not need create_variant. Requires a paid plan (server keys are Starter+; anonymous demo tokens are read-only).",
|
|
951
929
|
inputSchema: {
|
|
952
930
|
projectId: projectIdSchema,
|
|
953
|
-
componentId: import_zod9.z.string().describe("The component ID to add a variant to"),
|
|
954
|
-
displayName: import_zod9.z.string().describe("Human-readable name for the new variant"),
|
|
955
|
-
content: import_zod9.z.string().optional().describe("The text content for this managed variant (rendered by <AdaptiveText>). Generate it from get_variant_brief context; omit only to create an empty placeholder to fill in from the dashboard.")
|
|
931
|
+
componentId: import_zod9.z.string().min(1).max(200).describe("The component ID to add a variant to"),
|
|
932
|
+
displayName: import_zod9.z.string().min(1).max(200).describe("Human-readable name for the new variant"),
|
|
933
|
+
content: import_zod9.z.string().max(1e4).optional().describe("The text content for this managed variant (rendered by <AdaptiveText>). Generate it from get_variant_brief context; omit only to create an empty placeholder to fill in from the dashboard.")
|
|
956
934
|
},
|
|
957
935
|
outputSchema: {
|
|
958
936
|
variantId: import_zod9.z.string().describe("The new variant ID"),
|
|
959
|
-
displayName
|
|
937
|
+
// API returns `body.displayName ?? null`, so a successful create can
|
|
938
|
+
// carry a null name — match that contract or outputSchema validation
|
|
939
|
+
// would reject an otherwise-successful response.
|
|
940
|
+
displayName: import_zod9.z.string().nullable(),
|
|
960
941
|
componentId: import_zod9.z.string(),
|
|
961
942
|
state: import_zod9.z.literal("draft").describe("New managed variants start in draft state"),
|
|
962
943
|
hasContent: import_zod9.z.boolean().describe("Whether text content was provided at creation")
|
|
@@ -1450,7 +1431,7 @@ function registerIntegrationGuideTools(server) {
|
|
|
1450
1431
|
}
|
|
1451
1432
|
|
|
1452
1433
|
// src/server.ts
|
|
1453
|
-
var
|
|
1434
|
+
var PKG_VERSION = true ? "0.8.2" : "0.0.0-dev";
|
|
1454
1435
|
function createMcpServer(client) {
|
|
1455
1436
|
const server = new import_mcp.McpServer(
|
|
1456
1437
|
{
|
package/dist/lib.js
CHANGED