integrate-sdk 0.8.60-dev.0 → 0.8.62-dev.0
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/adapters/auto-routes.js +309 -121
- package/dist/adapters/base-handler.d.ts.map +1 -1
- package/dist/adapters/index.js +306 -118
- package/dist/adapters/nextjs.js +306 -118
- package/dist/adapters/node.js +306 -118
- package/dist/adapters/svelte-kit.js +306 -118
- package/dist/adapters/tanstack-start.js +306 -118
- package/dist/index.js +306 -112
- package/dist/oauth.js +300 -112
- package/dist/server.js +293 -105
- package/dist/src/adapters/base-handler.d.ts.map +1 -1
- package/dist/src/index.d.ts +4 -1
- package/dist/src/index.d.ts.map +1 -1
- package/dist/src/server.d.ts.map +1 -1
- package/dist/src/triggers/executor.d.ts +50 -0
- package/dist/src/triggers/executor.d.ts.map +1 -0
- package/dist/src/triggers/index.d.ts +6 -2
- package/dist/src/triggers/index.d.ts.map +1 -1
- package/dist/src/triggers/types.d.ts +116 -0
- package/dist/src/triggers/types.d.ts.map +1 -1
- package/dist/src/triggers/utils.d.ts +20 -0
- package/dist/src/triggers/utils.d.ts.map +1 -1
- package/dist/src/triggers/webhooks.d.ts +28 -0
- package/dist/src/triggers/webhooks.d.ts.map +1 -0
- package/package.json +1 -1
package/dist/index.js
CHANGED
|
@@ -8303,6 +8303,7 @@ var init_index_browser = () => {};
|
|
|
8303
8303
|
// src/triggers/utils.ts
|
|
8304
8304
|
var exports_utils = {};
|
|
8305
8305
|
__export(exports_utils, {
|
|
8306
|
+
validateStepLimit: () => validateStepLimit,
|
|
8306
8307
|
validateStatusTransition: () => validateStatusTransition,
|
|
8307
8308
|
generateTriggerId: () => generateTriggerId,
|
|
8308
8309
|
extractProviderFromToolName: () => extractProviderFromToolName,
|
|
@@ -8330,6 +8331,15 @@ function validateStatusTransition(currentStatus, targetStatus) {
|
|
|
8330
8331
|
}
|
|
8331
8332
|
return { valid: true };
|
|
8332
8333
|
}
|
|
8334
|
+
function validateStepLimit(stepIndex, maxSteps) {
|
|
8335
|
+
if (stepIndex >= maxSteps) {
|
|
8336
|
+
return {
|
|
8337
|
+
valid: false,
|
|
8338
|
+
error: `Step index ${stepIndex} exceeds maximum of ${maxSteps} steps`
|
|
8339
|
+
};
|
|
8340
|
+
}
|
|
8341
|
+
return { valid: true };
|
|
8342
|
+
}
|
|
8333
8343
|
function calculateHasMore(offset, returnedCount, total) {
|
|
8334
8344
|
return offset + returnedCount < total;
|
|
8335
8345
|
}
|
|
@@ -10337,6 +10347,204 @@ var init_ai = __esm(() => {
|
|
|
10337
10347
|
init_trigger_tools();
|
|
10338
10348
|
});
|
|
10339
10349
|
|
|
10350
|
+
// src/triggers/webhooks.ts
|
|
10351
|
+
async function signPayload(payload, secret) {
|
|
10352
|
+
const encoder = new TextEncoder;
|
|
10353
|
+
const data = encoder.encode(JSON.stringify(payload));
|
|
10354
|
+
const key = await crypto.subtle.importKey("raw", encoder.encode(secret), { name: "HMAC", hash: "SHA-256" }, false, ["sign"]);
|
|
10355
|
+
const signature = await crypto.subtle.sign("HMAC", key, data);
|
|
10356
|
+
return Array.from(new Uint8Array(signature)).map((b) => b.toString(16).padStart(2, "0")).join("");
|
|
10357
|
+
}
|
|
10358
|
+
async function deliverWebhook(webhook, payload, timeoutMs) {
|
|
10359
|
+
const headers = {
|
|
10360
|
+
"Content-Type": "application/json",
|
|
10361
|
+
...webhook.headers
|
|
10362
|
+
};
|
|
10363
|
+
if (webhook.secret) {
|
|
10364
|
+
headers["X-Webhook-Signature"] = await signPayload(payload, webhook.secret);
|
|
10365
|
+
}
|
|
10366
|
+
const controller = new AbortController;
|
|
10367
|
+
const timeout = setTimeout(() => controller.abort(), timeoutMs);
|
|
10368
|
+
try {
|
|
10369
|
+
const response = await fetch(webhook.url, {
|
|
10370
|
+
method: "POST",
|
|
10371
|
+
headers,
|
|
10372
|
+
body: JSON.stringify(payload),
|
|
10373
|
+
signal: controller.signal
|
|
10374
|
+
});
|
|
10375
|
+
if (!response.ok) {
|
|
10376
|
+
logger30.warn(`Webhook delivery to ${webhook.url} returned ${response.status}`);
|
|
10377
|
+
}
|
|
10378
|
+
} finally {
|
|
10379
|
+
clearTimeout(timeout);
|
|
10380
|
+
}
|
|
10381
|
+
}
|
|
10382
|
+
async function deliverWebhooks(webhooks, payload, timeoutMs) {
|
|
10383
|
+
if (webhooks.length === 0)
|
|
10384
|
+
return;
|
|
10385
|
+
const results = await Promise.allSettled(webhooks.map((webhook) => deliverWebhook(webhook, payload, timeoutMs)));
|
|
10386
|
+
for (let i = 0;i < results.length; i++) {
|
|
10387
|
+
const result = results[i];
|
|
10388
|
+
if (result.status === "rejected") {
|
|
10389
|
+
logger30.warn(`Webhook delivery to ${webhooks[i].url} failed:`, result.reason);
|
|
10390
|
+
}
|
|
10391
|
+
}
|
|
10392
|
+
}
|
|
10393
|
+
var logger30;
|
|
10394
|
+
var init_webhooks = __esm(() => {
|
|
10395
|
+
init_logger();
|
|
10396
|
+
logger30 = createLogger("Webhooks", "server");
|
|
10397
|
+
});
|
|
10398
|
+
|
|
10399
|
+
// src/triggers/types.ts
|
|
10400
|
+
var MAX_TRIGGER_STEPS = 20, WEBHOOK_DELIVERY_TIMEOUT_MS = 1e4;
|
|
10401
|
+
|
|
10402
|
+
// src/triggers/executor.ts
|
|
10403
|
+
var exports_executor = {};
|
|
10404
|
+
__export(exports_executor, {
|
|
10405
|
+
executeTrigger: () => executeTrigger
|
|
10406
|
+
});
|
|
10407
|
+
async function executeTrigger(trigger, config, context) {
|
|
10408
|
+
const steps = [];
|
|
10409
|
+
let currentToolName = trigger.toolName;
|
|
10410
|
+
let currentToolArguments = trigger.toolArguments;
|
|
10411
|
+
let currentProvider = trigger.provider;
|
|
10412
|
+
let stepIndex = 0;
|
|
10413
|
+
while (stepIndex < MAX_TRIGGER_STEPS) {
|
|
10414
|
+
const stepValidation = validateStepLimit(stepIndex, MAX_TRIGGER_STEPS);
|
|
10415
|
+
if (!stepValidation.valid) {
|
|
10416
|
+
logger31.error(`[Trigger ${trigger.id}] ${stepValidation.error}`);
|
|
10417
|
+
break;
|
|
10418
|
+
}
|
|
10419
|
+
const providerToken = await config.getProviderToken(currentProvider, undefined, context);
|
|
10420
|
+
if (!providerToken) {
|
|
10421
|
+
const error = `No OAuth token available for provider '${currentProvider}'`;
|
|
10422
|
+
logger31.error(`[Trigger ${trigger.id}] ${error}`);
|
|
10423
|
+
steps.push({
|
|
10424
|
+
stepIndex,
|
|
10425
|
+
toolName: currentToolName,
|
|
10426
|
+
success: false,
|
|
10427
|
+
error,
|
|
10428
|
+
duration: 0,
|
|
10429
|
+
executedAt: new Date().toISOString()
|
|
10430
|
+
});
|
|
10431
|
+
await config.triggers.update(trigger.id, {
|
|
10432
|
+
lastRunAt: new Date().toISOString(),
|
|
10433
|
+
runCount: (trigger.runCount || 0) + 1,
|
|
10434
|
+
lastError: error,
|
|
10435
|
+
status: "failed"
|
|
10436
|
+
}, context);
|
|
10437
|
+
return { success: false, steps, error };
|
|
10438
|
+
}
|
|
10439
|
+
const startTime = Date.now();
|
|
10440
|
+
let toolResult;
|
|
10441
|
+
let stepSuccess = true;
|
|
10442
|
+
let stepError;
|
|
10443
|
+
try {
|
|
10444
|
+
toolResult = await config.handleToolCall({ name: currentToolName, arguments: currentToolArguments }, `${providerToken.tokenType || "Bearer"} ${providerToken.accessToken}`, null);
|
|
10445
|
+
} catch (err) {
|
|
10446
|
+
stepSuccess = false;
|
|
10447
|
+
stepError = err.message || "Tool execution failed";
|
|
10448
|
+
logger31.error(`[Trigger ${trigger.id}] Step ${stepIndex} failed:`, err);
|
|
10449
|
+
}
|
|
10450
|
+
const duration = Date.now() - startTime;
|
|
10451
|
+
const executedAt = new Date().toISOString();
|
|
10452
|
+
steps.push({
|
|
10453
|
+
stepIndex,
|
|
10454
|
+
toolName: currentToolName,
|
|
10455
|
+
success: stepSuccess,
|
|
10456
|
+
result: stepSuccess ? toolResult : undefined,
|
|
10457
|
+
error: stepError,
|
|
10458
|
+
duration,
|
|
10459
|
+
executedAt
|
|
10460
|
+
});
|
|
10461
|
+
if (!config.triggers.onComplete || !stepSuccess) {
|
|
10462
|
+
const updates = {
|
|
10463
|
+
lastRunAt: executedAt,
|
|
10464
|
+
runCount: (trigger.runCount || 0) + 1
|
|
10465
|
+
};
|
|
10466
|
+
if (stepSuccess) {
|
|
10467
|
+
updates.lastResult = toolResult;
|
|
10468
|
+
updates.lastError = undefined;
|
|
10469
|
+
if (trigger.schedule.type === "once") {
|
|
10470
|
+
updates.status = "completed";
|
|
10471
|
+
}
|
|
10472
|
+
} else {
|
|
10473
|
+
updates.lastError = stepError;
|
|
10474
|
+
updates.status = "failed";
|
|
10475
|
+
}
|
|
10476
|
+
await config.triggers.update(trigger.id, updates, context);
|
|
10477
|
+
return { success: stepSuccess, steps, error: stepError };
|
|
10478
|
+
}
|
|
10479
|
+
const completeRequest = {
|
|
10480
|
+
success: stepSuccess,
|
|
10481
|
+
result: stepSuccess ? toolResult : undefined,
|
|
10482
|
+
error: stepError,
|
|
10483
|
+
executedAt,
|
|
10484
|
+
duration,
|
|
10485
|
+
stepIndex,
|
|
10486
|
+
previousResults: steps,
|
|
10487
|
+
final: false
|
|
10488
|
+
};
|
|
10489
|
+
const completeResponse = await config.triggers.onComplete({
|
|
10490
|
+
trigger,
|
|
10491
|
+
request: completeRequest,
|
|
10492
|
+
context
|
|
10493
|
+
});
|
|
10494
|
+
if (completeResponse.hasMore && completeResponse.nextStep) {
|
|
10495
|
+
currentToolName = completeResponse.nextStep.toolName;
|
|
10496
|
+
currentToolArguments = completeResponse.nextStep.toolArguments;
|
|
10497
|
+
currentProvider = completeResponse.nextStep.provider;
|
|
10498
|
+
stepIndex++;
|
|
10499
|
+
continue;
|
|
10500
|
+
}
|
|
10501
|
+
const finalUpdates = {
|
|
10502
|
+
lastRunAt: executedAt,
|
|
10503
|
+
runCount: (trigger.runCount || 0) + 1
|
|
10504
|
+
};
|
|
10505
|
+
if (stepSuccess) {
|
|
10506
|
+
finalUpdates.lastResult = toolResult;
|
|
10507
|
+
finalUpdates.lastError = undefined;
|
|
10508
|
+
if (trigger.schedule.type === "once") {
|
|
10509
|
+
finalUpdates.status = "completed";
|
|
10510
|
+
}
|
|
10511
|
+
} else {
|
|
10512
|
+
finalUpdates.lastError = stepError;
|
|
10513
|
+
finalUpdates.status = "failed";
|
|
10514
|
+
}
|
|
10515
|
+
await config.triggers.update(trigger.id, finalUpdates, context);
|
|
10516
|
+
if (completeResponse.webhooks && completeResponse.webhooks.length > 0) {
|
|
10517
|
+
const totalDuration = steps.reduce((sum, s) => sum + (s.duration || 0), 0);
|
|
10518
|
+
const payload = {
|
|
10519
|
+
triggerId: trigger.id,
|
|
10520
|
+
success: steps.every((s) => s.success),
|
|
10521
|
+
steps,
|
|
10522
|
+
totalSteps: steps.length,
|
|
10523
|
+
totalDuration,
|
|
10524
|
+
executedAt
|
|
10525
|
+
};
|
|
10526
|
+
deliverWebhooks(completeResponse.webhooks, payload, WEBHOOK_DELIVERY_TIMEOUT_MS).catch(() => {});
|
|
10527
|
+
}
|
|
10528
|
+
return { success: stepSuccess, steps, error: stepError };
|
|
10529
|
+
}
|
|
10530
|
+
const limitError = `Trigger execution exceeded maximum of ${MAX_TRIGGER_STEPS} steps`;
|
|
10531
|
+
logger31.error(`[Trigger ${trigger.id}] ${limitError}`);
|
|
10532
|
+
await config.triggers.update(trigger.id, {
|
|
10533
|
+
lastRunAt: new Date().toISOString(),
|
|
10534
|
+
runCount: (trigger.runCount || 0) + 1,
|
|
10535
|
+
lastError: limitError,
|
|
10536
|
+
status: "failed"
|
|
10537
|
+
}, context);
|
|
10538
|
+
return { success: false, steps, error: limitError };
|
|
10539
|
+
}
|
|
10540
|
+
var logger31;
|
|
10541
|
+
var init_executor = __esm(() => {
|
|
10542
|
+
init_logger();
|
|
10543
|
+
init_utils2();
|
|
10544
|
+
init_webhooks();
|
|
10545
|
+
logger31 = createLogger("TriggerExecutor", "server");
|
|
10546
|
+
});
|
|
10547
|
+
|
|
10340
10548
|
// src/server.ts
|
|
10341
10549
|
var exports_server = {};
|
|
10342
10550
|
__export(exports_server, {
|
|
@@ -10430,7 +10638,7 @@ function createMCPServer(config) {
|
|
|
10430
10638
|
if (integration.oauth) {
|
|
10431
10639
|
const { clientId, clientSecret, redirectUri: integrationRedirectUri, config: oauthConfig } = integration.oauth;
|
|
10432
10640
|
if (!clientId || !clientSecret) {
|
|
10433
|
-
|
|
10641
|
+
logger32.warn(`Warning: Integration "${integration.id}" is missing OAuth credentials. ` + `Provide clientId and clientSecret in the integration configuration.`);
|
|
10434
10642
|
return integration;
|
|
10435
10643
|
}
|
|
10436
10644
|
const redirectUri = integrationRedirectUri || config.redirectUri || getDefaultRedirectUri();
|
|
@@ -10561,7 +10769,7 @@ function createMCPServer(config) {
|
|
|
10561
10769
|
}
|
|
10562
10770
|
return response2;
|
|
10563
10771
|
} catch (error) {
|
|
10564
|
-
|
|
10772
|
+
logger32.error("[MCP Tool Call] Error:", error);
|
|
10565
10773
|
return Response.json({ error: error.message || "Failed to execute tool call" }, { status: error.statusCode || 500 });
|
|
10566
10774
|
}
|
|
10567
10775
|
}
|
|
@@ -10577,6 +10785,57 @@ function createMCPServer(config) {
|
|
|
10577
10785
|
}));
|
|
10578
10786
|
return Response.json({ integrations });
|
|
10579
10787
|
}
|
|
10788
|
+
if (segments.length === 2 && segments[0] === "triggers" && segments[1] === "notify" && method === "POST") {
|
|
10789
|
+
if (!config.triggers) {
|
|
10790
|
+
return Response.json({ error: "Triggers not configured. Add triggers callbacks to createMCPServer config." }, { status: 501 });
|
|
10791
|
+
}
|
|
10792
|
+
try {
|
|
10793
|
+
const apiKey = webRequest.headers.get("x-api-key");
|
|
10794
|
+
if (!apiKey || apiKey !== config.apiKey) {
|
|
10795
|
+
return Response.json({ error: "Unauthorized" }, { status: 401 });
|
|
10796
|
+
}
|
|
10797
|
+
const body = await webRequest.json();
|
|
10798
|
+
const { triggerId } = body;
|
|
10799
|
+
if (!triggerId) {
|
|
10800
|
+
return Response.json({ error: "triggerId is required" }, { status: 400 });
|
|
10801
|
+
}
|
|
10802
|
+
const trigger = await config.triggers.get(triggerId);
|
|
10803
|
+
if (!trigger) {
|
|
10804
|
+
return Response.json({ error: "Trigger not found" }, { status: 404 });
|
|
10805
|
+
}
|
|
10806
|
+
if (!trigger.provider) {
|
|
10807
|
+
return Response.json({ error: "Trigger has no provider configured" }, { status: 400 });
|
|
10808
|
+
}
|
|
10809
|
+
const triggerContext = trigger.userId ? { userId: trigger.userId } : undefined;
|
|
10810
|
+
const { executeTrigger: executeTrigger2 } = await Promise.resolve().then(() => (init_executor(), exports_executor));
|
|
10811
|
+
const { OAuthHandler: OAuthHandler2 } = await Promise.resolve().then(() => (init_base_handler(), exports_base_handler));
|
|
10812
|
+
const oauthHandler = new OAuthHandler2({
|
|
10813
|
+
providers,
|
|
10814
|
+
serverUrl: config.serverUrl,
|
|
10815
|
+
apiKey: config.apiKey,
|
|
10816
|
+
setProviderToken: config.setProviderToken,
|
|
10817
|
+
removeProviderToken: config.removeProviderToken,
|
|
10818
|
+
getSessionContext: config.getSessionContext
|
|
10819
|
+
});
|
|
10820
|
+
const executionResult = await executeTrigger2(trigger, {
|
|
10821
|
+
triggers: config.triggers,
|
|
10822
|
+
getProviderToken: async (provider, email, ctx) => {
|
|
10823
|
+
return config.getProviderToken ? await config.getProviderToken(provider, email, ctx) : undefined;
|
|
10824
|
+
},
|
|
10825
|
+
handleToolCall: (toolBody, authHeader, integrationsHeader) => {
|
|
10826
|
+
return oauthHandler.handleToolCall(toolBody, authHeader, integrationsHeader);
|
|
10827
|
+
}
|
|
10828
|
+
}, triggerContext);
|
|
10829
|
+
return Response.json({
|
|
10830
|
+
success: executionResult.success,
|
|
10831
|
+
steps: executionResult.steps,
|
|
10832
|
+
error: executionResult.error
|
|
10833
|
+
});
|
|
10834
|
+
} catch (error) {
|
|
10835
|
+
logger32.error("[Trigger Notify] Error:", error);
|
|
10836
|
+
return Response.json({ error: error.message || "Failed to execute trigger" }, { status: 500 });
|
|
10837
|
+
}
|
|
10838
|
+
}
|
|
10580
10839
|
if (segments.length >= 1 && segments[0] === "triggers") {
|
|
10581
10840
|
if (!config.triggers) {
|
|
10582
10841
|
return Response.json({ error: "Triggers not configured. Add triggers callbacks to createMCPServer config." }, { status: 501 });
|
|
@@ -10617,8 +10876,9 @@ function createMCPServer(config) {
|
|
|
10617
10876
|
};
|
|
10618
10877
|
const created = await config.triggers.create(trigger, context2);
|
|
10619
10878
|
const schedulerUrl = config.schedulerUrl || config.serverUrl || "https://mcp.integrate.dev";
|
|
10620
|
-
const
|
|
10879
|
+
const defaultCallbackBaseUrl = process.env.INTEGRATE_URL || (typeof window !== "undefined" ? window.location.origin : "http://localhost:3000");
|
|
10621
10880
|
try {
|
|
10881
|
+
const callbackBaseUrl = config.triggers.getCallbackUrl ? await config.triggers.getCallbackUrl(context2) : defaultCallbackBaseUrl;
|
|
10622
10882
|
await fetch(`${schedulerUrl}/scheduler/register`, {
|
|
10623
10883
|
method: "POST",
|
|
10624
10884
|
headers: {
|
|
@@ -10628,8 +10888,7 @@ function createMCPServer(config) {
|
|
|
10628
10888
|
body: JSON.stringify({
|
|
10629
10889
|
triggerId: created.id,
|
|
10630
10890
|
schedule: created.schedule,
|
|
10631
|
-
callbackUrl: `${callbackBaseUrl}/api/integrate/triggers
|
|
10632
|
-
completeUrl: `${callbackBaseUrl}/api/integrate/triggers/${created.id}/complete`,
|
|
10891
|
+
callbackUrl: `${callbackBaseUrl}/api/integrate/triggers/notify`,
|
|
10633
10892
|
metadata: {
|
|
10634
10893
|
userId: context2?.userId,
|
|
10635
10894
|
provider: created.provider
|
|
@@ -10637,7 +10896,7 @@ function createMCPServer(config) {
|
|
|
10637
10896
|
})
|
|
10638
10897
|
});
|
|
10639
10898
|
} catch (scheduleError) {
|
|
10640
|
-
|
|
10899
|
+
logger32.error("[Trigger] Failed to register with scheduler:", scheduleError);
|
|
10641
10900
|
}
|
|
10642
10901
|
return Response.json(created, { status: 201 });
|
|
10643
10902
|
}
|
|
@@ -10672,7 +10931,7 @@ function createMCPServer(config) {
|
|
|
10672
10931
|
body: JSON.stringify({ triggerId })
|
|
10673
10932
|
});
|
|
10674
10933
|
} catch (error) {
|
|
10675
|
-
|
|
10934
|
+
logger32.error("[Trigger] Failed to pause in scheduler:", error);
|
|
10676
10935
|
}
|
|
10677
10936
|
return Response.json(updated);
|
|
10678
10937
|
} else if (subAction === "resume" && method === "POST") {
|
|
@@ -10700,7 +10959,7 @@ function createMCPServer(config) {
|
|
|
10700
10959
|
body: JSON.stringify({ triggerId })
|
|
10701
10960
|
});
|
|
10702
10961
|
} catch (error) {
|
|
10703
|
-
|
|
10962
|
+
logger32.error("[Trigger] Failed to resume in scheduler:", error);
|
|
10704
10963
|
}
|
|
10705
10964
|
return Response.json(updated);
|
|
10706
10965
|
} else if (subAction === "run" && method === "POST") {
|
|
@@ -10711,10 +10970,7 @@ function createMCPServer(config) {
|
|
|
10711
10970
|
if (!trigger.provider) {
|
|
10712
10971
|
return Response.json({ error: "Trigger has no provider configured" }, { status: 400 });
|
|
10713
10972
|
}
|
|
10714
|
-
const
|
|
10715
|
-
if (!providerToken) {
|
|
10716
|
-
return Response.json({ error: "No OAuth token available for this trigger" }, { status: 401 });
|
|
10717
|
-
}
|
|
10973
|
+
const { executeTrigger: executeTrigger2 } = await Promise.resolve().then(() => (init_executor(), exports_executor));
|
|
10718
10974
|
const { OAuthHandler: OAuthHandler2 } = await Promise.resolve().then(() => (init_base_handler(), exports_base_handler));
|
|
10719
10975
|
const oauthHandler = new OAuthHandler2({
|
|
10720
10976
|
providers,
|
|
@@ -10724,91 +10980,23 @@ function createMCPServer(config) {
|
|
|
10724
10980
|
removeProviderToken: config.removeProviderToken,
|
|
10725
10981
|
getSessionContext: config.getSessionContext
|
|
10726
10982
|
});
|
|
10727
|
-
const
|
|
10728
|
-
|
|
10729
|
-
|
|
10730
|
-
|
|
10731
|
-
const executionResult = {
|
|
10732
|
-
success: true,
|
|
10733
|
-
result,
|
|
10734
|
-
executedAt: new Date().toISOString(),
|
|
10735
|
-
duration
|
|
10736
|
-
};
|
|
10737
|
-
await config.triggers.update(triggerId, {
|
|
10738
|
-
lastRunAt: executionResult.executedAt,
|
|
10739
|
-
runCount: (trigger.runCount || 0) + 1,
|
|
10740
|
-
lastResult: result,
|
|
10741
|
-
lastError: undefined
|
|
10742
|
-
}, context2);
|
|
10743
|
-
return Response.json(executionResult);
|
|
10744
|
-
} catch (error) {
|
|
10745
|
-
const duration = Date.now() - startTime;
|
|
10746
|
-
const executionResult = {
|
|
10747
|
-
success: false,
|
|
10748
|
-
error: error.message || "Tool execution failed",
|
|
10749
|
-
executedAt: new Date().toISOString(),
|
|
10750
|
-
duration
|
|
10751
|
-
};
|
|
10752
|
-
await config.triggers.update(triggerId, {
|
|
10753
|
-
lastRunAt: executionResult.executedAt,
|
|
10754
|
-
runCount: (trigger.runCount || 0) + 1,
|
|
10755
|
-
lastError: error.message,
|
|
10756
|
-
status: "failed"
|
|
10757
|
-
}, context2);
|
|
10758
|
-
return Response.json(executionResult, { status: 500 });
|
|
10759
|
-
}
|
|
10760
|
-
} else if (subAction === "execute" && method === "GET") {
|
|
10761
|
-
const apiKey = webRequest.headers.get("x-api-key");
|
|
10762
|
-
if (!apiKey || apiKey !== config.apiKey) {
|
|
10763
|
-
return Response.json({ error: "Unauthorized" }, { status: 401 });
|
|
10764
|
-
}
|
|
10765
|
-
const trigger = await config.triggers.get(triggerId, context2);
|
|
10766
|
-
if (!trigger) {
|
|
10767
|
-
return Response.json({ error: "Trigger not found" }, { status: 404 });
|
|
10768
|
-
}
|
|
10769
|
-
if (!trigger.provider) {
|
|
10770
|
-
return Response.json({ error: "Trigger has no provider configured" }, { status: 400 });
|
|
10771
|
-
}
|
|
10772
|
-
const providerToken = config.getProviderToken ? await config.getProviderToken(trigger.provider, undefined, context2) : undefined;
|
|
10773
|
-
if (!providerToken) {
|
|
10774
|
-
return Response.json({ error: "No OAuth token available for this trigger" }, { status: 401 });
|
|
10775
|
-
}
|
|
10776
|
-
return Response.json({
|
|
10777
|
-
trigger: {
|
|
10778
|
-
id: trigger.id,
|
|
10779
|
-
toolName: trigger.toolName,
|
|
10780
|
-
toolArguments: trigger.toolArguments,
|
|
10781
|
-
provider: trigger.provider
|
|
10983
|
+
const executionResult = await executeTrigger2(trigger, {
|
|
10984
|
+
triggers: config.triggers,
|
|
10985
|
+
getProviderToken: async (provider, email, ctx) => {
|
|
10986
|
+
return config.getProviderToken ? await config.getProviderToken(provider, email, ctx) : undefined;
|
|
10782
10987
|
},
|
|
10783
|
-
|
|
10784
|
-
|
|
10785
|
-
});
|
|
10786
|
-
} else if (subAction === "complete" && method === "POST") {
|
|
10787
|
-
const apiKey = webRequest.headers.get("x-api-key");
|
|
10788
|
-
if (!apiKey || apiKey !== config.apiKey) {
|
|
10789
|
-
return Response.json({ error: "Unauthorized" }, { status: 401 });
|
|
10790
|
-
}
|
|
10791
|
-
const body = await webRequest.json();
|
|
10792
|
-
const trigger = await config.triggers.get(triggerId, context2);
|
|
10793
|
-
if (!trigger) {
|
|
10794
|
-
return Response.json({ error: "Trigger not found" }, { status: 404 });
|
|
10795
|
-
}
|
|
10796
|
-
const updates = {
|
|
10797
|
-
lastRunAt: body.executedAt,
|
|
10798
|
-
runCount: (trigger.runCount || 0) + 1
|
|
10799
|
-
};
|
|
10800
|
-
if (body.success) {
|
|
10801
|
-
updates.lastResult = body.result;
|
|
10802
|
-
updates.lastError = undefined;
|
|
10803
|
-
if (trigger.schedule.type === "once") {
|
|
10804
|
-
updates.status = "completed";
|
|
10988
|
+
handleToolCall: (toolBody, authHeader, integrationsHeader) => {
|
|
10989
|
+
return oauthHandler.handleToolCall(toolBody, authHeader, integrationsHeader);
|
|
10805
10990
|
}
|
|
10806
|
-
}
|
|
10807
|
-
|
|
10808
|
-
|
|
10809
|
-
|
|
10810
|
-
|
|
10811
|
-
|
|
10991
|
+
}, context2);
|
|
10992
|
+
return Response.json({
|
|
10993
|
+
success: executionResult.success,
|
|
10994
|
+
result: executionResult.steps[0]?.result,
|
|
10995
|
+
executedAt: executionResult.steps[0]?.executedAt || new Date().toISOString(),
|
|
10996
|
+
duration: executionResult.steps[0]?.duration,
|
|
10997
|
+
error: executionResult.error,
|
|
10998
|
+
steps: executionResult.steps
|
|
10999
|
+
}, { status: executionResult.success ? 200 : 500 });
|
|
10812
11000
|
} else if (!subAction && method === "GET") {
|
|
10813
11001
|
const trigger = await config.triggers.get(triggerId, context2);
|
|
10814
11002
|
if (!trigger) {
|
|
@@ -10841,7 +11029,7 @@ function createMCPServer(config) {
|
|
|
10841
11029
|
})
|
|
10842
11030
|
});
|
|
10843
11031
|
} catch (error) {
|
|
10844
|
-
|
|
11032
|
+
logger32.error("[Trigger] Failed to update scheduler:", error);
|
|
10845
11033
|
}
|
|
10846
11034
|
}
|
|
10847
11035
|
return Response.json(updated);
|
|
@@ -10858,14 +11046,14 @@ function createMCPServer(config) {
|
|
|
10858
11046
|
body: JSON.stringify({ triggerId })
|
|
10859
11047
|
});
|
|
10860
11048
|
} catch (error) {
|
|
10861
|
-
|
|
11049
|
+
logger32.error("[Trigger] Failed to unregister from scheduler:", error);
|
|
10862
11050
|
}
|
|
10863
11051
|
return new Response(null, { status: 204 });
|
|
10864
11052
|
}
|
|
10865
11053
|
}
|
|
10866
11054
|
return Response.json({ error: "Invalid trigger route or method" }, { status: 404 });
|
|
10867
11055
|
} catch (error) {
|
|
10868
|
-
|
|
11056
|
+
logger32.error("[Trigger] Error:", error);
|
|
10869
11057
|
return Response.json({ error: error.message || "Failed to process trigger request" }, { status: error.statusCode || 500 });
|
|
10870
11058
|
}
|
|
10871
11059
|
}
|
|
@@ -10891,11 +11079,11 @@ function createMCPServer(config) {
|
|
|
10891
11079
|
const errorRedirectUrl = "/auth-error";
|
|
10892
11080
|
if (error) {
|
|
10893
11081
|
const errorMsg = errorDescription || error;
|
|
10894
|
-
|
|
11082
|
+
logger32.error("[OAuth Redirect] Error:", errorMsg);
|
|
10895
11083
|
return Response.redirect(new URL(`${errorRedirectUrl}?error=${encodeURIComponent(errorMsg)}`, webRequest.url));
|
|
10896
11084
|
}
|
|
10897
11085
|
if (!code || !state) {
|
|
10898
|
-
|
|
11086
|
+
logger32.error("[OAuth Redirect] Missing code or state parameter");
|
|
10899
11087
|
return Response.redirect(new URL(`${errorRedirectUrl}?error=${encodeURIComponent("Invalid OAuth callback")}`, webRequest.url));
|
|
10900
11088
|
}
|
|
10901
11089
|
let returnUrl = defaultRedirectUrl;
|
|
@@ -10971,7 +11159,7 @@ function createMCPServer(config) {
|
|
|
10971
11159
|
frontendUrl.hash = `oauth_callback=${encodeURIComponent(JSON.stringify({ code, state, tokenData }))}`;
|
|
10972
11160
|
return Response.redirect(frontendUrl);
|
|
10973
11161
|
} catch (error2) {
|
|
10974
|
-
|
|
11162
|
+
logger32.error("[OAuth Backend Callback] Error:", error2);
|
|
10975
11163
|
return Response.redirect(new URL(`${errorRedirectUrl}?error=${encodeURIComponent(error2.message || "Failed to exchange token")}`, webRequest.url));
|
|
10976
11164
|
}
|
|
10977
11165
|
} else {
|
|
@@ -11190,7 +11378,7 @@ function toSvelteKitHandler(clientOrHandlerOrOptions, _redirectOptions) {
|
|
|
11190
11378
|
}
|
|
11191
11379
|
};
|
|
11192
11380
|
}
|
|
11193
|
-
var SERVER_LOG_CONTEXT2 = "server",
|
|
11381
|
+
var SERVER_LOG_CONTEXT2 = "server", logger32, globalServerConfig = null, codeVerifierStorage, POST = async (req, context) => {
|
|
11194
11382
|
if (!globalServerConfig) {
|
|
11195
11383
|
return Response.json({ error: "OAuth not configured. Call createMCPServer() in your server initialization file first." }, { status: 500 });
|
|
11196
11384
|
}
|
|
@@ -11238,7 +11426,7 @@ var init_server = __esm(() => {
|
|
|
11238
11426
|
init_anthropic();
|
|
11239
11427
|
init_google();
|
|
11240
11428
|
init_ai();
|
|
11241
|
-
|
|
11429
|
+
logger32 = createLogger("MCPServer", SERVER_LOG_CONTEXT2);
|
|
11242
11430
|
codeVerifierStorage = new Map;
|
|
11243
11431
|
});
|
|
11244
11432
|
|
|
@@ -11589,7 +11777,7 @@ class OAuthHandler {
|
|
|
11589
11777
|
url.searchParams.set("state", authorizeRequest.state);
|
|
11590
11778
|
url.searchParams.set("code_challenge", authorizeRequest.codeChallenge);
|
|
11591
11779
|
url.searchParams.set("code_challenge_method", authorizeRequest.codeChallengeMethod);
|
|
11592
|
-
const redirectUri =
|
|
11780
|
+
const redirectUri = providerConfig.redirectUri;
|
|
11593
11781
|
if (redirectUri) {
|
|
11594
11782
|
url.searchParams.set("redirect_uri", redirectUri);
|
|
11595
11783
|
}
|
|
@@ -11701,7 +11889,7 @@ class OAuthHandler {
|
|
|
11701
11889
|
tokenType: result.tokenType,
|
|
11702
11890
|
expiresIn: result.expiresIn,
|
|
11703
11891
|
expiresAt: result.expiresAt,
|
|
11704
|
-
scopes: result.scopes
|
|
11892
|
+
scopes: result.scopes ? result.scopes.flatMap((s) => s.split(" ").filter(Boolean)) : result.scopes
|
|
11705
11893
|
};
|
|
11706
11894
|
await this.config.setProviderToken(callbackRequest.provider, tokenData, undefined, context);
|
|
11707
11895
|
} catch (error) {}
|
|
@@ -11751,11 +11939,11 @@ class OAuthHandler {
|
|
|
11751
11939
|
try {
|
|
11752
11940
|
await this.config.removeProviderToken(request.provider, undefined, context);
|
|
11753
11941
|
} catch (error) {
|
|
11754
|
-
|
|
11942
|
+
logger33.error(`Failed to delete token for ${request.provider} from database via removeProviderToken:`, error);
|
|
11755
11943
|
}
|
|
11756
11944
|
}
|
|
11757
11945
|
} catch (error) {
|
|
11758
|
-
|
|
11946
|
+
logger33.error(`Failed to extract context for disconnect:`, error);
|
|
11759
11947
|
}
|
|
11760
11948
|
}
|
|
11761
11949
|
const url = new URL("/oauth/disconnect", this.serverUrl);
|
|
@@ -11815,10 +12003,10 @@ class OAuthHandler {
|
|
|
11815
12003
|
return jsonRpcResponse.result;
|
|
11816
12004
|
}
|
|
11817
12005
|
}
|
|
11818
|
-
var SERVER_LOG_CONTEXT3 = "server",
|
|
12006
|
+
var SERVER_LOG_CONTEXT3 = "server", logger33, MCP_SERVER_URL2 = "https://mcp.integrate.dev/api/v1/mcp";
|
|
11819
12007
|
var init_base_handler = __esm(() => {
|
|
11820
12008
|
init_logger();
|
|
11821
|
-
|
|
12009
|
+
logger33 = createLogger("OAuthHandler", SERVER_LOG_CONTEXT3);
|
|
11822
12010
|
});
|
|
11823
12011
|
|
|
11824
12012
|
// src/index.ts
|
|
@@ -11831,7 +12019,7 @@ init_nextjs();
|
|
|
11831
12019
|
// src/adapters/nextjs-oauth-redirect.ts
|
|
11832
12020
|
init_logger();
|
|
11833
12021
|
var SERVER_LOG_CONTEXT4 = "server";
|
|
11834
|
-
var
|
|
12022
|
+
var logger34 = createLogger("OAuthRedirect", SERVER_LOG_CONTEXT4);
|
|
11835
12023
|
function createOAuthRedirectHandler(config) {
|
|
11836
12024
|
const defaultRedirectUrl = config?.redirectUrl || "/";
|
|
11837
12025
|
const errorRedirectUrl = config?.errorRedirectUrl || "/auth-error";
|
|
@@ -11843,11 +12031,11 @@ function createOAuthRedirectHandler(config) {
|
|
|
11843
12031
|
const errorDescription = searchParams.get("error_description");
|
|
11844
12032
|
if (error) {
|
|
11845
12033
|
const errorMsg = errorDescription || error;
|
|
11846
|
-
|
|
12034
|
+
logger34.error("[OAuth Redirect] Error:", errorMsg);
|
|
11847
12035
|
return Response.redirect(new URL(`${errorRedirectUrl}?error=${encodeURIComponent(errorMsg)}`, req.url));
|
|
11848
12036
|
}
|
|
11849
12037
|
if (!code || !state) {
|
|
11850
|
-
|
|
12038
|
+
logger34.error("[OAuth Redirect] Missing code or state parameter");
|
|
11851
12039
|
return Response.redirect(new URL(`${errorRedirectUrl}?error=${encodeURIComponent("Invalid OAuth callback")}`, req.url));
|
|
11852
12040
|
}
|
|
11853
12041
|
let returnUrl = defaultRedirectUrl;
|
|
@@ -11927,6 +12115,8 @@ init_intercom();
|
|
|
11927
12115
|
init_hubspot();
|
|
11928
12116
|
init_youtube();
|
|
11929
12117
|
init_cursor();
|
|
12118
|
+
init_utils2();
|
|
12119
|
+
init_webhooks();
|
|
11930
12120
|
init_generic();
|
|
11931
12121
|
init_messages();
|
|
11932
12122
|
init_http_session();
|
|
@@ -11989,6 +12179,7 @@ export {
|
|
|
11989
12179
|
youtubeIntegration,
|
|
11990
12180
|
whatsappIntegration,
|
|
11991
12181
|
vercelIntegration,
|
|
12182
|
+
validateStepLimit,
|
|
11992
12183
|
todoistIntegration,
|
|
11993
12184
|
toWebRequest,
|
|
11994
12185
|
toTanStackStartHandler,
|
|
@@ -12022,6 +12213,7 @@ export {
|
|
|
12022
12213
|
gcalIntegration,
|
|
12023
12214
|
fromNodeHeaders,
|
|
12024
12215
|
figmaIntegration,
|
|
12216
|
+
deliverWebhooks,
|
|
12025
12217
|
cursorIntegration,
|
|
12026
12218
|
createTanStackOAuthHandler,
|
|
12027
12219
|
createSimpleIntegration,
|
|
@@ -12032,6 +12224,7 @@ export {
|
|
|
12032
12224
|
clearClientCache,
|
|
12033
12225
|
calcomIntegration,
|
|
12034
12226
|
airtableIntegration,
|
|
12227
|
+
WEBHOOK_DELIVERY_TIMEOUT_MS,
|
|
12035
12228
|
TriggerClient,
|
|
12036
12229
|
ToolCallError,
|
|
12037
12230
|
TokenExpiredError,
|
|
@@ -12040,6 +12233,7 @@ export {
|
|
|
12040
12233
|
OAuthHandler,
|
|
12041
12234
|
MCPMethod,
|
|
12042
12235
|
MCPClientBase,
|
|
12236
|
+
MAX_TRIGGER_STEPS,
|
|
12043
12237
|
IntegrateSDKError,
|
|
12044
12238
|
HttpSessionTransport,
|
|
12045
12239
|
ConnectionError,
|