@lov3kaizen/agentsea-core 0.5.1 → 0.6.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/index.mjs CHANGED
@@ -88,6 +88,7 @@ __export(index_exports, {
88
88
  calculatorServer: () => calculatorServer,
89
89
  calculatorTool: () => calculatorTool,
90
90
  clientTool: () => clientTool,
91
+ codeEditTool: () => codeEditTool,
91
92
  createACPTools: () => createACPTools,
92
93
  createAnthropicProvider: () => createAnthropicProvider,
93
94
  createGeminiProvider: () => createGeminiProvider,
@@ -103,8 +104,16 @@ __export(index_exports, {
103
104
  fileListTool: () => fileListTool,
104
105
  fileReadTool: () => fileReadTool,
105
106
  fileWriteTool: () => fileWriteTool,
107
+ gitAddTool: () => gitAddTool,
108
+ gitBranchTool: () => gitBranchTool,
109
+ gitCommitTool: () => gitCommitTool,
110
+ gitDiffTool: () => gitDiffTool,
111
+ gitLogTool: () => gitLogTool,
112
+ gitStatusTool: () => gitStatusTool,
113
+ globTool: () => globTool,
106
114
  globalMetrics: () => globalMetrics,
107
115
  globalTracer: () => globalTracer,
116
+ grepTool: () => grepTool,
108
117
  httpRequestTool: () => httpRequestTool,
109
118
  hybridTool: () => hybridTool,
110
119
  mcpToolToAgenticTool: () => mcpToolToAgenticTool,
@@ -114,6 +123,7 @@ __export(index_exports, {
114
123
  n8nListWorkflowsTool: () => n8nListWorkflowsTool,
115
124
  n8nTriggerWebhookTool: () => n8nTriggerWebhookTool,
116
125
  serverTool: () => serverTool,
126
+ shellExecuteTool: () => shellExecuteTool,
117
127
  stringTransformTool: () => stringTransformTool,
118
128
  textSummaryTool: () => textSummaryTool,
119
129
  toLegacyTool: () => toLegacyTool,
@@ -1443,17 +1453,551 @@ async function pollExecutionStatus(executionId, apiKey, baseUrl, maxAttempts = 3
1443
1453
  );
1444
1454
  }
1445
1455
 
1446
- // src/tools/built-in/calculator.isomorphic.ts
1456
+ // src/tools/built-in/shell.tool.ts
1457
+ import { execSync } from "child_process";
1458
+ import { z as z7 } from "zod";
1459
+ var MAX_OUTPUT_BYTES = 100 * 1024;
1460
+ var DEFAULT_TIMEOUT_MS = 3e4;
1461
+ var MAX_TIMEOUT_MS = 12e4;
1462
+ var DANGEROUS_PATTERNS = [
1463
+ /\brm\s+-[^\s]*r[^\s]*f[^\s]*\s+\/\s*$/,
1464
+ // rm -rf /
1465
+ /\brm\s+-[^\s]*f[^\s]*r[^\s]*\s+\/\s*$/,
1466
+ // rm -fr /
1467
+ /\bmkfs\b/,
1468
+ // mkfs (format disk)
1469
+ /:(){ :\|:& };:/,
1470
+ // fork bomb
1471
+ /\bdd\b.*\bof=\/dev\//,
1472
+ // dd to device
1473
+ /\b>\s*\/dev\/sd[a-z]/,
1474
+ // redirect to raw device
1475
+ /\bchmod\s+-R\s+777\s+\//,
1476
+ // chmod -R 777 /
1477
+ /\bchown\s+-R\s+.*\s+\/\s*$/
1478
+ // chown -R ... /
1479
+ ];
1480
+ var shellExecuteTool = {
1481
+ name: "shell_execute",
1482
+ description: "Execute a shell command and return stdout/stderr. Commands are checked against a safety blocklist. Non-zero exit codes return results (not errors) since tools like grep exit 1 on no matches.",
1483
+ parameters: z7.object({
1484
+ command: z7.string().describe("The shell command to execute"),
1485
+ cwd: z7.string().optional().describe(
1486
+ "Working directory for the command (defaults to process.cwd())"
1487
+ ),
1488
+ timeout: z7.number().min(1e3).max(MAX_TIMEOUT_MS).default(DEFAULT_TIMEOUT_MS).describe("Timeout in milliseconds (default 30s, max 120s)")
1489
+ }),
1490
+ execute: (params) => {
1491
+ for (const pattern of DANGEROUS_PATTERNS) {
1492
+ if (pattern.test(params.command)) {
1493
+ throw new Error(
1494
+ `Command blocked by safety filter: matches dangerous pattern. If you need to run this command, please do so directly in your terminal.`
1495
+ );
1496
+ }
1497
+ }
1498
+ const timeout = Math.min(params.timeout, MAX_TIMEOUT_MS);
1499
+ try {
1500
+ const output = execSync(params.command, {
1501
+ cwd: params.cwd || process.cwd(),
1502
+ timeout,
1503
+ encoding: "utf8",
1504
+ maxBuffer: MAX_OUTPUT_BYTES * 2,
1505
+ // allow some headroom
1506
+ stdio: ["pipe", "pipe", "pipe"]
1507
+ });
1508
+ const truncated = output.length > MAX_OUTPUT_BYTES;
1509
+ const content = truncated ? output.slice(0, MAX_OUTPUT_BYTES) + "\n... [output truncated at 100KB]" : output;
1510
+ return Promise.resolve({
1511
+ exitCode: 0,
1512
+ stdout: content,
1513
+ stderr: "",
1514
+ truncated
1515
+ });
1516
+ } catch (error) {
1517
+ const execError = error;
1518
+ if (execError.killed || execError.signal) {
1519
+ throw new Error(`Shell execution timed out after ${timeout}ms`);
1520
+ }
1521
+ if (execError.status !== void 0 && execError.status !== null) {
1522
+ const stdout = String(execError.stdout || "");
1523
+ const stderr = String(execError.stderr || "");
1524
+ const truncated = stdout.length > MAX_OUTPUT_BYTES;
1525
+ return Promise.resolve({
1526
+ exitCode: execError.status,
1527
+ stdout: truncated ? stdout.slice(0, MAX_OUTPUT_BYTES) + "\n... [output truncated at 100KB]" : stdout,
1528
+ stderr: stderr.slice(0, MAX_OUTPUT_BYTES),
1529
+ truncated
1530
+ });
1531
+ }
1532
+ throw new Error(
1533
+ `Shell execution failed: ${execError.message || String(error)}`
1534
+ );
1535
+ }
1536
+ }
1537
+ };
1538
+
1539
+ // src/tools/built-in/code-edit.tool.ts
1540
+ import { promises as fs2 } from "fs";
1447
1541
  import { z as z8 } from "zod";
1542
+ var codeEditTool = {
1543
+ name: "code_edit",
1544
+ description: "Edit a file by replacing an exact string match with new content. Uses literal string matching (not regex). Set oldString to empty and newString to content to insert at the beginning of the file. Set newString to empty to delete the matched text.",
1545
+ parameters: z8.object({
1546
+ path: z8.string().describe("Path to the file to edit"),
1547
+ oldString: z8.string().describe(
1548
+ "The exact string to find and replace. Must match file content exactly including whitespace and indentation."
1549
+ ),
1550
+ newString: z8.string().describe(
1551
+ "The replacement string. Use empty string to delete the matched text."
1552
+ ),
1553
+ expectedReplacements: z8.number().int().min(1).default(1).describe(
1554
+ "Expected number of occurrences to replace. Fails if actual count differs. Defaults to 1."
1555
+ )
1556
+ }),
1557
+ execute: async (params) => {
1558
+ try {
1559
+ const content = await fs2.readFile(params.path, "utf8");
1560
+ if (params.oldString === "") {
1561
+ const newContent2 = params.newString + content;
1562
+ await fs2.writeFile(params.path, newContent2, "utf8");
1563
+ return {
1564
+ success: true,
1565
+ path: params.path,
1566
+ replacements: 1,
1567
+ message: "Content inserted at beginning of file"
1568
+ };
1569
+ }
1570
+ let count = 0;
1571
+ let searchFrom = 0;
1572
+ let idx = content.indexOf(params.oldString, searchFrom);
1573
+ while (idx !== -1) {
1574
+ count++;
1575
+ searchFrom = idx + params.oldString.length;
1576
+ idx = content.indexOf(params.oldString, searchFrom);
1577
+ }
1578
+ if (count === 0) {
1579
+ throw new Error(
1580
+ `String not found in ${params.path}. Make sure the oldString matches exactly, including whitespace and indentation.`
1581
+ );
1582
+ }
1583
+ if (count !== params.expectedReplacements) {
1584
+ throw new Error(
1585
+ `Expected ${params.expectedReplacements} occurrence(s) of the string, but found ${count} in ${params.path}. Provide more context in oldString to make the match unique, or set expectedReplacements to ${count}.`
1586
+ );
1587
+ }
1588
+ const newContent = content.split(params.oldString).join(params.newString);
1589
+ await fs2.writeFile(params.path, newContent, "utf8");
1590
+ return {
1591
+ success: true,
1592
+ path: params.path,
1593
+ replacements: count,
1594
+ message: `Replaced ${count} occurrence(s)`
1595
+ };
1596
+ } catch (error) {
1597
+ if (error instanceof Error) {
1598
+ throw new Error(`Code edit failed: ${error.message}`);
1599
+ }
1600
+ throw error;
1601
+ }
1602
+ }
1603
+ };
1604
+
1605
+ // src/tools/built-in/glob.tool.ts
1606
+ import { promises as fs3 } from "fs";
1607
+ import fg from "fast-glob";
1608
+ import { z as z9 } from "zod";
1609
+ var DEFAULT_IGNORE = [
1610
+ "**/node_modules/**",
1611
+ "**/dist/**",
1612
+ "**/.git/**",
1613
+ "**/.next/**",
1614
+ "**/coverage/**",
1615
+ "**/.cache/**",
1616
+ "**/build/**"
1617
+ ];
1618
+ var globTool = {
1619
+ name: "glob",
1620
+ description: "Find files matching a glob pattern. Returns file paths sorted by modification time (newest first). Ignores node_modules, dist, .git, .next, coverage, .cache, and build directories by default.",
1621
+ parameters: z9.object({
1622
+ pattern: z9.string().describe(
1623
+ 'Glob pattern to match (e.g., "**/*.ts", "src/**/*.{ts,tsx}", "*.json")'
1624
+ ),
1625
+ cwd: z9.string().optional().describe("Directory to search in (defaults to process.cwd())"),
1626
+ ignore: z9.array(z9.string()).optional().describe("Additional patterns to ignore"),
1627
+ maxResults: z9.number().int().min(1).max(1e4).default(1e3).describe("Maximum number of results to return (default 1000)")
1628
+ }),
1629
+ execute: async (params) => {
1630
+ try {
1631
+ const cwd = params.cwd || process.cwd();
1632
+ const ignorePatterns = [...DEFAULT_IGNORE, ...params.ignore || []];
1633
+ const files = await fg(params.pattern, {
1634
+ cwd,
1635
+ ignore: ignorePatterns,
1636
+ absolute: true,
1637
+ dot: false,
1638
+ onlyFiles: true
1639
+ });
1640
+ const withStats = await Promise.all(
1641
+ files.map(async (filePath) => {
1642
+ try {
1643
+ const stats = await fs3.stat(filePath);
1644
+ return { path: filePath, mtime: stats.mtimeMs };
1645
+ } catch {
1646
+ return { path: filePath, mtime: 0 };
1647
+ }
1648
+ })
1649
+ );
1650
+ withStats.sort((a, b) => b.mtime - a.mtime);
1651
+ const limited = withStats.slice(0, params.maxResults);
1652
+ return {
1653
+ files: limited.map((f) => f.path),
1654
+ count: limited.length,
1655
+ totalMatches: files.length,
1656
+ truncated: files.length > params.maxResults
1657
+ };
1658
+ } catch (error) {
1659
+ if (error instanceof Error) {
1660
+ throw new Error(`Glob failed: ${error.message}`);
1661
+ }
1662
+ throw error;
1663
+ }
1664
+ }
1665
+ };
1666
+
1667
+ // src/tools/built-in/grep.tool.ts
1668
+ import { promises as fs4 } from "fs";
1669
+ import { join as join2, relative } from "path";
1670
+ import { z as z10 } from "zod";
1671
+ var MAX_FILE_SIZE = 5 * 1024 * 1024;
1672
+ var DEFAULT_IGNORE_DIRS = /* @__PURE__ */ new Set([
1673
+ "node_modules",
1674
+ "dist",
1675
+ ".git",
1676
+ ".next",
1677
+ "coverage",
1678
+ ".cache",
1679
+ "build",
1680
+ "__pycache__",
1681
+ ".venv"
1682
+ ]);
1683
+ async function walkDir(dir, includePattern) {
1684
+ const results = [];
1685
+ const entries = await fs4.readdir(dir, { withFileTypes: true });
1686
+ for (const entry of entries) {
1687
+ if (DEFAULT_IGNORE_DIRS.has(entry.name)) continue;
1688
+ if (entry.name.startsWith(".") && entry.name !== ".env.example") continue;
1689
+ const fullPath = join2(dir, entry.name);
1690
+ if (entry.isDirectory()) {
1691
+ const subResults = await walkDir(fullPath, includePattern);
1692
+ results.push(...subResults);
1693
+ } else if (entry.isFile()) {
1694
+ if (includePattern && !includePattern.test(entry.name)) continue;
1695
+ results.push(fullPath);
1696
+ }
1697
+ }
1698
+ return results;
1699
+ }
1700
+ async function searchFile(filePath, regex, contextLines) {
1701
+ const stats = await fs4.stat(filePath);
1702
+ if (stats.size > MAX_FILE_SIZE) return [];
1703
+ const content = await fs4.readFile(filePath, "utf8");
1704
+ const lines = content.split("\n");
1705
+ const matches = [];
1706
+ for (let i = 0; i < lines.length; i++) {
1707
+ regex.lastIndex = 0;
1708
+ if (regex.test(lines[i])) {
1709
+ const match = {
1710
+ file: filePath,
1711
+ line: i + 1,
1712
+ content: lines[i]
1713
+ };
1714
+ if (contextLines > 0) {
1715
+ const beforeStart = Math.max(0, i - contextLines);
1716
+ match.contextBefore = lines.slice(beforeStart, i);
1717
+ const afterEnd = Math.min(lines.length, i + 1 + contextLines);
1718
+ match.contextAfter = lines.slice(i + 1, afterEnd);
1719
+ }
1720
+ matches.push(match);
1721
+ }
1722
+ }
1723
+ return matches;
1724
+ }
1725
+ var grepTool = {
1726
+ name: "grep",
1727
+ description: "Search for a regex pattern across files recursively. Skips files larger than 5MB and ignores common non-source directories. Returns matching lines with optional context.",
1728
+ parameters: z10.object({
1729
+ pattern: z10.string().describe("Regex pattern to search for"),
1730
+ path: z10.string().optional().describe("Directory or file to search in (defaults to process.cwd())"),
1731
+ include: z10.string().optional().describe('File name pattern to include (e.g., "*.ts", "*.{js,jsx}")'),
1732
+ caseInsensitive: z10.boolean().default(false).describe("Whether to perform case-insensitive matching"),
1733
+ contextLines: z10.number().int().min(0).max(10).default(0).describe("Number of context lines before and after each match"),
1734
+ maxResults: z10.number().int().min(1).max(1e3).default(100).describe("Maximum number of matches to return")
1735
+ }),
1736
+ execute: async (params) => {
1737
+ try {
1738
+ const searchPath = params.path || process.cwd();
1739
+ const flags = params.caseInsensitive ? "gi" : "g";
1740
+ let includePattern = null;
1741
+ if (params.include) {
1742
+ const escaped = params.include.replace(/\./g, "\\.").replace(/\*/g, ".*").replace(/\{([^}]+)\}/g, (_match, group) => {
1743
+ return `(${group.split(",").join("|")})`;
1744
+ });
1745
+ includePattern = new RegExp(`^${escaped}$`);
1746
+ }
1747
+ const stat = await fs4.stat(searchPath);
1748
+ let files;
1749
+ if (stat.isFile()) {
1750
+ files = [searchPath];
1751
+ } else {
1752
+ files = await walkDir(searchPath, includePattern);
1753
+ }
1754
+ const allMatches = [];
1755
+ for (const file of files) {
1756
+ if (allMatches.length >= params.maxResults) break;
1757
+ try {
1758
+ const matches = await searchFile(
1759
+ file,
1760
+ new RegExp(params.pattern, flags),
1761
+ params.contextLines
1762
+ );
1763
+ for (const match of matches) {
1764
+ if (allMatches.length >= params.maxResults) break;
1765
+ match.file = stat.isFile() ? match.file : relative(searchPath, match.file);
1766
+ allMatches.push(match);
1767
+ }
1768
+ } catch {
1769
+ }
1770
+ }
1771
+ return {
1772
+ matches: allMatches,
1773
+ count: allMatches.length,
1774
+ filesSearched: files.length,
1775
+ truncated: allMatches.length >= params.maxResults
1776
+ };
1777
+ } catch (error) {
1778
+ if (error instanceof Error) {
1779
+ throw new Error(`Grep failed: ${error.message}`);
1780
+ }
1781
+ throw error;
1782
+ }
1783
+ }
1784
+ };
1785
+
1786
+ // src/tools/built-in/git.tool.ts
1787
+ import { execSync as execSync2 } from "child_process";
1788
+ import { z as z11 } from "zod";
1789
+ var GIT_TIMEOUT_MS = 15e3;
1790
+ function gitExec(args, cwd) {
1791
+ return execSync2(`git ${args}`, {
1792
+ cwd: cwd || process.cwd(),
1793
+ timeout: GIT_TIMEOUT_MS,
1794
+ encoding: "utf8",
1795
+ stdio: ["pipe", "pipe", "pipe"]
1796
+ }).trim();
1797
+ }
1798
+ var gitStatusTool = {
1799
+ name: "git_status",
1800
+ description: "Show the working tree status. Returns staged, unstaged, and untracked files.",
1801
+ parameters: z11.object({
1802
+ cwd: z11.string().optional().describe("Repository directory")
1803
+ }),
1804
+ execute: (params) => {
1805
+ try {
1806
+ const output = gitExec("status --porcelain", params.cwd);
1807
+ const branch = gitExec("branch --show-current", params.cwd);
1808
+ const staged = [];
1809
+ const unstaged = [];
1810
+ const untracked = [];
1811
+ for (const line of output.split("\n")) {
1812
+ if (!line.trim()) continue;
1813
+ const index = line[0];
1814
+ const worktree = line[1];
1815
+ const file = line.slice(3);
1816
+ if (index === "?") {
1817
+ untracked.push(file);
1818
+ } else {
1819
+ if (index !== " " && index !== "?") staged.push(file);
1820
+ if (worktree !== " " && worktree !== "?") unstaged.push(file);
1821
+ }
1822
+ }
1823
+ return Promise.resolve({
1824
+ branch,
1825
+ staged,
1826
+ unstaged,
1827
+ untracked,
1828
+ clean: staged.length === 0 && unstaged.length === 0 && untracked.length === 0,
1829
+ raw: output
1830
+ });
1831
+ } catch (error) {
1832
+ if (error instanceof Error) {
1833
+ throw new Error(`Git status failed: ${error.message}`);
1834
+ }
1835
+ throw error;
1836
+ }
1837
+ }
1838
+ };
1839
+ var gitDiffTool = {
1840
+ name: "git_diff",
1841
+ description: "Show changes between commits, commit and working tree, etc.",
1842
+ parameters: z11.object({
1843
+ staged: z11.boolean().default(false).describe("Show staged changes (--cached)"),
1844
+ path: z11.string().optional().describe("Limit diff to specific path"),
1845
+ cwd: z11.string().optional().describe("Repository directory")
1846
+ }),
1847
+ execute: (params) => {
1848
+ try {
1849
+ let args = "diff";
1850
+ if (params.staged) args += " --cached";
1851
+ if (params.path) args += ` -- ${params.path}`;
1852
+ const output = gitExec(args, params.cwd);
1853
+ return Promise.resolve({
1854
+ diff: output,
1855
+ hasChanges: output.length > 0
1856
+ });
1857
+ } catch (error) {
1858
+ if (error instanceof Error) {
1859
+ throw new Error(`Git diff failed: ${error.message}`);
1860
+ }
1861
+ throw error;
1862
+ }
1863
+ }
1864
+ };
1865
+ var gitAddTool = {
1866
+ name: "git_add",
1867
+ description: "Add file contents to the staging area.",
1868
+ parameters: z11.object({
1869
+ paths: z11.array(z11.string()).min(1).describe("Files to add to staging"),
1870
+ cwd: z11.string().optional().describe("Repository directory")
1871
+ }),
1872
+ execute: (params) => {
1873
+ try {
1874
+ const escapedPaths = params.paths.map((p) => `"${p}"`).join(" ");
1875
+ gitExec(`add ${escapedPaths}`, params.cwd);
1876
+ return Promise.resolve({
1877
+ success: true,
1878
+ added: params.paths
1879
+ });
1880
+ } catch (error) {
1881
+ if (error instanceof Error) {
1882
+ throw new Error(`Git add failed: ${error.message}`);
1883
+ }
1884
+ throw error;
1885
+ }
1886
+ }
1887
+ };
1888
+ var gitCommitTool = {
1889
+ name: "git_commit",
1890
+ description: "Record changes to the repository.",
1891
+ parameters: z11.object({
1892
+ message: z11.string().min(1).describe("Commit message"),
1893
+ cwd: z11.string().optional().describe("Repository directory")
1894
+ }),
1895
+ execute: (params) => {
1896
+ try {
1897
+ const safeMessage = params.message.replace(/'/g, "'\\''");
1898
+ const output = gitExec(`commit -m '${safeMessage}'`, params.cwd);
1899
+ return Promise.resolve({
1900
+ success: true,
1901
+ output
1902
+ });
1903
+ } catch (error) {
1904
+ if (error instanceof Error) {
1905
+ throw new Error(`Git commit failed: ${error.message}`);
1906
+ }
1907
+ throw error;
1908
+ }
1909
+ }
1910
+ };
1911
+ var gitLogTool = {
1912
+ name: "git_log",
1913
+ description: "Show commit logs.",
1914
+ parameters: z11.object({
1915
+ maxCount: z11.number().int().min(1).max(100).default(10).describe("Maximum number of commits to show"),
1916
+ oneline: z11.boolean().default(true).describe("Show each commit on a single line"),
1917
+ path: z11.string().optional().describe("Limit to commits affecting this path"),
1918
+ cwd: z11.string().optional().describe("Repository directory")
1919
+ }),
1920
+ execute: (params) => {
1921
+ try {
1922
+ let args = `log -${params.maxCount}`;
1923
+ if (params.oneline) {
1924
+ args += " --oneline";
1925
+ } else {
1926
+ args += " --format=%H%n%an%n%ae%n%ai%n%s%n---";
1927
+ }
1928
+ if (params.path) args += ` -- ${params.path}`;
1929
+ const output = gitExec(args, params.cwd);
1930
+ if (params.oneline) {
1931
+ const commits = output.split("\n").filter(Boolean).map((line) => {
1932
+ const spaceIdx = line.indexOf(" ");
1933
+ return {
1934
+ hash: line.slice(0, spaceIdx),
1935
+ message: line.slice(spaceIdx + 1)
1936
+ };
1937
+ });
1938
+ return Promise.resolve({ commits, count: commits.length });
1939
+ }
1940
+ return Promise.resolve({ log: output });
1941
+ } catch (error) {
1942
+ if (error instanceof Error) {
1943
+ throw new Error(`Git log failed: ${error.message}`);
1944
+ }
1945
+ throw error;
1946
+ }
1947
+ }
1948
+ };
1949
+ var gitBranchTool = {
1950
+ name: "git_branch",
1951
+ description: "List, create, or switch branches.",
1952
+ parameters: z11.object({
1953
+ action: z11.enum(["list", "create", "switch"]).default("list").describe("Action to perform"),
1954
+ name: z11.string().optional().describe("Branch name (required for create/switch)"),
1955
+ cwd: z11.string().optional().describe("Repository directory")
1956
+ }),
1957
+ execute: (params) => {
1958
+ try {
1959
+ switch (params.action) {
1960
+ case "list": {
1961
+ const output = gitExec("branch -a", params.cwd);
1962
+ const current = gitExec("branch --show-current", params.cwd);
1963
+ const branches = output.split("\n").filter(Boolean).map((b) => b.replace(/^\*?\s+/, "").trim());
1964
+ return Promise.resolve({ branches, current });
1965
+ }
1966
+ case "create": {
1967
+ if (!params.name) {
1968
+ throw new Error("Branch name is required for create action");
1969
+ }
1970
+ gitExec(`branch ${params.name}`, params.cwd);
1971
+ return Promise.resolve({ success: true, created: params.name });
1972
+ }
1973
+ case "switch": {
1974
+ if (!params.name) {
1975
+ throw new Error("Branch name is required for switch action");
1976
+ }
1977
+ gitExec(`checkout ${params.name}`, params.cwd);
1978
+ return Promise.resolve({ success: true, switched: params.name });
1979
+ }
1980
+ }
1981
+ } catch (error) {
1982
+ if (error instanceof Error) {
1983
+ throw new Error(`Git branch failed: ${error.message}`);
1984
+ }
1985
+ throw error;
1986
+ }
1987
+ }
1988
+ };
1989
+
1990
+ // src/tools/built-in/calculator.isomorphic.ts
1991
+ import { z as z13 } from "zod";
1448
1992
 
1449
1993
  // src/tools/tool-definition.ts
1450
- import { z as z7 } from "zod";
1994
+ import { z as z12 } from "zod";
1451
1995
  function toolDefinition(options) {
1452
1996
  const {
1453
1997
  name,
1454
1998
  description,
1455
1999
  inputSchema,
1456
- outputSchema = z7.unknown(),
2000
+ outputSchema = z12.unknown(),
1457
2001
  needsApproval = false,
1458
2002
  retryConfig
1459
2003
  } = options;
@@ -1561,13 +2105,13 @@ function toLegacyTools(tools) {
1561
2105
  }
1562
2106
 
1563
2107
  // src/tools/built-in/calculator.isomorphic.ts
1564
- var calculatorInputSchema = z8.object({
1565
- operation: z8.enum(["add", "subtract", "multiply", "divide"]).describe("The arithmetic operation to perform"),
1566
- a: z8.number().describe("First number"),
1567
- b: z8.number().describe("Second number")
2108
+ var calculatorInputSchema = z13.object({
2109
+ operation: z13.enum(["add", "subtract", "multiply", "divide"]).describe("The arithmetic operation to perform"),
2110
+ a: z13.number().describe("First number"),
2111
+ b: z13.number().describe("Second number")
1568
2112
  });
1569
- var calculatorOutputSchema = z8.object({
1570
- result: z8.number().describe("The result of the calculation")
2113
+ var calculatorOutputSchema = z13.object({
2114
+ result: z13.number().describe("The result of the calculation")
1571
2115
  });
1572
2116
  var calculatorDef = toolDefinition({
1573
2117
  name: "calculator",
@@ -2525,6 +3069,24 @@ function createProvider(config) {
2525
3069
  case "gemini":
2526
3070
  provider = new GeminiProvider();
2527
3071
  break;
3072
+ case "mistral":
3073
+ provider = new OpenAICompatibleProvider({
3074
+ baseUrl: "https://api.mistral.ai/v1",
3075
+ apiKey: process.env.MISTRAL_API_KEY
3076
+ });
3077
+ break;
3078
+ case "deepseek":
3079
+ provider = new OpenAICompatibleProvider({
3080
+ baseUrl: "https://api.deepseek.com/v1",
3081
+ apiKey: process.env.DEEPSEEK_API_KEY
3082
+ });
3083
+ break;
3084
+ case "xai":
3085
+ provider = new OpenAICompatibleProvider({
3086
+ baseUrl: "https://api.x.ai/v1",
3087
+ apiKey: process.env.XAI_API_KEY
3088
+ });
3089
+ break;
2528
3090
  case "ollama":
2529
3091
  provider = new OllamaProvider();
2530
3092
  break;
@@ -4088,7 +4650,7 @@ var MCPClient = class extends EventEmitter2 {
4088
4650
  };
4089
4651
 
4090
4652
  // src/mcp/tool-adapter.ts
4091
- import { z as z9 } from "zod";
4653
+ import { z as z14 } from "zod";
4092
4654
  function mcpToolToAgenticTool(mcpTool, client) {
4093
4655
  const zodSchema = jsonSchemaToZod(mcpTool.inputSchema);
4094
4656
  return {
@@ -4123,25 +4685,25 @@ function jsonSchemaToZod(schema) {
4123
4685
  let zodType;
4124
4686
  switch (propSchema.type) {
4125
4687
  case "string":
4126
- zodType = z9.string();
4688
+ zodType = z14.string();
4127
4689
  if (typeof propSchema.description === "string") {
4128
4690
  zodType = zodType.describe(propSchema.description);
4129
4691
  }
4130
4692
  break;
4131
4693
  case "number":
4132
- zodType = z9.number();
4694
+ zodType = z14.number();
4133
4695
  if (typeof propSchema.description === "string") {
4134
4696
  zodType = zodType.describe(propSchema.description);
4135
4697
  }
4136
4698
  break;
4137
4699
  case "boolean":
4138
- zodType = z9.boolean();
4700
+ zodType = z14.boolean();
4139
4701
  if (typeof propSchema.description === "string") {
4140
4702
  zodType = zodType.describe(propSchema.description);
4141
4703
  }
4142
4704
  break;
4143
4705
  case "array":
4144
- zodType = z9.array(
4706
+ zodType = z14.array(
4145
4707
  jsonSchemaToZod(
4146
4708
  propSchema.items || {}
4147
4709
  )
@@ -4154,7 +4716,7 @@ function jsonSchemaToZod(schema) {
4154
4716
  zodType = jsonSchemaToZod(propSchema);
4155
4717
  break;
4156
4718
  default:
4157
- zodType = z9.any();
4719
+ zodType = z14.any();
4158
4720
  }
4159
4721
  const required = schema.required;
4160
4722
  if (!required?.includes(key)) {
@@ -4162,9 +4724,9 @@ function jsonSchemaToZod(schema) {
4162
4724
  }
4163
4725
  shape[key] = zodType;
4164
4726
  }
4165
- return z9.object(shape);
4727
+ return z14.object(shape);
4166
4728
  }
4167
- return z9.any();
4729
+ return z14.any();
4168
4730
  }
4169
4731
 
4170
4732
  // src/mcp/registry.ts
@@ -4561,7 +5123,7 @@ var ACPClient = class {
4561
5123
  };
4562
5124
 
4563
5125
  // src/acp/tools.ts
4564
- import { z as z10 } from "zod";
5126
+ import { z as z15 } from "zod";
4565
5127
  function createACPTools(client) {
4566
5128
  return [
4567
5129
  createSearchProductsTool(client),
@@ -4584,15 +5146,15 @@ function createSearchProductsTool(client) {
4584
5146
  return {
4585
5147
  name: "acp_search_products",
4586
5148
  description: "Search for products in the commerce catalog. Supports filtering by query text, category, price range, and sorting.",
4587
- parameters: z10.object({
4588
- query: z10.string().optional().describe("Search query text"),
4589
- category: z10.string().optional().describe("Product category filter"),
4590
- minPrice: z10.number().optional().describe("Minimum price filter"),
4591
- maxPrice: z10.number().optional().describe("Maximum price filter"),
4592
- limit: z10.number().optional().default(10).describe("Maximum number of results"),
4593
- offset: z10.number().optional().default(0).describe("Pagination offset"),
4594
- sortBy: z10.enum(["price", "name", "popularity", "newest"]).optional().describe("Sort field"),
4595
- sortOrder: z10.enum(["asc", "desc"]).optional().default("asc").describe("Sort order")
5149
+ parameters: z15.object({
5150
+ query: z15.string().optional().describe("Search query text"),
5151
+ category: z15.string().optional().describe("Product category filter"),
5152
+ minPrice: z15.number().optional().describe("Minimum price filter"),
5153
+ maxPrice: z15.number().optional().describe("Maximum price filter"),
5154
+ limit: z15.number().optional().default(10).describe("Maximum number of results"),
5155
+ offset: z15.number().optional().default(0).describe("Pagination offset"),
5156
+ sortBy: z15.enum(["price", "name", "popularity", "newest"]).optional().describe("Sort field"),
5157
+ sortOrder: z15.enum(["asc", "desc"]).optional().default("asc").describe("Sort order")
4596
5158
  }),
4597
5159
  execute: async (params) => {
4598
5160
  const response = await client.searchProducts(params);
@@ -4611,8 +5173,8 @@ function createGetProductTool(client) {
4611
5173
  return {
4612
5174
  name: "acp_get_product",
4613
5175
  description: "Get detailed information about a specific product by its ID.",
4614
- parameters: z10.object({
4615
- productId: z10.string().describe("Product ID")
5176
+ parameters: z15.object({
5177
+ productId: z15.string().describe("Product ID")
4616
5178
  }),
4617
5179
  execute: async (params) => {
4618
5180
  const response = await client.getProduct(params.productId);
@@ -4627,7 +5189,7 @@ function createCreateCartTool(client) {
4627
5189
  return {
4628
5190
  name: "acp_create_cart",
4629
5191
  description: "Create a new shopping cart for the customer. Returns the cart ID for subsequent operations.",
4630
- parameters: z10.object({}),
5192
+ parameters: z15.object({}),
4631
5193
  execute: async () => {
4632
5194
  const response = await client.createCart();
4633
5195
  if (response.error) {
@@ -4641,14 +5203,14 @@ function createAddToCartTool(client) {
4641
5203
  return {
4642
5204
  name: "acp_add_to_cart",
4643
5205
  description: "Add a product to the shopping cart with specified quantity.",
4644
- parameters: z10.object({
4645
- cartId: z10.string().describe("Cart ID"),
4646
- productId: z10.string().describe("Product ID to add"),
4647
- variantId: z10.string().optional().describe("Product variant ID"),
4648
- quantity: z10.number().min(1).describe("Quantity to add"),
4649
- price: z10.object({
4650
- amount: z10.number().describe("Price amount"),
4651
- currency: z10.string().describe("Currency code (e.g., USD, EUR)")
5206
+ parameters: z15.object({
5207
+ cartId: z15.string().describe("Cart ID"),
5208
+ productId: z15.string().describe("Product ID to add"),
5209
+ variantId: z15.string().optional().describe("Product variant ID"),
5210
+ quantity: z15.number().min(1).describe("Quantity to add"),
5211
+ price: z15.object({
5212
+ amount: z15.number().describe("Price amount"),
5213
+ currency: z15.string().describe("Currency code (e.g., USD, EUR)")
4652
5214
  }).describe("Product price")
4653
5215
  }),
4654
5216
  execute: async (params) => {
@@ -4671,10 +5233,10 @@ function createUpdateCartItemTool(client) {
4671
5233
  return {
4672
5234
  name: "acp_update_cart_item",
4673
5235
  description: "Update the quantity of an item in the shopping cart.",
4674
- parameters: z10.object({
4675
- cartId: z10.string().describe("Cart ID"),
4676
- productId: z10.string().describe("Product ID to update"),
4677
- quantity: z10.number().min(0).describe("New quantity (0 to remove)")
5236
+ parameters: z15.object({
5237
+ cartId: z15.string().describe("Cart ID"),
5238
+ productId: z15.string().describe("Product ID to update"),
5239
+ quantity: z15.number().min(0).describe("New quantity (0 to remove)")
4678
5240
  }),
4679
5241
  execute: async (params) => {
4680
5242
  const response = await client.updateCartItem(
@@ -4695,9 +5257,9 @@ function createRemoveFromCartTool(client) {
4695
5257
  return {
4696
5258
  name: "acp_remove_from_cart",
4697
5259
  description: "Remove a product from the shopping cart.",
4698
- parameters: z10.object({
4699
- cartId: z10.string().describe("Cart ID"),
4700
- productId: z10.string().describe("Product ID to remove")
5260
+ parameters: z15.object({
5261
+ cartId: z15.string().describe("Cart ID"),
5262
+ productId: z15.string().describe("Product ID to remove")
4701
5263
  }),
4702
5264
  execute: async (params) => {
4703
5265
  const response = await client.removeFromCart(
@@ -4717,8 +5279,8 @@ function createGetCartTool(client) {
4717
5279
  return {
4718
5280
  name: "acp_get_cart",
4719
5281
  description: "Get the current state of a shopping cart including all items and total amount.",
4720
- parameters: z10.object({
4721
- cartId: z10.string().describe("Cart ID")
5282
+ parameters: z15.object({
5283
+ cartId: z15.string().describe("Cart ID")
4722
5284
  }),
4723
5285
  execute: async (params) => {
4724
5286
  const response = await client.getCart(params.cartId);
@@ -4733,12 +5295,12 @@ function createCheckoutTool(client) {
4733
5295
  return {
4734
5296
  name: "acp_create_checkout",
4735
5297
  description: "Create a checkout session from a shopping cart to begin the purchase process.",
4736
- parameters: z10.object({
4737
- cartId: z10.string().describe("Cart ID"),
4738
- customer: z10.object({
4739
- email: z10.string().email().describe("Customer email"),
4740
- name: z10.string().optional().describe("Customer name"),
4741
- phone: z10.string().optional().describe("Customer phone number")
5298
+ parameters: z15.object({
5299
+ cartId: z15.string().describe("Cart ID"),
5300
+ customer: z15.object({
5301
+ email: z15.string().email().describe("Customer email"),
5302
+ name: z15.string().optional().describe("Customer name"),
5303
+ phone: z15.string().optional().describe("Customer phone number")
4742
5304
  }).optional().describe("Customer information")
4743
5305
  }),
4744
5306
  execute: async (params) => {
@@ -4759,15 +5321,15 @@ function createUpdateShippingAddressTool(client) {
4759
5321
  return {
4760
5322
  name: "acp_update_shipping_address",
4761
5323
  description: "Update the shipping address for a checkout session.",
4762
- parameters: z10.object({
4763
- sessionId: z10.string().describe("Checkout session ID"),
4764
- address: z10.object({
4765
- line1: z10.string().describe("Address line 1"),
4766
- line2: z10.string().optional().describe("Address line 2"),
4767
- city: z10.string().describe("City"),
4768
- state: z10.string().optional().describe("State/Province"),
4769
- postalCode: z10.string().describe("Postal/ZIP code"),
4770
- country: z10.string().describe("Country code (e.g., US, GB)")
5324
+ parameters: z15.object({
5325
+ sessionId: z15.string().describe("Checkout session ID"),
5326
+ address: z15.object({
5327
+ line1: z15.string().describe("Address line 1"),
5328
+ line2: z15.string().optional().describe("Address line 2"),
5329
+ city: z15.string().describe("City"),
5330
+ state: z15.string().optional().describe("State/Province"),
5331
+ postalCode: z15.string().describe("Postal/ZIP code"),
5332
+ country: z15.string().describe("Country code (e.g., US, GB)")
4771
5333
  }).describe("Shipping address")
4772
5334
  }),
4773
5335
  execute: async (params) => {
@@ -4788,12 +5350,12 @@ function createUpdatePaymentMethodTool(client) {
4788
5350
  return {
4789
5351
  name: "acp_update_payment_method",
4790
5352
  description: "Update the payment method for a checkout session.",
4791
- parameters: z10.object({
4792
- sessionId: z10.string().describe("Checkout session ID"),
4793
- paymentMethod: z10.object({
4794
- type: z10.enum(["card", "delegated", "wallet", "bank_transfer"]).describe("Payment method type"),
4795
- token: z10.string().optional().describe("Payment token"),
4796
- delegatedProvider: z10.string().optional().describe("Delegated payment provider (e.g., stripe, paypal)")
5353
+ parameters: z15.object({
5354
+ sessionId: z15.string().describe("Checkout session ID"),
5355
+ paymentMethod: z15.object({
5356
+ type: z15.enum(["card", "delegated", "wallet", "bank_transfer"]).describe("Payment method type"),
5357
+ token: z15.string().optional().describe("Payment token"),
5358
+ delegatedProvider: z15.string().optional().describe("Delegated payment provider (e.g., stripe, paypal)")
4797
5359
  }).describe("Payment method details")
4798
5360
  }),
4799
5361
  execute: async (params) => {
@@ -4814,8 +5376,8 @@ function createCompleteCheckoutTool(client) {
4814
5376
  return {
4815
5377
  name: "acp_complete_checkout",
4816
5378
  description: "Complete the checkout process and create an order. This finalizes the purchase.",
4817
- parameters: z10.object({
4818
- sessionId: z10.string().describe("Checkout session ID")
5379
+ parameters: z15.object({
5380
+ sessionId: z15.string().describe("Checkout session ID")
4819
5381
  }),
4820
5382
  execute: async (params) => {
4821
5383
  const response = await client.completeCheckout(params.sessionId);
@@ -4832,8 +5394,8 @@ function createGetOrderTool(client) {
4832
5394
  return {
4833
5395
  name: "acp_get_order",
4834
5396
  description: "Get detailed information about an order by its ID.",
4835
- parameters: z10.object({
4836
- orderId: z10.string().describe("Order ID")
5397
+ parameters: z15.object({
5398
+ orderId: z15.string().describe("Order ID")
4837
5399
  }),
4838
5400
  execute: async (params) => {
4839
5401
  const response = await client.getOrder(params.orderId);
@@ -4848,8 +5410,8 @@ function createCancelOrderTool(client) {
4848
5410
  return {
4849
5411
  name: "acp_cancel_order",
4850
5412
  description: "Cancel an order. Only orders that have not been shipped can be cancelled.",
4851
- parameters: z10.object({
4852
- orderId: z10.string().describe("Order ID")
5413
+ parameters: z15.object({
5414
+ orderId: z15.string().describe("Order ID")
4853
5415
  }),
4854
5416
  execute: async (params) => {
4855
5417
  const response = await client.cancelOrder(params.orderId);
@@ -4864,8 +5426,8 @@ function createGetOrderTrackingTool(client) {
4864
5426
  return {
4865
5427
  name: "acp_get_order_tracking",
4866
5428
  description: "Get shipping tracking information for an order.",
4867
- parameters: z10.object({
4868
- orderId: z10.string().describe("Order ID")
5429
+ parameters: z15.object({
5430
+ orderId: z15.string().describe("Order ID")
4869
5431
  }),
4870
5432
  execute: async (params) => {
4871
5433
  const response = await client.getOrderTracking(params.orderId);
@@ -5190,7 +5752,7 @@ import {
5190
5752
 
5191
5753
  // src/voice/voice-agent.ts
5192
5754
  import { writeFileSync } from "fs";
5193
- import { join as join2 } from "path";
5755
+ import { join as join3 } from "path";
5194
5756
  var VoiceAgent = class {
5195
5757
  agent;
5196
5758
  sttProvider;
@@ -5354,10 +5916,10 @@ var VoiceAgent = class {
5354
5916
  exportConversation(outputDir) {
5355
5917
  for (let i = 0; i < this.conversationHistory.length; i++) {
5356
5918
  const message = this.conversationHistory[i];
5357
- const textPath = join2(outputDir, `${i}-${message.role}.txt`);
5919
+ const textPath = join3(outputDir, `${i}-${message.role}.txt`);
5358
5920
  writeFileSync(textPath, message.text);
5359
5921
  if (message.audio) {
5360
- const audioPath = join2(outputDir, `${i}-${message.role}.mp3`);
5922
+ const audioPath = join3(outputDir, `${i}-${message.role}.mp3`);
5361
5923
  writeFileSync(audioPath, message.audio);
5362
5924
  }
5363
5925
  }
@@ -5578,7 +6140,7 @@ var OpenAIWhisperProvider = class {
5578
6140
  import { exec } from "child_process";
5579
6141
  import { writeFileSync as writeFileSync2, unlinkSync, existsSync } from "fs";
5580
6142
  import { tmpdir } from "os";
5581
- import { join as join3 } from "path";
6143
+ import { join as join4 } from "path";
5582
6144
  import { promisify } from "util";
5583
6145
  var execAsync = promisify(exec);
5584
6146
  var LocalWhisperProvider = class {
@@ -5596,7 +6158,7 @@ var LocalWhisperProvider = class {
5596
6158
  let isTemporary = false;
5597
6159
  try {
5598
6160
  if (Buffer.isBuffer(audio)) {
5599
- audioPath = join3(tmpdir(), `audio-${Date.now()}.wav`);
6161
+ audioPath = join4(tmpdir(), `audio-${Date.now()}.wav`);
5600
6162
  writeFileSync2(audioPath, audio);
5601
6163
  isTemporary = true;
5602
6164
  } else {
@@ -5963,7 +6525,7 @@ var ElevenLabsTTSProvider = class {
5963
6525
  import { exec as exec2 } from "child_process";
5964
6526
  import { writeFileSync as writeFileSync3, readFileSync, unlinkSync as unlinkSync2, existsSync as existsSync2 } from "fs";
5965
6527
  import { tmpdir as tmpdir2 } from "os";
5966
- import { join as join4 } from "path";
6528
+ import { join as join5 } from "path";
5967
6529
  import { promisify as promisify2 } from "util";
5968
6530
  var execAsync2 = promisify2(exec2);
5969
6531
  var PiperTTSProvider = class {
@@ -5980,13 +6542,13 @@ var PiperTTSProvider = class {
5980
6542
  */
5981
6543
  async synthesize(text, config) {
5982
6544
  try {
5983
- const outputPath = join4(tmpdir2(), `speech-${Date.now()}.wav`);
6545
+ const outputPath = join5(tmpdir2(), `speech-${Date.now()}.wav`);
5984
6546
  const model = this.modelPath || config?.model;
5985
6547
  if (!model) {
5986
6548
  throw new Error("Model path is required for Piper TTS");
5987
6549
  }
5988
6550
  const modelConfig = this.configPath || model.replace(".onnx", ".json");
5989
- const textPath = join4(tmpdir2(), `text-${Date.now()}.txt`);
6551
+ const textPath = join5(tmpdir2(), `text-${Date.now()}.txt`);
5990
6552
  writeFileSync3(textPath, text, "utf-8");
5991
6553
  const command = `${this.piperPath} --model ${model} --config ${modelConfig} --output_file ${outputPath} < ${textPath}`;
5992
6554
  await execAsync2(command, {
@@ -6548,6 +7110,7 @@ export {
6548
7110
  calculatorServer,
6549
7111
  calculatorTool,
6550
7112
  clientTool,
7113
+ codeEditTool,
6551
7114
  createACPTools,
6552
7115
  createAnthropicProvider,
6553
7116
  createGeminiProvider,
@@ -6563,8 +7126,16 @@ export {
6563
7126
  fileListTool,
6564
7127
  fileReadTool,
6565
7128
  fileWriteTool,
7129
+ gitAddTool,
7130
+ gitBranchTool,
7131
+ gitCommitTool,
7132
+ gitDiffTool,
7133
+ gitLogTool,
7134
+ gitStatusTool,
7135
+ globTool,
6566
7136
  globalMetrics,
6567
7137
  globalTracer,
7138
+ grepTool,
6568
7139
  httpRequestTool,
6569
7140
  hybridTool,
6570
7141
  mcpToolToAgenticTool,
@@ -6574,6 +7145,7 @@ export {
6574
7145
  n8nListWorkflowsTool,
6575
7146
  n8nTriggerWebhookTool,
6576
7147
  serverTool,
7148
+ shellExecuteTool,
6577
7149
  stringTransformTool,
6578
7150
  textSummaryTool,
6579
7151
  toLegacyTool,