@wix/mcp 1.0.15 → 1.0.17
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/build/bin-standalone.js +12692 -12857
- package/build/bin-standalone.js.map +4 -4
- package/build/cjs/index.cjs +290 -228
- package/build/cjs/index.cjs.map +4 -4
- package/build/dts/api-call/index.d.ts +1 -1
- package/build/dts/api-call/index.d.ts.map +1 -1
- package/build/dts/api-call/index.js +161 -128
- package/build/dts/api-call/index.js.map +1 -1
- package/build/dts/api-call/validation.d.ts +8 -0
- package/build/dts/api-call/validation.d.ts.map +1 -0
- package/build/dts/api-call/validation.js +31 -0
- package/build/dts/api-call/validation.js.map +1 -0
- package/build/dts/api-call/validation.test.d.ts +2 -0
- package/build/dts/api-call/validation.test.d.ts.map +1 -0
- package/build/dts/api-call/validation.test.js +42 -0
- package/build/dts/api-call/validation.test.js.map +1 -0
- package/build/dts/bin.d.ts.map +1 -1
- package/build/dts/bin.js +22 -0
- package/build/dts/bin.js.map +1 -1
- package/build/dts/cli-tools/cli.d.ts +1 -1
- package/build/dts/cli-tools/cli.d.ts.map +1 -1
- package/build/dts/cli-tools/cli.js +2 -223
- package/build/dts/cli-tools/cli.js.map +1 -1
- package/build/dts/docs/docs.d.ts.map +1 -1
- package/build/dts/docs/docs.js +6 -2
- package/build/dts/docs/docs.js.map +1 -1
- package/build/dts/docs/fetch-article.d.ts.map +1 -1
- package/build/dts/docs/fetch-article.js +11 -0
- package/build/dts/docs/fetch-article.js.map +1 -1
- package/build/dts/docs/fetch-article.test.d.ts +2 -0
- package/build/dts/docs/fetch-article.test.d.ts.map +1 -0
- package/build/dts/docs/fetch-article.test.js +12 -0
- package/build/dts/docs/fetch-article.test.js.map +1 -0
- package/build/dts/infra/panorama.d.ts +2 -0
- package/build/dts/infra/panorama.d.ts.map +1 -1
- package/build/dts/infra/panorama.js +1 -0
- package/build/dts/infra/panorama.js.map +1 -1
- package/build/dts/wix-mcp-server.d.ts +3 -0
- package/build/dts/wix-mcp-server.d.ts.map +1 -1
- package/build/dts/wix-mcp-server.js +13 -4
- package/build/dts/wix-mcp-server.js.map +1 -1
- package/build/esm/index.js +258 -190
- package/build/esm/index.js.map +3 -3
- package/package.json +5 -5
- package/build/dts/cli-tools/utils.d.ts +0 -3
- package/build/dts/cli-tools/utils.d.ts.map +0 -1
- package/build/dts/cli-tools/utils.js +0 -26
- package/build/dts/cli-tools/utils.js.map +0 -1
package/build/esm/index.js
CHANGED
|
@@ -6833,19 +6833,6 @@ var errorUtil;
|
|
|
6833
6833
|
})(errorUtil || (errorUtil = {}));
|
|
6834
6834
|
|
|
6835
6835
|
// ../../node_modules/zod/dist/esm/v3/types.js
|
|
6836
|
-
var __classPrivateFieldGet = function(receiver, state, kind, f) {
|
|
6837
|
-
if (kind === "a" && !f) throw new TypeError("Private accessor was defined without a getter");
|
|
6838
|
-
if (typeof state === "function" ? receiver !== state || !f : !state.has(receiver)) throw new TypeError("Cannot read private member from an object whose class did not declare it");
|
|
6839
|
-
return kind === "m" ? f : kind === "a" ? f.call(receiver) : f ? f.value : state.get(receiver);
|
|
6840
|
-
};
|
|
6841
|
-
var __classPrivateFieldSet = function(receiver, state, value, kind, f) {
|
|
6842
|
-
if (kind === "m") throw new TypeError("Private method is not writable");
|
|
6843
|
-
if (kind === "a" && !f) throw new TypeError("Private accessor was defined without a setter");
|
|
6844
|
-
if (typeof state === "function" ? receiver !== state || !f : !state.has(receiver)) throw new TypeError("Cannot write private member to an object whose class did not declare it");
|
|
6845
|
-
return kind === "a" ? f.call(receiver, value) : f ? f.value = value : state.set(receiver, value), value;
|
|
6846
|
-
};
|
|
6847
|
-
var _ZodEnum_cache;
|
|
6848
|
-
var _ZodNativeEnum_cache;
|
|
6849
6836
|
var ParseInputLazyPath = class {
|
|
6850
6837
|
constructor(parent, value, path2, key) {
|
|
6851
6838
|
this._cachedPath = [];
|
|
@@ -9670,10 +9657,6 @@ function createZodEnum(values, params) {
|
|
|
9670
9657
|
});
|
|
9671
9658
|
}
|
|
9672
9659
|
var ZodEnum = class _ZodEnum extends ZodType {
|
|
9673
|
-
constructor() {
|
|
9674
|
-
super(...arguments);
|
|
9675
|
-
_ZodEnum_cache.set(this, void 0);
|
|
9676
|
-
}
|
|
9677
9660
|
_parse(input) {
|
|
9678
9661
|
if (typeof input.data !== "string") {
|
|
9679
9662
|
const ctx = this._getOrReturnCtx(input);
|
|
@@ -9685,10 +9668,10 @@ var ZodEnum = class _ZodEnum extends ZodType {
|
|
|
9685
9668
|
});
|
|
9686
9669
|
return INVALID;
|
|
9687
9670
|
}
|
|
9688
|
-
if (!
|
|
9689
|
-
|
|
9671
|
+
if (!this._cache) {
|
|
9672
|
+
this._cache = new Set(this._def.values);
|
|
9690
9673
|
}
|
|
9691
|
-
if (!
|
|
9674
|
+
if (!this._cache.has(input.data)) {
|
|
9692
9675
|
const ctx = this._getOrReturnCtx(input);
|
|
9693
9676
|
const expectedValues = this._def.values;
|
|
9694
9677
|
addIssueToContext(ctx, {
|
|
@@ -9737,13 +9720,8 @@ var ZodEnum = class _ZodEnum extends ZodType {
|
|
|
9737
9720
|
});
|
|
9738
9721
|
}
|
|
9739
9722
|
};
|
|
9740
|
-
_ZodEnum_cache = /* @__PURE__ */ new WeakMap();
|
|
9741
9723
|
ZodEnum.create = createZodEnum;
|
|
9742
9724
|
var ZodNativeEnum = class extends ZodType {
|
|
9743
|
-
constructor() {
|
|
9744
|
-
super(...arguments);
|
|
9745
|
-
_ZodNativeEnum_cache.set(this, void 0);
|
|
9746
|
-
}
|
|
9747
9725
|
_parse(input) {
|
|
9748
9726
|
const nativeEnumValues = util.getValidEnumValues(this._def.values);
|
|
9749
9727
|
const ctx = this._getOrReturnCtx(input);
|
|
@@ -9756,10 +9734,10 @@ var ZodNativeEnum = class extends ZodType {
|
|
|
9756
9734
|
});
|
|
9757
9735
|
return INVALID;
|
|
9758
9736
|
}
|
|
9759
|
-
if (!
|
|
9760
|
-
|
|
9737
|
+
if (!this._cache) {
|
|
9738
|
+
this._cache = new Set(util.getValidEnumValues(this._def.values));
|
|
9761
9739
|
}
|
|
9762
|
-
if (!
|
|
9740
|
+
if (!this._cache.has(input.data)) {
|
|
9763
9741
|
const expectedValues = util.objectValues(nativeEnumValues);
|
|
9764
9742
|
addIssueToContext(ctx, {
|
|
9765
9743
|
received: ctx.data,
|
|
@@ -9774,7 +9752,6 @@ var ZodNativeEnum = class extends ZodType {
|
|
|
9774
9752
|
return this._def.values;
|
|
9775
9753
|
}
|
|
9776
9754
|
};
|
|
9777
|
-
_ZodNativeEnum_cache = /* @__PURE__ */ new WeakMap();
|
|
9778
9755
|
ZodNativeEnum.create = (values, params) => {
|
|
9779
9756
|
return new ZodNativeEnum({
|
|
9780
9757
|
values,
|
|
@@ -9915,7 +9892,7 @@ var ZodEffects = class extends ZodType {
|
|
|
9915
9892
|
parent: ctx
|
|
9916
9893
|
});
|
|
9917
9894
|
if (!isValid(base))
|
|
9918
|
-
return
|
|
9895
|
+
return INVALID;
|
|
9919
9896
|
const result = effect.transform(base.value, checkCtx);
|
|
9920
9897
|
if (result instanceof Promise) {
|
|
9921
9898
|
throw new Error(`Asynchronous transform encountered during synchronous parse operation. Use .parseAsync instead.`);
|
|
@@ -9924,7 +9901,7 @@ var ZodEffects = class extends ZodType {
|
|
|
9924
9901
|
} else {
|
|
9925
9902
|
return this._def.schema._parseAsync({ data: ctx.data, path: ctx.path, parent: ctx }).then((base) => {
|
|
9926
9903
|
if (!isValid(base))
|
|
9927
|
-
return
|
|
9904
|
+
return INVALID;
|
|
9928
9905
|
return Promise.resolve(effect.transform(base.value, checkCtx)).then((result) => ({
|
|
9929
9906
|
status: status.value,
|
|
9930
9907
|
value: result
|
|
@@ -11337,7 +11314,7 @@ var Protocol = class {
|
|
|
11337
11314
|
request(request, resultSchema, options) {
|
|
11338
11315
|
const { relatedRequestId, resumptionToken, onresumptiontoken } = options !== null && options !== void 0 ? options : {};
|
|
11339
11316
|
return new Promise((resolve, reject) => {
|
|
11340
|
-
var _a, _b, _c, _d, _e;
|
|
11317
|
+
var _a, _b, _c, _d, _e, _f;
|
|
11341
11318
|
if (!this._transport) {
|
|
11342
11319
|
reject(new Error("Not connected"));
|
|
11343
11320
|
return;
|
|
@@ -11356,7 +11333,10 @@ var Protocol = class {
|
|
|
11356
11333
|
this._progressHandlers.set(messageId, options.onprogress);
|
|
11357
11334
|
jsonrpcRequest.params = {
|
|
11358
11335
|
...request.params,
|
|
11359
|
-
_meta: {
|
|
11336
|
+
_meta: {
|
|
11337
|
+
...((_c = request.params) === null || _c === void 0 ? void 0 : _c._meta) || {},
|
|
11338
|
+
progressToken: messageId
|
|
11339
|
+
}
|
|
11360
11340
|
};
|
|
11361
11341
|
}
|
|
11362
11342
|
const cancel = (reason) => {
|
|
@@ -11389,13 +11369,13 @@ var Protocol = class {
|
|
|
11389
11369
|
reject(error);
|
|
11390
11370
|
}
|
|
11391
11371
|
});
|
|
11392
|
-
(
|
|
11372
|
+
(_d = options === null || options === void 0 ? void 0 : options.signal) === null || _d === void 0 ? void 0 : _d.addEventListener("abort", () => {
|
|
11393
11373
|
var _a2;
|
|
11394
11374
|
cancel((_a2 = options === null || options === void 0 ? void 0 : options.signal) === null || _a2 === void 0 ? void 0 : _a2.reason);
|
|
11395
11375
|
});
|
|
11396
|
-
const timeout = (
|
|
11376
|
+
const timeout = (_e = options === null || options === void 0 ? void 0 : options.timeout) !== null && _e !== void 0 ? _e : DEFAULT_REQUEST_TIMEOUT_MSEC;
|
|
11397
11377
|
const timeoutHandler = () => cancel(new McpError(ErrorCode.RequestTimeout, "Request timed out", { timeout }));
|
|
11398
|
-
this._setupTimeout(messageId, timeout, options === null || options === void 0 ? void 0 : options.maxTotalTimeout, timeoutHandler, (
|
|
11378
|
+
this._setupTimeout(messageId, timeout, options === null || options === void 0 ? void 0 : options.maxTotalTimeout, timeoutHandler, (_f = options === null || options === void 0 ? void 0 : options.resetTimeoutOnProgress) !== null && _f !== void 0 ? _f : false);
|
|
11399
11379
|
this._transport.send(jsonrpcRequest, { relatedRequestId, resumptionToken, onresumptiontoken }).catch((error) => {
|
|
11400
11380
|
this._cleanupTimeout(messageId);
|
|
11401
11381
|
reject(error);
|
|
@@ -13052,6 +13032,9 @@ var McpServer = class {
|
|
|
13052
13032
|
return;
|
|
13053
13033
|
}
|
|
13054
13034
|
this.server.assertCanSetRequestHandler(CompleteRequestSchema.shape.method.value);
|
|
13035
|
+
this.server.registerCapabilities({
|
|
13036
|
+
completions: {}
|
|
13037
|
+
});
|
|
13055
13038
|
this.server.setRequestHandler(CompleteRequestSchema, async (request) => {
|
|
13056
13039
|
switch (request.params.ref.type) {
|
|
13057
13040
|
case "ref/prompt":
|
|
@@ -13124,8 +13107,9 @@ var McpServer = class {
|
|
|
13124
13107
|
const result = await template.resourceTemplate.listCallback(extra);
|
|
13125
13108
|
for (const resource of result.resources) {
|
|
13126
13109
|
templateResources.push({
|
|
13127
|
-
...
|
|
13128
|
-
|
|
13110
|
+
...template.metadata,
|
|
13111
|
+
// the defined resource metadata should override the template metadata if present
|
|
13112
|
+
...resource
|
|
13129
13113
|
});
|
|
13130
13114
|
}
|
|
13131
13115
|
}
|
|
@@ -15264,6 +15248,7 @@ var createPanoramaClient = (opts) => {
|
|
|
15264
15248
|
},
|
|
15265
15249
|
data: {
|
|
15266
15250
|
environment: opts.environment,
|
|
15251
|
+
serverInfo: opts.serverInfo,
|
|
15267
15252
|
runtime: {
|
|
15268
15253
|
packageVersion: packageJson.version,
|
|
15269
15254
|
versions: process.versions,
|
|
@@ -16863,12 +16848,9 @@ var logger2 = createNullLogger();
|
|
|
16863
16848
|
|
|
16864
16849
|
// src/wix-mcp-server.ts
|
|
16865
16850
|
var WixMcpServer = class extends McpServer {
|
|
16866
|
-
biLogger;
|
|
16867
|
-
nodeEnv;
|
|
16868
|
-
sessionId;
|
|
16869
|
-
getUserId;
|
|
16870
16851
|
constructor(serverInfo, options, nodeEnv) {
|
|
16871
16852
|
super(serverInfo, options);
|
|
16853
|
+
this.serverInfo = serverInfo;
|
|
16872
16854
|
this.sessionId = v4_default();
|
|
16873
16855
|
this.nodeEnv = getEnvironment(nodeEnv);
|
|
16874
16856
|
this.biLogger = createBiLogger({
|
|
@@ -16876,9 +16858,17 @@ var WixMcpServer = class extends McpServer {
|
|
|
16876
16858
|
});
|
|
16877
16859
|
logger2.log(`WixMcpServer created with sessionId: ${this.sessionId}`);
|
|
16878
16860
|
}
|
|
16861
|
+
biLogger;
|
|
16862
|
+
nodeEnv;
|
|
16863
|
+
sessionId;
|
|
16864
|
+
getUserId;
|
|
16865
|
+
getClientName;
|
|
16879
16866
|
setUserIdGetter(getUserId) {
|
|
16880
16867
|
this.getUserId = getUserId;
|
|
16881
16868
|
}
|
|
16869
|
+
setClientNameGetter(getClientName) {
|
|
16870
|
+
this.getClientName = getClientName;
|
|
16871
|
+
}
|
|
16882
16872
|
tool(...args) {
|
|
16883
16873
|
const cbIndex = args.findIndex((arg) => typeof arg === "function");
|
|
16884
16874
|
if (cbIndex !== -1) {
|
|
@@ -16893,7 +16883,8 @@ var WixMcpServer = class extends McpServer {
|
|
|
16893
16883
|
environment: this.nodeEnv,
|
|
16894
16884
|
sessionId: this.sessionId,
|
|
16895
16885
|
componentId: toolName,
|
|
16896
|
-
uuid: this.getUserId?.()
|
|
16886
|
+
uuid: this.getUserId?.(),
|
|
16887
|
+
serverInfo: this.serverInfo
|
|
16897
16888
|
});
|
|
16898
16889
|
const toolInvocationId = v4_default();
|
|
16899
16890
|
const httpClient = new HttpClient3({
|
|
@@ -16942,6 +16933,7 @@ var WixMcpServer = class extends McpServer {
|
|
|
16942
16933
|
} finally {
|
|
16943
16934
|
const endTime = performance.now();
|
|
16944
16935
|
const duration = Math.round(endTime - startTime);
|
|
16936
|
+
const clientName = this.server.getClientVersion()?.name;
|
|
16945
16937
|
if (!isDevEnvironment) {
|
|
16946
16938
|
if (this.getUserId) {
|
|
16947
16939
|
const userId = this.getUserId();
|
|
@@ -16951,14 +16943,15 @@ var WixMcpServer = class extends McpServer {
|
|
|
16951
16943
|
}
|
|
16952
16944
|
this.biLogger.report(
|
|
16953
16945
|
wixMcpRequestSrc39Evid1607({
|
|
16946
|
+
clientName: this.getClientName?.() || clientName,
|
|
16947
|
+
duration,
|
|
16948
|
+
errorBody,
|
|
16954
16949
|
toolInvocationId,
|
|
16955
16950
|
toolName,
|
|
16956
16951
|
params: JSON.stringify(argsBeforeExtra),
|
|
16957
16952
|
origin: this.nodeEnv,
|
|
16958
|
-
duration,
|
|
16959
16953
|
sessionId: this.sessionId,
|
|
16960
|
-
executionResult: toolSucceeded ? "Success" : "Error"
|
|
16961
|
-
errorBody
|
|
16954
|
+
executionResult: toolSucceeded ? "Success" : "Error"
|
|
16962
16955
|
})
|
|
16963
16956
|
);
|
|
16964
16957
|
}
|
|
@@ -17116,6 +17109,18 @@ async function fetchArticleContentFromDigor(httpClient, articleUrl, mode, stripH
|
|
|
17116
17109
|
}
|
|
17117
17110
|
async function fetchArticleContent(httpClient, articleUrl, mode, stripHeader = false) {
|
|
17118
17111
|
if (mode === "raw") {
|
|
17112
|
+
let parsedUrl;
|
|
17113
|
+
try {
|
|
17114
|
+
parsedUrl = new URL(articleUrl);
|
|
17115
|
+
} catch {
|
|
17116
|
+
throw new Error(`Invalid URL format: ${articleUrl}`);
|
|
17117
|
+
}
|
|
17118
|
+
const hostname = parsedUrl.hostname.replace("www.", "");
|
|
17119
|
+
if (hostname !== "dev.wix.com") {
|
|
17120
|
+
throw new Error(
|
|
17121
|
+
`Unsupported URL domain: ${hostname}. Article URL must be from dev.wix.com`
|
|
17122
|
+
);
|
|
17123
|
+
}
|
|
17119
17124
|
const { data: doc } = await httpClient.get(articleUrl);
|
|
17120
17125
|
return doc;
|
|
17121
17126
|
}
|
|
@@ -17607,7 +17612,7 @@ var addDocsTools = (server, allowedTools = [
|
|
|
17607
17612
|
getToKnowWixEnabled ? WixREADME_DEPENDENT_DESCRIPTION : ""
|
|
17608
17613
|
].join("\n"),
|
|
17609
17614
|
{
|
|
17610
|
-
articleUrl: external_exports.string().describe(
|
|
17615
|
+
articleUrl: external_exports.string().url().startsWith("https://dev.wix.com/").describe(
|
|
17611
17616
|
"The URL of the docs article or method article to fetch. Should be something like https://dev.wix.com/docs/.../.../..."
|
|
17612
17617
|
)
|
|
17613
17618
|
},
|
|
@@ -17644,7 +17649,7 @@ var addDocsTools = (server, allowedTools = [
|
|
|
17644
17649
|
content: [
|
|
17645
17650
|
{
|
|
17646
17651
|
type: "text",
|
|
17647
|
-
text:
|
|
17652
|
+
text: `Could not fetch article content: "${error.message}". You should try completing the task without it.`
|
|
17648
17653
|
}
|
|
17649
17654
|
]
|
|
17650
17655
|
};
|
|
@@ -17658,7 +17663,7 @@ var addDocsTools = (server, allowedTools = [
|
|
|
17658
17663
|
"This will give you the entire request/response schema with all the fields and their descriptions."
|
|
17659
17664
|
].join("\n"),
|
|
17660
17665
|
{
|
|
17661
|
-
articleUrl: external_exports.string().describe(
|
|
17666
|
+
articleUrl: external_exports.string().url().startsWith("https://dev.wix.com/").describe(
|
|
17662
17667
|
"The URL of the documentation to fetch. Should be something like https://dev.wix.com/docs/.../.../..."
|
|
17663
17668
|
)
|
|
17664
17669
|
},
|
|
@@ -17688,7 +17693,7 @@ var addDocsTools = (server, allowedTools = [
|
|
|
17688
17693
|
content: [
|
|
17689
17694
|
{
|
|
17690
17695
|
type: "text",
|
|
17691
|
-
text:
|
|
17696
|
+
text: `Could not fetch method schema: "${error.message}". You should try completing the task without it.`
|
|
17692
17697
|
}
|
|
17693
17698
|
]
|
|
17694
17699
|
};
|
|
@@ -17735,164 +17740,227 @@ var handleWixAPIResponse = async (response) => {
|
|
|
17735
17740
|
return responseData;
|
|
17736
17741
|
};
|
|
17737
17742
|
|
|
17743
|
+
// src/api-call/validation.ts
|
|
17744
|
+
function isApiUrlAllowed(url) {
|
|
17745
|
+
let parsedUrl;
|
|
17746
|
+
try {
|
|
17747
|
+
parsedUrl = new URL(url);
|
|
17748
|
+
} catch {
|
|
17749
|
+
return {
|
|
17750
|
+
isAllowed: false,
|
|
17751
|
+
error: `Invalid URL format: ${url}`
|
|
17752
|
+
};
|
|
17753
|
+
}
|
|
17754
|
+
const ALLOWED_HOSTNAMES = [
|
|
17755
|
+
"wix.com",
|
|
17756
|
+
"dev.wix.com",
|
|
17757
|
+
"manage.wix.com",
|
|
17758
|
+
"editor.wix.com",
|
|
17759
|
+
"wixapis.com"
|
|
17760
|
+
];
|
|
17761
|
+
const hostname = parsedUrl.hostname.replace("www.", "");
|
|
17762
|
+
const isAllowedHostname = ALLOWED_HOSTNAMES.some(
|
|
17763
|
+
(domain) => hostname === domain
|
|
17764
|
+
);
|
|
17765
|
+
if (!isAllowedHostname) {
|
|
17766
|
+
return {
|
|
17767
|
+
isAllowed: false,
|
|
17768
|
+
error: `Unsupported URL domain: ${hostname}. URL must be from one of the allowed domains: ${ALLOWED_HOSTNAMES.join(", ")}`
|
|
17769
|
+
};
|
|
17770
|
+
}
|
|
17771
|
+
return {
|
|
17772
|
+
isAllowed: true
|
|
17773
|
+
};
|
|
17774
|
+
}
|
|
17775
|
+
|
|
17738
17776
|
// src/api-call/index.ts
|
|
17739
|
-
function addApiCallTool(server, strategy) {
|
|
17740
|
-
|
|
17741
|
-
|
|
17742
|
-
|
|
17743
|
-
|
|
17744
|
-
|
|
17745
|
-
|
|
17746
|
-
|
|
17747
|
-
|
|
17748
|
-
|
|
17749
|
-
|
|
17750
|
-
|
|
17751
|
-
|
|
17752
|
-
|
|
17753
|
-
|
|
17754
|
-
|
|
17755
|
-
|
|
17756
|
-
|
|
17757
|
-
|
|
17758
|
-
|
|
17759
|
-
|
|
17760
|
-
|
|
17761
|
-
|
|
17762
|
-
|
|
17763
|
-
|
|
17764
|
-
|
|
17765
|
-
|
|
17766
|
-
|
|
17767
|
-
const
|
|
17768
|
-
|
|
17769
|
-
|
|
17770
|
-
|
|
17771
|
-
|
|
17772
|
-
|
|
17773
|
-
|
|
17774
|
-
|
|
17775
|
-
|
|
17776
|
-
|
|
17777
|
-
|
|
17778
|
-
content: [
|
|
17779
|
-
{
|
|
17780
|
-
type: "text",
|
|
17781
|
-
text: `Wix Site API call successful: ${JSON.stringify(responseData)}`
|
|
17782
|
-
}
|
|
17783
|
-
]
|
|
17784
|
-
};
|
|
17785
|
-
} catch (error) {
|
|
17786
|
-
logger2.error(`Failed to call Wix Site API: ${error}`);
|
|
17787
|
-
const response = error.response;
|
|
17788
|
-
if (!response) {
|
|
17789
|
-
throw new Error(`Failed to call Wix Site API: ${error}`);
|
|
17777
|
+
function addApiCallTool(server, strategy, allowedTools = ["CallWixSiteAPI", "ListWixSites", "ManageWixSite"]) {
|
|
17778
|
+
if (allowedTools.includes("CallWixSiteAPI")) {
|
|
17779
|
+
server.tool(
|
|
17780
|
+
"CallWixSiteAPI",
|
|
17781
|
+
[
|
|
17782
|
+
"Call Wix apis on a business or site. Use this to create, read, update, and delete data and other Wix entities in your Wix site,",
|
|
17783
|
+
`You should ALWAYS check the rest docs - "SearchWixRESTDocumentation" for the specific API you want to call, don't just call it without knowing what it does, CHECK THE DOCS`,
|
|
17784
|
+
"Error Handling:",
|
|
17785
|
+
'If the error is related to missing installed app or "WDE0110: Wix Code not enabled", you should install the missing app by using ReadFullDocsArticle tool to fetch the article - https://dev.wix.com/docs/kb-only/MCP_REST_RECIPES_KB_ID/TRAIN_wix.devcenter.apps.installer.v1.AppsInstallerService.InstallApp',
|
|
17786
|
+
"**Note:** there is no need to check if an app is installed/ Wix Code enabled in advance, just call the API and handle the error if it occurs, the API error message will state it clearly.",
|
|
17787
|
+
"For any other error, use your default error handling mechanism"
|
|
17788
|
+
].join("\n"),
|
|
17789
|
+
{
|
|
17790
|
+
siteId: external_exports.string().describe("The id of the site selected using site selection tool"),
|
|
17791
|
+
url: external_exports.string().url().describe(
|
|
17792
|
+
"The url of the api to call - ALWAYS get the information from the Wix REST docs or from the conversation context, the URL MUST BE ABSOLUTE URL"
|
|
17793
|
+
),
|
|
17794
|
+
method: external_exports.string().describe(
|
|
17795
|
+
"The HTTP method to use for the API call (e.g. GET, POST, PUT, DELETE)"
|
|
17796
|
+
),
|
|
17797
|
+
body: external_exports.string().optional().describe(
|
|
17798
|
+
"A string representing of a valid JSON object to describe the body of the request"
|
|
17799
|
+
)
|
|
17800
|
+
},
|
|
17801
|
+
async ({ url, body, method, siteId }, { httpClient }) => {
|
|
17802
|
+
logger2.log(
|
|
17803
|
+
`Calling Wix Site API: ${siteId} ${url}, body: ${JSON.stringify(body)}`
|
|
17804
|
+
);
|
|
17805
|
+
const { isAllowed, error: urlError } = isApiUrlAllowed(url);
|
|
17806
|
+
if (!isAllowed) {
|
|
17807
|
+
return {
|
|
17808
|
+
content: [
|
|
17809
|
+
{
|
|
17810
|
+
isError: true,
|
|
17811
|
+
type: "text",
|
|
17812
|
+
text: `Error validating URL: ${urlError}`
|
|
17813
|
+
}
|
|
17814
|
+
]
|
|
17815
|
+
};
|
|
17790
17816
|
}
|
|
17791
|
-
|
|
17792
|
-
|
|
17793
|
-
|
|
17794
|
-
|
|
17795
|
-
|
|
17796
|
-
|
|
17797
|
-
|
|
17798
|
-
|
|
17799
|
-
|
|
17800
|
-
|
|
17801
|
-
|
|
17802
|
-
|
|
17803
|
-
|
|
17804
|
-
|
|
17805
|
-
|
|
17806
|
-
|
|
17807
|
-
"https://www.wixapis.com/site-list/v2/sites/query",
|
|
17808
|
-
{
|
|
17809
|
-
query: {
|
|
17810
|
-
cursorPaging: { limit: 21 },
|
|
17811
|
-
filter: {
|
|
17812
|
-
...nameSearch ? {
|
|
17813
|
-
name: nameSearch
|
|
17814
|
-
} : {},
|
|
17815
|
-
namespace: {
|
|
17816
|
-
$in: ["WIX", "DASHBOARD_FIRST", "ANYWHERE", "HEADLESS"]
|
|
17817
|
+
try {
|
|
17818
|
+
const response = await httpClient.request({
|
|
17819
|
+
url,
|
|
17820
|
+
method,
|
|
17821
|
+
headers: {
|
|
17822
|
+
...await strategy.getSiteAuthHeaders(siteId),
|
|
17823
|
+
...body ? { "Content-Type": "application/json" } : {}
|
|
17824
|
+
},
|
|
17825
|
+
data: method === "GET" ? void 0 : body
|
|
17826
|
+
});
|
|
17827
|
+
const responseData = await handleWixAPIResponse(response);
|
|
17828
|
+
return {
|
|
17829
|
+
content: [
|
|
17830
|
+
{
|
|
17831
|
+
type: "text",
|
|
17832
|
+
text: `Wix Site API call successful: ${JSON.stringify(responseData)}`
|
|
17817
17833
|
}
|
|
17818
|
-
|
|
17819
|
-
}
|
|
17820
|
-
}
|
|
17821
|
-
|
|
17822
|
-
|
|
17823
|
-
|
|
17824
|
-
|
|
17825
|
-
Accept: "application/json, text/plain, */*"
|
|
17834
|
+
]
|
|
17835
|
+
};
|
|
17836
|
+
} catch (error) {
|
|
17837
|
+
logger2.error(`Failed to call Wix Site API: ${error}`);
|
|
17838
|
+
const response = error.response;
|
|
17839
|
+
if (!response) {
|
|
17840
|
+
throw new Error(`Failed to call Wix Site API: ${error}`);
|
|
17826
17841
|
}
|
|
17842
|
+
return handleWixAPIResponse(response);
|
|
17827
17843
|
}
|
|
17828
|
-
|
|
17829
|
-
|
|
17830
|
-
|
|
17831
|
-
|
|
17832
|
-
|
|
17833
|
-
|
|
17834
|
-
|
|
17844
|
+
}
|
|
17845
|
+
);
|
|
17846
|
+
}
|
|
17847
|
+
if (allowedTools.includes("ListWixSites")) {
|
|
17848
|
+
server.tool(
|
|
17849
|
+
"ListWixSites",
|
|
17850
|
+
"List Wix sites for the current user, by default it will return all sites, but you can filter by name",
|
|
17851
|
+
{
|
|
17852
|
+
nameSearch: external_exports.string().optional().describe(
|
|
17853
|
+
"optional filer by name, if not provided all sites will be returned"
|
|
17854
|
+
),
|
|
17855
|
+
// Hack for Cursor ignoring tools with no params (when nameSearch is optional)
|
|
17856
|
+
alwaysTrue: external_exports.boolean().describe("Always pass true to this parameter")
|
|
17857
|
+
},
|
|
17858
|
+
async ({ nameSearch }, { httpClient }) => {
|
|
17859
|
+
const sitesRes = await httpClient.post(
|
|
17860
|
+
"https://www.wixapis.com/site-list/v2/sites/query",
|
|
17835
17861
|
{
|
|
17836
|
-
|
|
17837
|
-
|
|
17862
|
+
query: {
|
|
17863
|
+
cursorPaging: { limit: 21 },
|
|
17864
|
+
filter: {
|
|
17865
|
+
...nameSearch ? {
|
|
17866
|
+
name: nameSearch
|
|
17867
|
+
} : {},
|
|
17868
|
+
namespace: {
|
|
17869
|
+
$in: ["WIX", "DASHBOARD_FIRST", "ANYWHERE", "HEADLESS"]
|
|
17870
|
+
}
|
|
17871
|
+
}
|
|
17872
|
+
}
|
|
17838
17873
|
},
|
|
17839
17874
|
{
|
|
17840
|
-
|
|
17841
|
-
|
|
17875
|
+
headers: {
|
|
17876
|
+
...await strategy.getAccountAuthHeaders(),
|
|
17877
|
+
"Content-Type": "application/json",
|
|
17878
|
+
Accept: "application/json, text/plain, */*"
|
|
17879
|
+
}
|
|
17842
17880
|
}
|
|
17843
|
-
|
|
17844
|
-
|
|
17845
|
-
|
|
17846
|
-
|
|
17847
|
-
|
|
17848
|
-
"ManageWixSite",
|
|
17849
|
-
`Use account level API in order to create a site, update a site and publish site.
|
|
17850
|
-
ALWAYS use "SearchWixRESTDocumentation" to search for the API you should invoke, NEVER GUESS THE SITE API URL
|
|
17851
|
-
You should ALWAYS check the rest docs - "SearchWixRESTDocumentation" for the specific API you want to call, don't just call it without knowing what it does, CHECK THE DOCS`,
|
|
17852
|
-
{
|
|
17853
|
-
url: external_exports.string().describe(
|
|
17854
|
-
"The url of the api to call - ALWAYS get the information from the Wix REST docs DONT GUESS IT, the URL MUST BE ABSOLUTE URL"
|
|
17855
|
-
),
|
|
17856
|
-
method: external_exports.string().describe(
|
|
17857
|
-
"The HTTP method to use for the API call (e.g. GET, POST, PUT, DELETE)"
|
|
17858
|
-
),
|
|
17859
|
-
body: external_exports.string().optional().describe(
|
|
17860
|
-
"A string representing of a valid JSON object to describe the body of the request"
|
|
17861
|
-
)
|
|
17862
|
-
},
|
|
17863
|
-
async ({ url, body, method }, { httpClient }) => {
|
|
17864
|
-
logger2.log(
|
|
17865
|
-
`Calling Wix Account level API: ${url}, body: ${JSON.stringify(body)}`
|
|
17866
|
-
);
|
|
17867
|
-
try {
|
|
17868
|
-
const response = await httpClient.request({
|
|
17869
|
-
url,
|
|
17870
|
-
method,
|
|
17871
|
-
headers: {
|
|
17872
|
-
...await strategy.getAccountAuthHeaders(),
|
|
17873
|
-
...body ? { "Content-Type": "application/json" } : {}
|
|
17874
|
-
},
|
|
17875
|
-
data: method === "GET" ? void 0 : body
|
|
17876
|
-
});
|
|
17877
|
-
const responseData = await handleWixAPIResponse(response);
|
|
17881
|
+
);
|
|
17882
|
+
const result = sitesRes.data.sites?.map(({ id, displayName }) => ({
|
|
17883
|
+
id,
|
|
17884
|
+
name: displayName
|
|
17885
|
+
})) ?? [];
|
|
17878
17886
|
return {
|
|
17879
17887
|
content: [
|
|
17880
17888
|
{
|
|
17881
17889
|
type: "text",
|
|
17882
|
-
text:
|
|
17890
|
+
text: JSON.stringify(result)
|
|
17891
|
+
},
|
|
17892
|
+
{
|
|
17893
|
+
type: "text",
|
|
17894
|
+
text: "if there is more than one site returned, the user should pick one from a list, list the sites (only name) for the user and ask them to pick one,If more than 20 are found you should list all 20 and suggest to search by the name of the site they are looking for"
|
|
17883
17895
|
}
|
|
17884
17896
|
]
|
|
17885
17897
|
};
|
|
17886
|
-
}
|
|
17887
|
-
|
|
17888
|
-
|
|
17889
|
-
|
|
17890
|
-
|
|
17898
|
+
}
|
|
17899
|
+
);
|
|
17900
|
+
}
|
|
17901
|
+
if (allowedTools.includes("ManageWixSite")) {
|
|
17902
|
+
server.tool(
|
|
17903
|
+
"ManageWixSite",
|
|
17904
|
+
`Use account level API in order to create a site, update a site and publish site.
|
|
17905
|
+
ALWAYS use "SearchWixRESTDocumentation" to search for the API you should invoke, NEVER GUESS THE SITE API URL
|
|
17906
|
+
You should ALWAYS check the rest docs - "SearchWixRESTDocumentation" for the specific API you want to call, don't just call it without knowing what it does, CHECK THE DOCS`,
|
|
17907
|
+
{
|
|
17908
|
+
url: external_exports.string().url().describe(
|
|
17909
|
+
"The url of the api to call - ALWAYS get the information from the Wix REST docs DONT GUESS IT, the URL MUST BE ABSOLUTE URL"
|
|
17910
|
+
),
|
|
17911
|
+
method: external_exports.string().describe(
|
|
17912
|
+
"The HTTP method to use for the API call (e.g. GET, POST, PUT, DELETE)"
|
|
17913
|
+
),
|
|
17914
|
+
body: external_exports.string().optional().describe(
|
|
17915
|
+
"A string representing of a valid JSON object to describe the body of the request"
|
|
17916
|
+
)
|
|
17917
|
+
},
|
|
17918
|
+
async ({ url, body, method }, { httpClient }) => {
|
|
17919
|
+
logger2.log(
|
|
17920
|
+
`Calling Wix Account level API: ${url}, body: ${JSON.stringify(body)}`
|
|
17921
|
+
);
|
|
17922
|
+
const { isAllowed, error: urlError } = isApiUrlAllowed(url);
|
|
17923
|
+
if (!isAllowed) {
|
|
17924
|
+
return {
|
|
17925
|
+
content: [
|
|
17926
|
+
{
|
|
17927
|
+
isError: true,
|
|
17928
|
+
type: "text",
|
|
17929
|
+
text: `Error validating URL: ${urlError}`
|
|
17930
|
+
}
|
|
17931
|
+
]
|
|
17932
|
+
};
|
|
17933
|
+
}
|
|
17934
|
+
try {
|
|
17935
|
+
const response = await httpClient.request({
|
|
17936
|
+
url,
|
|
17937
|
+
method,
|
|
17938
|
+
headers: {
|
|
17939
|
+
...await strategy.getAccountAuthHeaders(),
|
|
17940
|
+
...body ? { "Content-Type": "application/json" } : {}
|
|
17941
|
+
},
|
|
17942
|
+
data: method === "GET" ? void 0 : body
|
|
17943
|
+
});
|
|
17944
|
+
const responseData = await handleWixAPIResponse(response);
|
|
17945
|
+
return {
|
|
17946
|
+
content: [
|
|
17947
|
+
{
|
|
17948
|
+
type: "text",
|
|
17949
|
+
text: `Wix Account API call successful: ${JSON.stringify(responseData)}`
|
|
17950
|
+
}
|
|
17951
|
+
]
|
|
17952
|
+
};
|
|
17953
|
+
} catch (error) {
|
|
17954
|
+
logger2.error(`Failed to call Wix Account API: ${error}`);
|
|
17955
|
+
const response = error.response;
|
|
17956
|
+
if (!response) {
|
|
17957
|
+
throw new Error(`Failed to call Wix Account API: ${error}`);
|
|
17958
|
+
}
|
|
17959
|
+
return handleWixAPIResponse(response);
|
|
17891
17960
|
}
|
|
17892
|
-
return handleWixAPIResponse(response);
|
|
17893
17961
|
}
|
|
17894
|
-
|
|
17895
|
-
|
|
17962
|
+
);
|
|
17963
|
+
}
|
|
17896
17964
|
}
|
|
17897
17965
|
|
|
17898
17966
|
// src/resources/docs.ts
|