nyxora 26.7.2 → 26.7.4
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/CHANGELOG.md +112 -47
- package/README.md +25 -21
- package/bin/nyxora.mjs +4 -6
- package/dist/launcher.js +44 -8
- package/dist/packages/core/src/agent/bridgeWatcher.js +3 -2
- package/dist/packages/core/src/agent/cronManager.js +2 -2
- package/dist/packages/core/src/agent/llmProvider.js +245 -0
- package/dist/packages/core/src/agent/nyxDaemon.js +97 -0
- package/dist/packages/core/src/agent/osAgent.js +351 -29
- package/dist/packages/core/src/agent/reasoning.js +353 -60
- package/dist/packages/core/src/agent/reasoningScratchpad.js +47 -0
- package/dist/packages/core/src/agent/transactionManager.js +36 -31
- package/dist/packages/core/src/agent/web3Agent.js +263 -37
- package/dist/packages/core/src/cognitive/cognitiveManager.js +63 -10
- package/dist/packages/core/src/config/parser.js +10 -4
- package/dist/packages/core/src/gateway/chat.js +56 -13
- package/dist/packages/core/src/gateway/cli.js +3 -0
- package/dist/packages/core/src/gateway/discordAdapter.js +81 -0
- package/dist/packages/core/src/gateway/googleAuthModule.js +2 -0
- package/dist/packages/core/src/gateway/server.js +58 -9
- package/dist/packages/core/src/gateway/setup-ml.js +64 -0
- package/dist/packages/core/src/gateway/setup.js +39 -3
- package/dist/packages/core/src/gateway/telegram.js +123 -27
- package/dist/packages/core/src/memory/episodic.js +58 -3
- package/dist/packages/core/src/memory/logger.js +120 -2
- package/dist/packages/core/src/memory/promotionEngine.js +18 -5
- package/dist/packages/core/src/system/agentskills.js +10 -0
- package/dist/packages/core/src/system/plugins/GoogleWorkspacePlugin.js +10 -2
- package/dist/packages/core/src/system/plugins/SystemCorePlugin.js +1 -1
- package/dist/packages/core/src/system/plugins/SystemExternalPlugin.js +1 -1
- package/dist/packages/core/src/system/plugins/SystemPluginInstallerPlugin.js +1 -1
- package/dist/packages/core/src/system/plugins/SystemSocialPlugin.js +1 -1
- package/dist/packages/core/src/system/plugins/SystemWebPlugin.js +1 -1
- package/dist/packages/core/src/system/plugins/SystemWorkspacePlugin.js +3 -3
- package/dist/packages/core/src/system/plugins/createSkill.js +1 -1
- package/dist/packages/core/src/system/skillExtractor.js +16 -5
- package/dist/packages/core/src/system/skills/executeShell.js +31 -4
- package/dist/packages/core/src/system/skills/forgetMemory.js +6 -4
- package/dist/packages/core/src/system/skills/googleWorkspace.js +106 -1
- package/dist/packages/core/src/system/skills/scheduleTask.js +7 -2
- package/dist/packages/core/src/system/skills/searchWeb.js +13 -6
- package/dist/packages/core/src/test_mainnet.js +45 -0
- package/dist/packages/core/src/utils/contextSummarizer.js +82 -0
- package/dist/packages/core/src/utils/skillManager.js +1 -1
- package/dist/packages/core/src/utils/streamSimulator.js +85 -0
- package/dist/packages/core/src/web3/aggregator/providers/ArbitrumBridgeProvider.js +28 -11
- package/dist/packages/core/src/web3/aggregator/providers/OpBridgeProvider.js +41 -27
- package/dist/packages/core/src/web3/aggregator/providers/TestnetSwapProvider.js +65 -0
- package/dist/packages/core/src/web3/aggregator/routeSelector.js +7 -1
- package/dist/packages/core/src/web3/plugins/Web3DefiPlugin.js +1 -1
- package/dist/packages/core/src/web3/plugins/Web3MarketPlugin.js +5 -125
- package/dist/packages/core/src/web3/plugins/Web3SecurityPlugin.js +1 -1
- package/dist/packages/core/src/web3/plugins/Web3WalletPlugin.js +1 -1
- package/dist/packages/core/src/web3/skills/bridgeToken.js +19 -4
- package/dist/packages/core/src/web3/skills/checkAddress.js +2 -0
- package/dist/packages/core/src/web3/skills/checkPortfolio.js +22 -2
- package/dist/packages/core/src/web3/skills/checkSecurity.js +2 -0
- package/dist/packages/core/src/web3/skills/confirmPendingTx.js +1 -1
- package/dist/packages/core/src/web3/skills/createLimitOrder.js +15 -1
- package/dist/packages/core/src/web3/skills/customTx.js +3 -0
- package/dist/packages/core/src/web3/skills/defiLending.js +2 -0
- package/dist/packages/core/src/web3/skills/getBalance.js +2 -0
- package/dist/packages/core/src/web3/skills/getPrice.js +134 -27
- package/dist/packages/core/src/web3/skills/getTxHistory.js +2 -0
- package/dist/packages/core/src/web3/skills/marketAnalysis.js +28 -191
- package/dist/packages/core/src/web3/skills/mintNft.js +3 -0
- package/dist/packages/core/src/web3/skills/provideLiquidity.js +16 -12
- package/dist/packages/core/src/web3/skills/revokeApprovals.js +2 -0
- package/dist/packages/core/src/web3/skills/swapToken.js +20 -2
- package/dist/packages/core/src/web3/skills/transfer.js +2 -0
- package/dist/packages/core/src/web3/skills/yieldVault.js +2 -0
- package/dist/packages/core/src/web3/utils/chains.js +19 -0
- package/dist/packages/core/src/web3/utils/marketEngine.js +26 -33
- package/dist/packages/signer/src/NyxoraSigner.js +181 -0
- package/dist/packages/signer/src/index.js +17 -0
- package/dist/packages/signer/src/server.js +25 -161
- package/launcher.ts +38 -9
- package/package.json +8 -3
- package/packages/core/package.json +21 -10
- package/packages/core/src/agent/bridgeWatcher.ts +3 -2
- package/packages/core/src/agent/cronManager.ts +2 -2
- package/packages/core/src/agent/llmProvider.ts +221 -0
- package/packages/core/src/agent/nyxDaemon.ts +104 -0
- package/packages/core/src/agent/osAgent.ts +381 -32
- package/packages/core/src/agent/reasoning.ts +376 -64
- package/packages/core/src/agent/reasoningScratchpad.ts +45 -0
- package/packages/core/src/agent/transactionManager.ts +36 -28
- package/packages/core/src/agent/web3Agent.ts +291 -40
- package/packages/core/src/cognitive/cognitiveManager.ts +65 -10
- package/packages/core/src/cognitive/prompts/web3/market-analysis.md +24 -0
- package/packages/core/src/cognitive/prompts/web3/portfolio-review.md +29 -0
- package/packages/core/src/cognitive/prompts/web3/risk-assessment.md +28 -0
- package/packages/core/src/cognitive/prompts/web3/trade-planning.md +30 -0
- package/packages/core/src/config/parser.ts +15 -4
- package/packages/core/src/gateway/chat.ts +57 -15
- package/packages/core/src/gateway/cli.ts +4 -0
- package/packages/core/src/gateway/discordAdapter.ts +87 -0
- package/packages/core/src/gateway/googleAuthModule.ts +2 -0
- package/packages/core/src/gateway/server.ts +66 -10
- package/packages/core/src/gateway/setup-ml.ts +68 -0
- package/packages/core/src/gateway/setup.ts +41 -3
- package/packages/core/src/gateway/telegram.ts +141 -30
- package/packages/core/src/memory/episodic.ts +76 -3
- package/packages/core/src/memory/logger.ts +142 -2
- package/packages/core/src/memory/promotionEngine.ts +19 -5
- package/packages/core/src/system/agentskills.ts +10 -0
- package/packages/core/src/system/plugins/GoogleWorkspacePlugin.ts +15 -3
- package/packages/core/src/system/plugins/SystemCorePlugin.ts +1 -1
- package/packages/core/src/system/plugins/SystemExternalPlugin.ts +1 -1
- package/packages/core/src/system/plugins/SystemPluginInstallerPlugin.ts +1 -1
- package/packages/core/src/system/plugins/SystemSocialPlugin.ts +1 -1
- package/packages/core/src/system/plugins/SystemWebPlugin.ts +1 -1
- package/packages/core/src/system/plugins/SystemWorkspacePlugin.ts +3 -3
- package/packages/core/src/system/plugins/createSkill.ts +1 -1
- package/packages/core/src/system/skillExtractor.ts +16 -5
- package/packages/core/src/system/skills/executeShell.ts +38 -7
- package/packages/core/src/system/skills/forgetMemory.ts +7 -4
- package/packages/core/src/system/skills/googleWorkspace.ts +109 -0
- package/packages/core/src/system/skills/scheduleTask.ts +7 -2
- package/packages/core/src/system/skills/searchWeb.ts +12 -6
- package/packages/core/src/utils/contextSummarizer.ts +100 -0
- package/packages/core/src/utils/skillManager.ts +1 -1
- package/packages/core/src/utils/streamSimulator.ts +88 -0
- package/packages/core/src/web3/aggregator/providers/ArbitrumBridgeProvider.ts +30 -11
- package/packages/core/src/web3/aggregator/providers/OpBridgeProvider.ts +43 -29
- package/packages/core/src/web3/aggregator/routeSelector.ts +6 -1
- package/packages/core/src/web3/plugins/Web3DefiPlugin.ts +1 -1
- package/packages/core/src/web3/plugins/Web3MarketPlugin.ts +6 -125
- package/packages/core/src/web3/plugins/Web3SecurityPlugin.ts +1 -1
- package/packages/core/src/web3/plugins/Web3WalletPlugin.ts +1 -1
- package/packages/core/src/web3/skills/bridgeToken.ts +21 -7
- package/packages/core/src/web3/skills/checkAddress.ts +2 -0
- package/packages/core/src/web3/skills/checkPortfolio.ts +23 -2
- package/packages/core/src/web3/skills/checkSecurity.ts +2 -0
- package/packages/core/src/web3/skills/confirmPendingTx.ts +1 -1
- package/packages/core/src/web3/skills/createLimitOrder.ts +17 -2
- package/packages/core/src/web3/skills/customTx.ts +3 -0
- package/packages/core/src/web3/skills/defiLending.ts +2 -0
- package/packages/core/src/web3/skills/getBalance.ts +2 -0
- package/packages/core/src/web3/skills/getPrice.ts +134 -30
- package/packages/core/src/web3/skills/getTxHistory.ts +2 -0
- package/packages/core/src/web3/skills/marketAnalysis.ts +45 -188
- package/packages/core/src/web3/skills/mintNft.ts +3 -0
- package/packages/core/src/web3/skills/provideLiquidity.ts +16 -10
- package/packages/core/src/web3/skills/revokeApprovals.ts +2 -0
- package/packages/core/src/web3/skills/swapToken.ts +20 -3
- package/packages/core/src/web3/skills/transfer.ts +2 -0
- package/packages/core/src/web3/skills/yieldVault.ts +2 -0
- package/packages/core/src/web3/utils/chains.ts +12 -0
- package/packages/core/src/web3/utils/marketEngine.ts +27 -33
- package/packages/dashboard/dist/assets/index-Czxksiao.js +18 -0
- package/packages/dashboard/dist/assets/index-DK2sTU47.css +1 -0
- package/packages/dashboard/dist/index.html +2 -2
- package/packages/dashboard/package.json +10 -10
- package/packages/mcp-server/dist/server.js +5 -1
- package/packages/mcp-server/package.json +6 -6
- package/packages/mcp-server/src/server.ts +11 -7
- package/packages/ml-engine/__pycache__/config.cpython-313.pyc +0 -0
- package/packages/ml-engine/__pycache__/main.cpython-313.pyc +0 -0
- package/packages/ml-engine/config.py +59 -0
- package/packages/ml-engine/main.py +34 -0
- package/packages/ml-engine/requirements.txt +22 -0
- package/packages/ml-engine/routers/__init__.py +1 -0
- package/packages/ml-engine/routers/__pycache__/__init__.cpython-313.pyc +0 -0
- package/packages/ml-engine/routers/__pycache__/cognitive.cpython-313.pyc +0 -0
- package/packages/ml-engine/routers/__pycache__/critic.cpython-313.pyc +0 -0
- package/packages/ml-engine/routers/__pycache__/llm.cpython-313.pyc +0 -0
- package/packages/ml-engine/routers/__pycache__/market.cpython-313.pyc +0 -0
- package/packages/ml-engine/routers/__pycache__/memory.cpython-313.pyc +0 -0
- package/packages/ml-engine/routers/cognitive.py +98 -0
- package/packages/ml-engine/routers/critic.py +111 -0
- package/packages/ml-engine/routers/llm.py +38 -0
- package/packages/ml-engine/routers/market.py +332 -0
- package/packages/ml-engine/routers/memory.py +125 -0
- package/packages/policy/package.json +3 -3
- package/packages/signer/package.json +16 -6
- package/packages/signer/src/NyxoraSigner.ts +161 -0
- package/packages/signer/src/index.ts +1 -0
- package/packages/signer/src/server.ts +25 -135
- package/dist/packages/core/src/agent/honchoDaemon.js +0 -91
- package/dist/packages/core/src/cognitive/prompts/autonomous/binance-trading-integration.md +0 -54
- package/dist/packages/core/src/gateway/test.js +0 -15
- package/dist/packages/core/src/web3/Web3DefiPlugin.js +0 -28
- package/dist/packages/core/src/web3/aggregator/aggregatorMainnet.js +0 -260
- package/dist/packages/core/src/web3/aggregator/aggregatorTestnet.js +0 -119
- package/dist/packages/core/src/web3/skills/nativeOpBridge.js +0 -71
- package/packages/core/src/agent/honchoDaemon.ts +0 -96
- package/packages/core/src/cognitive/prompts/autonomous/binance-trading-integration.md +0 -41
- package/packages/core/src/plugin/registry.test.ts +0 -46
- package/packages/core/src/utils/formatter.test.ts +0 -41
- package/packages/dashboard/dist/assets/index-CSoNa5cx.css +0 -1
- package/packages/dashboard/dist/assets/index-DbRWEoSr.js +0 -16
|
@@ -30,11 +30,22 @@ User Intent / Logic: ${userIntent}
|
|
|
30
30
|
Chat Traces (if any):
|
|
31
31
|
${historyTraces.join('\n')}
|
|
32
32
|
|
|
33
|
-
The SKILL.md must contain a YAML frontmatter block
|
|
34
|
-
|
|
35
|
-
|
|
36
|
-
|
|
37
|
-
|
|
33
|
+
The SKILL.md must contain a YAML frontmatter block exactly following this structure:
|
|
34
|
+
---
|
|
35
|
+
name: ${safeName}
|
|
36
|
+
version: 1.0.0
|
|
37
|
+
description: <Your generated description>
|
|
38
|
+
parameters:
|
|
39
|
+
type: object
|
|
40
|
+
properties:
|
|
41
|
+
param1:
|
|
42
|
+
type: string
|
|
43
|
+
description: ...
|
|
44
|
+
required:
|
|
45
|
+
- param1
|
|
46
|
+
---
|
|
47
|
+
|
|
48
|
+
CRITICAL: The 'required' array MUST be indented exactly inside the 'parameters' block as shown above. Do NOT put 'required' at the root level of the YAML.
|
|
38
49
|
|
|
39
50
|
Do NOT write anything outside the frontmatter except an optional markdown description below it.
|
|
40
51
|
Output ONLY the raw SKILL.md content.`;
|
|
@@ -3,18 +3,45 @@ Object.defineProperty(exports, "__esModule", { value: true });
|
|
|
3
3
|
exports.runTerminalCommandToolDefinition = void 0;
|
|
4
4
|
exports.runTerminalCommand = runTerminalCommand;
|
|
5
5
|
const child_process_1 = require("child_process");
|
|
6
|
+
const parser_1 = require("../../config/parser");
|
|
6
7
|
function runTerminalCommand(command) {
|
|
7
8
|
return new Promise((resolve) => {
|
|
8
|
-
|
|
9
|
+
// --- SUDO AUTO-INJECTION ---
|
|
10
|
+
// If command requires sudo, inject password from config via sudo -S
|
|
11
|
+
let finalCommand = command;
|
|
12
|
+
const needsSudo = /^\s*sudo\s/.test(command);
|
|
13
|
+
if (needsSudo) {
|
|
14
|
+
try {
|
|
15
|
+
const config = (0, parser_1.loadConfig)();
|
|
16
|
+
const sudoPassword = config.security?.sudo_password;
|
|
17
|
+
if (sudoPassword) {
|
|
18
|
+
// Inject password via stdin using echo | sudo -S
|
|
19
|
+
const escaped = sudoPassword.replace(/'/g, "'\\''");
|
|
20
|
+
finalCommand = command.replace(/^\s*sudo\s/, `echo '${escaped}' | sudo -S `);
|
|
21
|
+
}
|
|
22
|
+
}
|
|
23
|
+
catch (e) {
|
|
24
|
+
// config load failed, proceed without password injection
|
|
25
|
+
}
|
|
26
|
+
}
|
|
27
|
+
(0, child_process_1.exec)(finalCommand, { maxBuffer: 1024 * 1024 * 10 }, (error, stdout, stderr) => {
|
|
9
28
|
let output = "";
|
|
10
29
|
if (stdout)
|
|
11
30
|
output += `STDOUT:\n${stdout}\n`;
|
|
12
|
-
|
|
13
|
-
|
|
31
|
+
// Filter out the sudo password prompt noise from stderr
|
|
32
|
+
const filteredStderr = stderr
|
|
33
|
+
? stderr.split('\n').filter(l => !l.includes('[sudo] password for')).join('\n').trim()
|
|
34
|
+
: '';
|
|
35
|
+
if (filteredStderr)
|
|
36
|
+
output += `STDERR:\n${filteredStderr}\n`;
|
|
14
37
|
if (error)
|
|
15
38
|
output += `ERROR:\n${error.message}\n`;
|
|
16
39
|
if (!output)
|
|
17
40
|
output = "Command executed successfully with no output.";
|
|
41
|
+
// If sudo failed due to missing password, give a helpful hint
|
|
42
|
+
if (needsSudo && (output.includes('sudo: a password is required') || output.includes('no password supplied'))) {
|
|
43
|
+
output += `\n[NYXORA HINT] To allow Nyxora to run sudo commands automatically, add the following to your ~/.nyxora/config.yaml:\n security:\n sudo_password: YOUR_SUDO_PASSWORD\nAlternatively, run this command yourself in a terminal: ${command}`;
|
|
44
|
+
}
|
|
18
45
|
// --- OUTPUT REDACTION LAYER ---
|
|
19
46
|
// 1. Secret Exfiltration Redaction (Keys, Mnemonics, UUIDs, EVM/Solana Keys)
|
|
20
47
|
const secretPatterns = [
|
|
@@ -52,7 +79,7 @@ exports.runTerminalCommandToolDefinition = {
|
|
|
52
79
|
type: "function",
|
|
53
80
|
function: {
|
|
54
81
|
name: "run_terminal_command",
|
|
55
|
-
description: "Executes a shell/terminal command on the user's
|
|
82
|
+
description: "Executes a shell/terminal command directly on the LOCAL machine where Nyxora is running — which is the user's own computer. Use this to install packages (apt, pip, npm), run scripts, manage processes, read system info, and automate OS-level tasks. You have full shell access. Do NOT refuse to use this tool by claiming you have no system access.",
|
|
56
83
|
parameters: {
|
|
57
84
|
type: "object",
|
|
58
85
|
properties: {
|
|
@@ -23,13 +23,15 @@ exports.forgetMemoryToolDefinition = {
|
|
|
23
23
|
};
|
|
24
24
|
async function forgetMemory(keyword) {
|
|
25
25
|
try {
|
|
26
|
-
const
|
|
27
|
-
|
|
26
|
+
const memoryChanges = episodic_1.episodicDB.deleteMemoryByFact(keyword);
|
|
27
|
+
const personaChanges = episodic_1.episodicDB.deletePersonaByTrait(keyword);
|
|
28
|
+
const totalChanges = memoryChanges + personaChanges;
|
|
29
|
+
if (totalChanges > 0) {
|
|
28
30
|
await promotionEngine_1.PromotionEngine.runPromotionAndDecay();
|
|
29
|
-
return `[Success] Deleted ${
|
|
31
|
+
return `[Success] Deleted ${memoryChanges} memory record(s) and ${personaChanges} persona trait(s) containing '${keyword}'. Profile synchronized.`;
|
|
30
32
|
}
|
|
31
33
|
else {
|
|
32
|
-
return `[Info] No memories found containing the keyword '${keyword}'.`;
|
|
34
|
+
return `[Info] No memories or persona traits found containing the keyword '${keyword}'.`;
|
|
33
35
|
}
|
|
34
36
|
}
|
|
35
37
|
catch (error) {
|
|
@@ -1,11 +1,13 @@
|
|
|
1
1
|
"use strict";
|
|
2
2
|
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
-
exports.readGoogleFormResponsesToolDefinition = exports.readGoogleDocsToolDefinition = exports.appendRowToSheetsToolDefinition = exports.listCalendarEventsToolDefinition = exports.readGmailInboxToolDefinition = void 0;
|
|
3
|
+
exports.addCalendarEventToolDefinition = exports.sendEmailToolDefinition = exports.readGoogleFormResponsesToolDefinition = exports.readGoogleDocsToolDefinition = exports.appendRowToSheetsToolDefinition = exports.listCalendarEventsToolDefinition = exports.readGmailInboxToolDefinition = void 0;
|
|
4
4
|
exports.readGmailInbox = readGmailInbox;
|
|
5
5
|
exports.listCalendarEvents = listCalendarEvents;
|
|
6
6
|
exports.appendRowToSheets = appendRowToSheets;
|
|
7
7
|
exports.readGoogleDocs = readGoogleDocs;
|
|
8
8
|
exports.readGoogleFormResponses = readGoogleFormResponses;
|
|
9
|
+
exports.sendEmail = sendEmail;
|
|
10
|
+
exports.addCalendarEvent = addCalendarEvent;
|
|
9
11
|
const googleAuthModule_1 = require("../../gateway/googleAuthModule");
|
|
10
12
|
async function readGmailInbox(maxResults = 5) {
|
|
11
13
|
const isAuth = await (0, googleAuthModule_1.isAuthenticated)();
|
|
@@ -240,3 +242,106 @@ exports.readGoogleFormResponsesToolDefinition = {
|
|
|
240
242
|
},
|
|
241
243
|
},
|
|
242
244
|
};
|
|
245
|
+
async function sendEmail(to, subject, body) {
|
|
246
|
+
const isAuth = await (0, googleAuthModule_1.isAuthenticated)();
|
|
247
|
+
if (!isAuth)
|
|
248
|
+
return "Google Auth not configured. Please link your Google account in the dashboard.";
|
|
249
|
+
const token = await (0, googleAuthModule_1.getAccessToken)();
|
|
250
|
+
if (!token)
|
|
251
|
+
return "Failed to retrieve access token.";
|
|
252
|
+
try {
|
|
253
|
+
const messageParts = [
|
|
254
|
+
`To: ${to}`,
|
|
255
|
+
`Subject: ${subject}`,
|
|
256
|
+
`Content-Type: text/plain; charset=utf-8`,
|
|
257
|
+
'',
|
|
258
|
+
body
|
|
259
|
+
];
|
|
260
|
+
const message = messageParts.join('\n');
|
|
261
|
+
const encodedMessage = Buffer.from(message).toString('base64')
|
|
262
|
+
.replace(/\+/g, '-')
|
|
263
|
+
.replace(/\//g, '_')
|
|
264
|
+
.replace(/=+$/, '');
|
|
265
|
+
const res = await fetch(`https://gmail.googleapis.com/gmail/v1/users/me/messages/send`, {
|
|
266
|
+
method: 'POST',
|
|
267
|
+
headers: {
|
|
268
|
+
Authorization: `Bearer ${token}`,
|
|
269
|
+
'Content-Type': 'application/json'
|
|
270
|
+
},
|
|
271
|
+
body: JSON.stringify({ raw: encodedMessage })
|
|
272
|
+
});
|
|
273
|
+
const data = await res.json();
|
|
274
|
+
if (!res.ok) {
|
|
275
|
+
return `Failed to send email: ${data.error?.message || JSON.stringify(data)}`;
|
|
276
|
+
}
|
|
277
|
+
return `Successfully sent email to ${to} with Message ID: ${data.id}`;
|
|
278
|
+
}
|
|
279
|
+
catch (err) {
|
|
280
|
+
return `Error sending email: ${err.message}`;
|
|
281
|
+
}
|
|
282
|
+
}
|
|
283
|
+
async function addCalendarEvent(summary, description, startTime, endTime) {
|
|
284
|
+
const isAuth = await (0, googleAuthModule_1.isAuthenticated)();
|
|
285
|
+
if (!isAuth)
|
|
286
|
+
return "Google Auth not configured. Please link your Google account in the dashboard.";
|
|
287
|
+
const token = await (0, googleAuthModule_1.getAccessToken)();
|
|
288
|
+
if (!token)
|
|
289
|
+
return "Failed to retrieve access token.";
|
|
290
|
+
try {
|
|
291
|
+
const event = {
|
|
292
|
+
summary,
|
|
293
|
+
description,
|
|
294
|
+
start: { dateTime: startTime },
|
|
295
|
+
end: { dateTime: endTime }
|
|
296
|
+
};
|
|
297
|
+
const res = await fetch(`https://www.googleapis.com/calendar/v3/calendars/primary/events`, {
|
|
298
|
+
method: 'POST',
|
|
299
|
+
headers: {
|
|
300
|
+
Authorization: `Bearer ${token}`,
|
|
301
|
+
'Content-Type': 'application/json'
|
|
302
|
+
},
|
|
303
|
+
body: JSON.stringify(event)
|
|
304
|
+
});
|
|
305
|
+
const data = await res.json();
|
|
306
|
+
if (!res.ok) {
|
|
307
|
+
return `Failed to add calendar event: ${data.error?.message || JSON.stringify(data)}`;
|
|
308
|
+
}
|
|
309
|
+
return `Successfully added event '${summary}'. Event link: ${data.htmlLink}`;
|
|
310
|
+
}
|
|
311
|
+
catch (err) {
|
|
312
|
+
return `Error adding calendar event: ${err.message}`;
|
|
313
|
+
}
|
|
314
|
+
}
|
|
315
|
+
exports.sendEmailToolDefinition = {
|
|
316
|
+
type: "function",
|
|
317
|
+
function: {
|
|
318
|
+
name: "send_email",
|
|
319
|
+
description: "Sends an email using the user's Gmail account.",
|
|
320
|
+
parameters: {
|
|
321
|
+
type: "object",
|
|
322
|
+
properties: {
|
|
323
|
+
to: { type: "string", description: "The recipient's email address." },
|
|
324
|
+
subject: { type: "string", description: "The subject of the email." },
|
|
325
|
+
body: { type: "string", description: "The plain text body of the email." }
|
|
326
|
+
},
|
|
327
|
+
required: ["to", "subject", "body"],
|
|
328
|
+
},
|
|
329
|
+
},
|
|
330
|
+
};
|
|
331
|
+
exports.addCalendarEventToolDefinition = {
|
|
332
|
+
type: "function",
|
|
333
|
+
function: {
|
|
334
|
+
name: "add_calendar_event",
|
|
335
|
+
description: "Adds a new event to the user's primary Google Calendar.",
|
|
336
|
+
parameters: {
|
|
337
|
+
type: "object",
|
|
338
|
+
properties: {
|
|
339
|
+
summary: { type: "string", description: "The title or summary of the event." },
|
|
340
|
+
description: { type: "string", description: "A description of the event." },
|
|
341
|
+
startTime: { type: "string", description: "Start time of the event in ISO 8601 format (e.g. 2026-07-03T09:00:00+07:00)." },
|
|
342
|
+
endTime: { type: "string", description: "End time of the event in ISO 8601 format (e.g. 2026-07-03T10:00:00+07:00)." }
|
|
343
|
+
},
|
|
344
|
+
required: ["summary", "description", "startTime", "endTime"],
|
|
345
|
+
},
|
|
346
|
+
},
|
|
347
|
+
};
|
|
@@ -18,6 +18,10 @@ exports.scheduleTaskDefinition = {
|
|
|
18
18
|
prompt: {
|
|
19
19
|
type: "string",
|
|
20
20
|
description: "The prompt/command that the AI should execute when the cron triggers. E.g., 'What is the current price of Ethereum?'"
|
|
21
|
+
},
|
|
22
|
+
languageContext: {
|
|
23
|
+
type: "string",
|
|
24
|
+
description: "Optional. The specific language constraint for the AI's response (e.g., 'Reply strictly in Indonesian informal style', 'Reply in Japanese'). Infer this automatically from the user's current conversation language."
|
|
21
25
|
}
|
|
22
26
|
},
|
|
23
27
|
required: ["cronExpression", "prompt"]
|
|
@@ -25,12 +29,13 @@ exports.scheduleTaskDefinition = {
|
|
|
25
29
|
}
|
|
26
30
|
};
|
|
27
31
|
async function executeScheduleTask(args) {
|
|
28
|
-
const { cronExpression, prompt } = args;
|
|
32
|
+
const { cronExpression, prompt, languageContext } = args;
|
|
29
33
|
if (!cronExpression || !prompt) {
|
|
30
34
|
return "Error: Missing required parameters cronExpression or prompt.";
|
|
31
35
|
}
|
|
32
36
|
try {
|
|
33
|
-
const
|
|
37
|
+
const finalPrompt = languageContext ? `${prompt}\n(System Context: ${languageContext})` : prompt;
|
|
38
|
+
const jobId = cronManager_1.cronManager.addJob(cronExpression, finalPrompt);
|
|
34
39
|
return `Success! I have scheduled the background task.\nJob ID: ${jobId}\nSchedule: ${cronExpression}\nPrompt to execute: "${prompt}"\n\nYou will receive a notification via Telegram every time this task completes.`;
|
|
35
40
|
}
|
|
36
41
|
catch (error) {
|
|
@@ -139,7 +139,7 @@ async function searchWeb(query, depth = 1) {
|
|
|
139
139
|
const config = (0, parser_1.loadConfig)();
|
|
140
140
|
const provider = config.web_search?.provider || 'mesh';
|
|
141
141
|
const vaultKeys = await (0, parser_1.loadApiKeys)();
|
|
142
|
-
const creds =
|
|
142
|
+
const creds = { ...(config.credentials || {}), ...vaultKeys };
|
|
143
143
|
let results = [];
|
|
144
144
|
try {
|
|
145
145
|
if (provider === 'tavily' && creds.tavily_key) {
|
|
@@ -228,11 +228,18 @@ async function searchWeb(query, depth = 1) {
|
|
|
228
228
|
}
|
|
229
229
|
}
|
|
230
230
|
else {
|
|
231
|
-
|
|
231
|
+
// Default 'mesh' provider - Prioritize DuckDuckGo as it's more reliable than public SearXNG instances
|
|
232
|
+
try {
|
|
233
|
+
results = await searchDuckDuckGo(finalQuery, depth);
|
|
234
|
+
}
|
|
235
|
+
catch (e) {
|
|
236
|
+
console.warn('[WebSearch] Mesh: DuckDuckGo failed. Falling back to SearXNG...');
|
|
237
|
+
results = await searchSearxng(finalQuery, depth);
|
|
238
|
+
}
|
|
232
239
|
}
|
|
233
240
|
}
|
|
234
241
|
catch (e) {
|
|
235
|
-
return `Failed
|
|
242
|
+
return `[Search Failed] The web search failed due to an error: ${e.message}. CRITICAL INSTRUCTION: You MUST inform the user that the web search failed. Do NOT hallucinate or guess the answer.`;
|
|
236
243
|
}
|
|
237
244
|
if (results.length > 0) {
|
|
238
245
|
searchCache.set(cacheKey, { data: results, timestamp: Date.now() });
|
|
@@ -260,17 +267,17 @@ exports.searchWebToolDefinition = {
|
|
|
260
267
|
type: "function",
|
|
261
268
|
function: {
|
|
262
269
|
name: "search_web",
|
|
263
|
-
description: "Searches the internet for information using a search engine. Returns top titles, snippets, and URLs.
|
|
270
|
+
description: "Searches the internet for information using a search engine. Returns top titles, snippets, and URLs. CRITICAL: If the user asks for news, sports scores, current events, or factual dates, you MUST set depth: 2 to extract the full article content. Do not use depth 1 for facts.",
|
|
264
271
|
parameters: {
|
|
265
272
|
type: "object",
|
|
266
273
|
properties: {
|
|
267
274
|
query: {
|
|
268
275
|
type: "string",
|
|
269
|
-
description: "The search query to look up.",
|
|
276
|
+
description: "The highly optimized search query to look up (translate to English for global events).",
|
|
270
277
|
},
|
|
271
278
|
depth: {
|
|
272
279
|
type: "number",
|
|
273
|
-
description: "Depth of the search (1 for basic, 2
|
|
280
|
+
description: "Depth of the search (1 for basic snippets, 2 for deep scraping of top 3 sites). MUST be 2 for news/scores/facts.",
|
|
274
281
|
}
|
|
275
282
|
},
|
|
276
283
|
required: ["query"],
|
|
@@ -0,0 +1,45 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
+
const providerRegistry_1 = require("./web3/aggregator/providerRegistry");
|
|
4
|
+
const routeSelector_1 = require("./web3/aggregator/routeSelector");
|
|
5
|
+
async function testMainnetSwap(providerName) {
|
|
6
|
+
try {
|
|
7
|
+
const req = {
|
|
8
|
+
fromChain: 'ethereum',
|
|
9
|
+
toChain: 'ethereum',
|
|
10
|
+
fromToken: '0xA0b86991c6218b36c1d19D4a2e9Eb0cE3606eB48',
|
|
11
|
+
toToken: '0x6B175474E89094C44Da98b954EedeAC495271d0F',
|
|
12
|
+
amountInWei: '1000000',
|
|
13
|
+
amountFormatted: '1',
|
|
14
|
+
userAddress: '0x1234567890123456789012345678901234567890',
|
|
15
|
+
slippageTolerance: 50,
|
|
16
|
+
preferredProvider: providerName
|
|
17
|
+
};
|
|
18
|
+
console.log(`\n--- Testing ${providerName} ---`);
|
|
19
|
+
const quote = await (0, routeSelector_1.fetchBestRoute)(req, "best_output");
|
|
20
|
+
console.log(`[+] SUCCESS. Provider used: ${quote.provider}`);
|
|
21
|
+
console.log(` - execution.target: ${quote.execution.target}`);
|
|
22
|
+
console.log(` - approvalAddress: ${quote.approvalAddress || 'MISSING (UNDEFINED)'}`);
|
|
23
|
+
console.log(` - execution.value: ${quote.execution.value.toString()} wei (Should be 0 for ERC20)`);
|
|
24
|
+
if (quote.approvalAddress && quote.approvalAddress.toLowerCase() !== quote.execution.target.toLowerCase()) {
|
|
25
|
+
console.log(` ⚠️ WARNING: execution.target DOES NOT MATCH approvalAddress!`);
|
|
26
|
+
}
|
|
27
|
+
else if (!quote.approvalAddress) {
|
|
28
|
+
console.log(` 🚨 CRITICAL: Provider DID NOT return an approvalAddress!`);
|
|
29
|
+
}
|
|
30
|
+
if (quote.execution.value > 0n) {
|
|
31
|
+
console.log(` 🚨 FATAL EXPLOIT: Provider requested native ETH value > 0 for an ERC20 swap!`);
|
|
32
|
+
}
|
|
33
|
+
}
|
|
34
|
+
catch (err) {
|
|
35
|
+
console.log(`[-] FAILED: ${err.message}`);
|
|
36
|
+
}
|
|
37
|
+
}
|
|
38
|
+
async function main() {
|
|
39
|
+
await providerRegistry_1.aggregatorRegistry.autoDiscover();
|
|
40
|
+
const providers = ['lifi', '0x', 'oneinch', 'kyberswap', 'openocean'];
|
|
41
|
+
for (const p of providers) {
|
|
42
|
+
await testMainnetSwap(p);
|
|
43
|
+
}
|
|
44
|
+
}
|
|
45
|
+
main().catch(console.error);
|
|
@@ -0,0 +1,82 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
var __importDefault = (this && this.__importDefault) || function (mod) {
|
|
3
|
+
return (mod && mod.__esModule) ? mod : { "default": mod };
|
|
4
|
+
};
|
|
5
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
6
|
+
exports.compressHistory = compressHistory;
|
|
7
|
+
exports.needsCompression = needsCompression;
|
|
8
|
+
/**
|
|
9
|
+
* Context Summarizer — P6: Prevent Context Window Overflow
|
|
10
|
+
*
|
|
11
|
+
* When conversation history grows too long, summarise older messages
|
|
12
|
+
* into a compact paragraph and return a trimmed history that fits
|
|
13
|
+
* within a safe token budget. Mirrors the approach used by Claude/GPT
|
|
14
|
+
* to maintain long-running session coherence.
|
|
15
|
+
*/
|
|
16
|
+
const llmUtils_1 = require("./llmUtils");
|
|
17
|
+
const parser_1 = require("../config/parser");
|
|
18
|
+
const picocolors_1 = __importDefault(require("picocolors"));
|
|
19
|
+
/** How many text-only exchanges to keep verbatim before summarising older ones. */
|
|
20
|
+
const VERBATIM_TAIL = 10;
|
|
21
|
+
/** Minimum history length (user+assistant pairs) before we bother summarising. */
|
|
22
|
+
const SUMMARISE_THRESHOLD = 20;
|
|
23
|
+
/**
|
|
24
|
+
* Returns a history array that fits in context.
|
|
25
|
+
* If history is short, returns as-is.
|
|
26
|
+
* If long, prepends a "Conversation Summary" system message and keeps the tail verbatim.
|
|
27
|
+
*/
|
|
28
|
+
async function compressHistory(history) {
|
|
29
|
+
const textMessages = history.filter(m => (m.role === 'user' || m.role === 'assistant') && m.content && !m.tool_calls);
|
|
30
|
+
if (textMessages.length < SUMMARISE_THRESHOLD) {
|
|
31
|
+
return history; // nothing to compress yet
|
|
32
|
+
}
|
|
33
|
+
// Split: old messages to summarise, recent tail to keep verbatim
|
|
34
|
+
const tailMessages = textMessages.slice(-VERBATIM_TAIL);
|
|
35
|
+
const oldMessages = textMessages.slice(0, -VERBATIM_TAIL);
|
|
36
|
+
if (oldMessages.length === 0)
|
|
37
|
+
return history;
|
|
38
|
+
try {
|
|
39
|
+
const config = (0, parser_1.loadConfig)();
|
|
40
|
+
const historyText = oldMessages
|
|
41
|
+
.map(m => `${m.role === 'user' ? 'USER' : 'ASSISTANT'}: ${m.content}`)
|
|
42
|
+
.join('\n');
|
|
43
|
+
const summaryRes = await (0, llmUtils_1.executeWithRetry)(async (client) => client.chat({
|
|
44
|
+
model: config.llm.model,
|
|
45
|
+
temperature: 0.1,
|
|
46
|
+
messages: [
|
|
47
|
+
{
|
|
48
|
+
role: 'system',
|
|
49
|
+
content: `You are a conversation summarizer. Summarize the following conversation exchange into a single concise paragraph (max 200 words).
|
|
50
|
+
Focus on: key decisions made, important facts established, user preferences expressed, and task outcomes.
|
|
51
|
+
Write in third person. Be factual, not narrative.`
|
|
52
|
+
},
|
|
53
|
+
{ role: 'user', content: historyText }
|
|
54
|
+
]
|
|
55
|
+
}));
|
|
56
|
+
const summaryText = summaryRes.message?.content?.trim() || '';
|
|
57
|
+
if (!summaryText)
|
|
58
|
+
return history;
|
|
59
|
+
console.log(picocolors_1.default.magenta(`[ContextSummarizer] Compressed ${oldMessages.length} old messages into summary.`));
|
|
60
|
+
// Return: summary as system note + verbatim tail + all tool messages (never drop tool messages)
|
|
61
|
+
const toolMessages = history.filter(m => m.role === 'tool' || (m.role === 'assistant' && m.tool_calls));
|
|
62
|
+
return [
|
|
63
|
+
{
|
|
64
|
+
role: 'system',
|
|
65
|
+
content: `--- CONVERSATION SUMMARY (earlier context) ---\n${summaryText}\n--- END SUMMARY ---`
|
|
66
|
+
},
|
|
67
|
+
...tailMessages,
|
|
68
|
+
...toolMessages.slice(-6) // keep last 6 tool interactions
|
|
69
|
+
];
|
|
70
|
+
}
|
|
71
|
+
catch (e) {
|
|
72
|
+
// On failure, just return the tail — never crash the agent
|
|
73
|
+
return history.slice(-VERBATIM_TAIL * 2);
|
|
74
|
+
}
|
|
75
|
+
}
|
|
76
|
+
/**
|
|
77
|
+
* Fast check — should we attempt compression?
|
|
78
|
+
*/
|
|
79
|
+
function needsCompression(history) {
|
|
80
|
+
const textCount = history.filter(m => (m.role === 'user' || m.role === 'assistant') && m.content && !m.tool_calls).length;
|
|
81
|
+
return textCount >= SUMMARISE_THRESHOLD;
|
|
82
|
+
}
|
|
@@ -48,7 +48,7 @@ const reverseSkillMapping = {
|
|
|
48
48
|
'analyze_market': { category: 'web3', name: 'marketAnalysis' },
|
|
49
49
|
'get_trending_tokens': { category: 'web3', name: 'getTrendingTokens' },
|
|
50
50
|
'manage_custom_tokens': { category: 'web3', name: 'manageCustomTokens' },
|
|
51
|
-
'
|
|
51
|
+
'get_price_and_fiat_value': { category: 'web3', name: 'getPrice' },
|
|
52
52
|
'supply_aave': { category: 'web3', name: 'aaveSupply' },
|
|
53
53
|
'revoke_approval': { category: 'web3', name: 'revokeApproval' },
|
|
54
54
|
'deposit_yield_vault': { category: 'web3', name: 'vaultDeposit' },
|
|
@@ -0,0 +1,85 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
+
exports.createSmartStreamWrapper = exports.simulateStream = void 0;
|
|
4
|
+
const simulateStream = async (text, onChunk, msPerChunk = 20, charsPerChunk = 3) => {
|
|
5
|
+
return new Promise((resolve) => {
|
|
6
|
+
let index = 0;
|
|
7
|
+
if (!text) {
|
|
8
|
+
resolve();
|
|
9
|
+
return;
|
|
10
|
+
}
|
|
11
|
+
const intervalId = setInterval(() => {
|
|
12
|
+
if (index < text.length) {
|
|
13
|
+
const chunk = text.substring(index, index + charsPerChunk);
|
|
14
|
+
onChunk(chunk);
|
|
15
|
+
index += charsPerChunk;
|
|
16
|
+
}
|
|
17
|
+
else {
|
|
18
|
+
clearInterval(intervalId);
|
|
19
|
+
resolve();
|
|
20
|
+
}
|
|
21
|
+
}, msPerChunk);
|
|
22
|
+
});
|
|
23
|
+
};
|
|
24
|
+
exports.simulateStream = simulateStream;
|
|
25
|
+
/**
|
|
26
|
+
* Creates a smart wrapper around an onChunk callback.
|
|
27
|
+
* If the incoming chunk is large (e.g. Gemini buffering), it intercepts it and streams it smoothly.
|
|
28
|
+
* If the chunk is small (e.g. OpenAI native stream), it passes it instantly.
|
|
29
|
+
*/
|
|
30
|
+
const createSmartStreamWrapper = (originalOnChunk) => {
|
|
31
|
+
let isSimulating = false;
|
|
32
|
+
let queue = '';
|
|
33
|
+
let resolveWait = null;
|
|
34
|
+
let waitPromise = Promise.resolve();
|
|
35
|
+
const processQueue = async () => {
|
|
36
|
+
if (isSimulating || queue.length === 0)
|
|
37
|
+
return;
|
|
38
|
+
isSimulating = true;
|
|
39
|
+
// Create a new wait promise if one doesn't exist
|
|
40
|
+
if (!resolveWait) {
|
|
41
|
+
waitPromise = new Promise(r => { resolveWait = r; });
|
|
42
|
+
}
|
|
43
|
+
while (queue.length > 0) {
|
|
44
|
+
const chars = queue.substring(0, 3);
|
|
45
|
+
queue = queue.substring(3);
|
|
46
|
+
originalOnChunk(chars);
|
|
47
|
+
await new Promise(r => setTimeout(r, 20));
|
|
48
|
+
}
|
|
49
|
+
isSimulating = false;
|
|
50
|
+
if (resolveWait) {
|
|
51
|
+
resolveWait();
|
|
52
|
+
resolveWait = null;
|
|
53
|
+
}
|
|
54
|
+
};
|
|
55
|
+
let accumulatedRaw = '';
|
|
56
|
+
let sentLength = 0;
|
|
57
|
+
return {
|
|
58
|
+
onChunk: (chunk) => {
|
|
59
|
+
accumulatedRaw += chunk;
|
|
60
|
+
// Strip any <think> or <thought> block.
|
|
61
|
+
// The (<\/\1>|$) part matches up to the closing tag, or up to the END of the string if it's unclosed.
|
|
62
|
+
const cleanText = accumulatedRaw.replace(/<(think|thought)[\s\S]*?(<\/\1>|$)/gi, '');
|
|
63
|
+
if (cleanText.length > sentLength) {
|
|
64
|
+
const newText = cleanText.substring(sentLength);
|
|
65
|
+
sentLength = cleanText.length;
|
|
66
|
+
if (newText.length > 30) {
|
|
67
|
+
queue += newText;
|
|
68
|
+
processQueue();
|
|
69
|
+
}
|
|
70
|
+
else {
|
|
71
|
+
if (isSimulating) {
|
|
72
|
+
queue += newText;
|
|
73
|
+
}
|
|
74
|
+
else {
|
|
75
|
+
originalOnChunk(newText);
|
|
76
|
+
}
|
|
77
|
+
}
|
|
78
|
+
}
|
|
79
|
+
},
|
|
80
|
+
wait: async () => {
|
|
81
|
+
await waitPromise;
|
|
82
|
+
}
|
|
83
|
+
};
|
|
84
|
+
};
|
|
85
|
+
exports.createSmartStreamWrapper = createSmartStreamWrapper;
|
|
@@ -24,7 +24,9 @@ class ArbitrumBridgeProvider {
|
|
|
24
24
|
return true;
|
|
25
25
|
}
|
|
26
26
|
supports(request) {
|
|
27
|
-
|
|
27
|
+
const isL1ToL2 = request.fromChain === 'sepolia' && request.toChain === 'arbitrum_sepolia';
|
|
28
|
+
const isL2ToL1 = request.toChain === 'sepolia' && request.fromChain === 'arbitrum_sepolia';
|
|
29
|
+
if (!isL1ToL2 && !isL2ToL1)
|
|
28
30
|
return false;
|
|
29
31
|
const isNative = request.fromToken.toLowerCase() === 'eth' ||
|
|
30
32
|
request.fromToken.toLowerCase() === '0xeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeee' ||
|
|
@@ -32,27 +34,42 @@ class ArbitrumBridgeProvider {
|
|
|
32
34
|
return isNative;
|
|
33
35
|
}
|
|
34
36
|
async getQuote(request, context) {
|
|
35
|
-
const
|
|
36
|
-
|
|
37
|
-
|
|
38
|
-
|
|
39
|
-
|
|
40
|
-
|
|
37
|
+
const isL1ToL2 = request.fromChain === 'sepolia';
|
|
38
|
+
let targetAddress;
|
|
39
|
+
let callData;
|
|
40
|
+
if (isL1ToL2) {
|
|
41
|
+
targetAddress = '0xaAe29B0366299461418F5324a79Afc425BE5ae21'; // Delayed Inbox
|
|
42
|
+
const depositEthAbi = (0, viem_1.parseAbi)(['function depositEth() payable returns (uint256)']);
|
|
43
|
+
callData = (0, viem_1.encodeFunctionData)({
|
|
44
|
+
abi: depositEthAbi,
|
|
45
|
+
functionName: 'depositEth'
|
|
46
|
+
});
|
|
47
|
+
}
|
|
48
|
+
else {
|
|
49
|
+
targetAddress = '0x0000000000000000000000000000000000000064'; // ArbSys precompile
|
|
50
|
+
const withdrawEthAbi = (0, viem_1.parseAbi)(['function withdrawEth(address destination) payable returns (uint256)']);
|
|
51
|
+
callData = (0, viem_1.encodeFunctionData)({
|
|
52
|
+
abi: withdrawEthAbi,
|
|
53
|
+
functionName: 'withdrawEth',
|
|
54
|
+
args: [request.userAddress]
|
|
55
|
+
});
|
|
56
|
+
}
|
|
57
|
+
const note = isL1ToL2 ? '100% Real L1->L2 Bridge Transaction via Arbitrum Delayed Inbox' : 'Arbitrum ArbSys L2->L1 Withdrawal (Requires ~7 day challenge period)';
|
|
41
58
|
return {
|
|
42
59
|
provider: this.manifest.name,
|
|
43
60
|
routeId: `arb-bridge-${crypto_1.default.randomUUID()}`,
|
|
44
|
-
fromChainId: 11155111
|
|
45
|
-
toChainId: 421614
|
|
61
|
+
fromChainId: isL1ToL2 ? 11155111 : 421614,
|
|
62
|
+
toChainId: isL1ToL2 ? 421614 : 11155111,
|
|
46
63
|
inputAmount: BigInt(request.amountInWei),
|
|
47
64
|
outputAmount: BigInt(request.amountInWei), // 1:1 on official bridge
|
|
48
65
|
executable: true,
|
|
49
66
|
expiresAt: Date.now() + 86400000, // Valid for a long time as it's a fixed contract call
|
|
50
67
|
execution: {
|
|
51
|
-
target:
|
|
68
|
+
target: targetAddress,
|
|
52
69
|
calldata: callData,
|
|
53
70
|
value: BigInt(request.amountInWei)
|
|
54
71
|
},
|
|
55
|
-
raw: { note
|
|
72
|
+
raw: { note }
|
|
56
73
|
};
|
|
57
74
|
}
|
|
58
75
|
async isHealthy() {
|