@datasynx/agentic-crm 1.0.0 → 1.1.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.
Files changed (81) hide show
  1. package/README.md +8 -1
  2. package/dist/{ask-D8iYqDAr.js → ask-CDysGnRg.js} +2 -2
  3. package/dist/{ask-D8iYqDAr.js.map → ask-CDysGnRg.js.map} +1 -1
  4. package/dist/attachments-CX2GAtsw.cjs +517 -0
  5. package/dist/attachments-CX2GAtsw.cjs.map +1 -0
  6. package/dist/attachments-D207gXfN.js +514 -0
  7. package/dist/attachments-D207gXfN.js.map +1 -0
  8. package/dist/attachments-rLa96rOK.js +514 -0
  9. package/dist/attachments-rLa96rOK.js.map +1 -0
  10. package/dist/chunk-BfDYWZQ8.cjs +32 -0
  11. package/dist/chunk-BfDYWZQ8.cjs.map +1 -0
  12. package/dist/chunk-BhUZmQg5.js +32 -0
  13. package/dist/chunk-BhUZmQg5.js.map +1 -0
  14. package/dist/chunk-ChC83jai.js +2 -0
  15. package/dist/chunk-e_w8qqtP.js +32 -0
  16. package/dist/chunk-e_w8qqtP.js.map +1 -0
  17. package/dist/cli.js +16 -15
  18. package/dist/cli.js.map +1 -1
  19. package/dist/daemon/worker.js +3 -3
  20. package/dist/email-body-BFSRa0AW.cjs +42 -0
  21. package/dist/email-body-BFSRa0AW.cjs.map +1 -0
  22. package/dist/email-body-BOd7U-D2.js +42 -0
  23. package/dist/email-body-BOd7U-D2.js.map +1 -0
  24. package/dist/{gmail-sync-DueE6tl5.js → gmail-sync-B4Iu3AQb.js} +45 -15
  25. package/dist/gmail-sync-B4Iu3AQb.js.map +1 -0
  26. package/dist/{gmail-sync-GEy3oVvw.cjs → gmail-sync-BpSVESSe.cjs} +45 -15
  27. package/dist/gmail-sync-BpSVESSe.cjs.map +1 -0
  28. package/dist/{gmail-sync-C-NmibzS.js → gmail-sync-DIbrPnTK.js} +45 -15
  29. package/dist/gmail-sync-DIbrPnTK.js.map +1 -0
  30. package/dist/{gmail-webhook-handler-kGKpbY9h.js → gmail-webhook-handler-BzOFbvgh.js} +2 -2
  31. package/dist/{gmail-webhook-handler-kGKpbY9h.js.map → gmail-webhook-handler-BzOFbvgh.js.map} +1 -1
  32. package/dist/{gmail-webhook-handler-B26COilD.js → gmail-webhook-handler-CvSDW_Js.js} +1 -1
  33. package/dist/{google-drive-sync-D1n7WKZn.js → google-drive-sync-B_I1d54Y.js} +2 -2
  34. package/dist/{google-drive-sync-D1n7WKZn.js.map → google-drive-sync-B_I1d54Y.js.map} +1 -1
  35. package/dist/html-BaeOCZKE.js +36 -0
  36. package/dist/html-BaeOCZKE.js.map +1 -0
  37. package/dist/html-CmOku6jS.cjs +47 -0
  38. package/dist/html-CmOku6jS.cjs.map +1 -0
  39. package/dist/{import-hubspot-DB4n89jy.js → import-hubspot-CTId9IGV.js} +2 -2
  40. package/dist/{import-hubspot-DB4n89jy.js.map → import-hubspot-CTId9IGV.js.map} +1 -1
  41. package/dist/{index-pY7tYXwH.d.cts → index-BAutNcAT.d.cts} +13 -9
  42. package/dist/index-BAutNcAT.d.cts.map +1 -0
  43. package/dist/{index-B0IMMrp_.d.ts → index-FzDsNSSb.d.ts} +5 -1
  44. package/dist/index-FzDsNSSb.d.ts.map +1 -0
  45. package/dist/index.d.cts +13 -9
  46. package/dist/index.d.cts.map +1 -1
  47. package/dist/index.d.ts +5 -1
  48. package/dist/index.d.ts.map +1 -1
  49. package/dist/{interactions-writer-RJB8SWf2.js → interactions-writer-B2y-73lh.js} +1 -1
  50. package/dist/{interactions-writer-DbSyI2rt.js → interactions-writer-B8XAzdqR.js} +3 -2
  51. package/dist/interactions-writer-B8XAzdqR.js.map +1 -0
  52. package/dist/{interactions-writer-a2yzBd7T.cjs → interactions-writer-BRJNrefF.cjs} +3 -2
  53. package/dist/interactions-writer-BRJNrefF.cjs.map +1 -0
  54. package/dist/{interactions-writer-BZzUIgJd.js → interactions-writer-ZQcpFOh9.js} +3 -2
  55. package/dist/interactions-writer-ZQcpFOh9.js.map +1 -0
  56. package/dist/{knowledge-base-DHNc4hVj.js → knowledge-base--063Kpa3.js} +9 -7
  57. package/dist/{knowledge-base-DHNc4hVj.js.map → knowledge-base--063Kpa3.js.map} +1 -1
  58. package/dist/mcp.cjs +44 -22
  59. package/dist/mcp.cjs.map +1 -1
  60. package/dist/mcp.js +44 -22
  61. package/dist/mcp.js.map +1 -1
  62. package/dist/{microsoft-calendar-jIu9K5zX.js → microsoft-calendar-BgVR8GDv.js} +3 -3
  63. package/dist/{microsoft-calendar-jIu9K5zX.js.map → microsoft-calendar-BgVR8GDv.js.map} +1 -1
  64. package/dist/{microsoft-sync-R_r8HL-B.js → microsoft-sync-D30_XksI.js} +3 -3
  65. package/dist/{microsoft-sync-R_r8HL-B.js.map → microsoft-sync-D30_XksI.js.map} +1 -1
  66. package/dist/{nba-mTJ4yEqD.js → nba-DwdfM93s.js} +2 -2
  67. package/dist/{nba-mTJ4yEqD.js.map → nba-DwdfM93s.js.map} +1 -1
  68. package/dist/{server-DqSMYhSA.js → server-DoRPPOeR.js} +39 -19
  69. package/dist/server-DoRPPOeR.js.map +1 -0
  70. package/dist/{transcript-watcher-0mh2ZhmH.js → transcript-watcher-BoClrJAz.js} +2 -2
  71. package/dist/{transcript-watcher-0mh2ZhmH.js.map → transcript-watcher-BoClrJAz.js.map} +1 -1
  72. package/package.json +12 -1
  73. package/dist/gmail-sync-C-NmibzS.js.map +0 -1
  74. package/dist/gmail-sync-DueE6tl5.js.map +0 -1
  75. package/dist/gmail-sync-GEy3oVvw.cjs.map +0 -1
  76. package/dist/index-B0IMMrp_.d.ts.map +0 -1
  77. package/dist/index-pY7tYXwH.d.cts.map +0 -1
  78. package/dist/interactions-writer-BZzUIgJd.js.map +0 -1
  79. package/dist/interactions-writer-DbSyI2rt.js.map +0 -1
  80. package/dist/interactions-writer-a2yzBd7T.cjs.map +0 -1
  81. package/dist/server-DqSMYhSA.js.map +0 -1
@@ -0,0 +1,32 @@
1
+ //#region src/core/chunk.ts
2
+ /**
3
+ * Split long text into overlapping chunks for embedding/indexing. Each chunk is
4
+ * at most `maxChars`; chunks overlap by `overlap` characters so a query that
5
+ * straddles a boundary still matches. Splits prefer the nearest whitespace
6
+ * before the limit to avoid cutting words mid-token. Short text returns a single
7
+ * trimmed chunk; empty/whitespace-only text returns no chunks.
8
+ */
9
+ function chunkText(text, options = {}) {
10
+ const maxChars = options.maxChars ?? 1500;
11
+ const overlap = Math.min(options.overlap ?? 150, Math.floor(maxChars / 2));
12
+ const trimmed = text.trim();
13
+ if (!trimmed) return [];
14
+ if (trimmed.length <= maxChars) return [trimmed];
15
+ const chunks = [];
16
+ let start = 0;
17
+ while (start < trimmed.length) {
18
+ let end = Math.min(start + maxChars, trimmed.length);
19
+ if (end < trimmed.length) {
20
+ const lastSpace = trimmed.lastIndexOf(" ", end);
21
+ if (lastSpace > start + maxChars / 2) end = lastSpace;
22
+ }
23
+ chunks.push(trimmed.slice(start, end).trim());
24
+ if (end >= trimmed.length) break;
25
+ start = end - overlap;
26
+ }
27
+ return chunks.filter((c) => c.length > 0);
28
+ }
29
+ //#endregion
30
+ export { chunkText };
31
+
32
+ //# sourceMappingURL=chunk-e_w8qqtP.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"chunk-e_w8qqtP.js","names":[],"sources":["../src/core/chunk.ts"],"sourcesContent":["// src/core/chunk.ts\n\nexport interface ChunkOptions {\n /** Target maximum characters per chunk. */\n maxChars?: number;\n /** Characters of overlap carried from the end of one chunk into the next. */\n overlap?: number;\n}\n\n/**\n * Split long text into overlapping chunks for embedding/indexing. Each chunk is\n * at most `maxChars`; chunks overlap by `overlap` characters so a query that\n * straddles a boundary still matches. Splits prefer the nearest whitespace\n * before the limit to avoid cutting words mid-token. Short text returns a single\n * trimmed chunk; empty/whitespace-only text returns no chunks.\n */\nexport function chunkText(text: string, options: ChunkOptions = {}): string[] {\n const maxChars = options.maxChars ?? 1500;\n const overlap = Math.min(options.overlap ?? 150, Math.floor(maxChars / 2));\n const trimmed = text.trim();\n if (!trimmed) return [];\n if (trimmed.length <= maxChars) return [trimmed];\n\n const chunks: string[] = [];\n let start = 0;\n while (start < trimmed.length) {\n let end = Math.min(start + maxChars, trimmed.length);\n // Prefer breaking on whitespace, but only if it doesn't shrink the chunk too much.\n if (end < trimmed.length) {\n const lastSpace = trimmed.lastIndexOf(\" \", end);\n if (lastSpace > start + maxChars / 2) end = lastSpace;\n }\n chunks.push(trimmed.slice(start, end).trim());\n if (end >= trimmed.length) break;\n start = end - overlap;\n }\n return chunks.filter((c) => c.length > 0);\n}\n"],"mappings":";;;;;;;;AAgBA,SAAgB,UAAU,MAAc,UAAwB,CAAC,GAAa;CAC5E,MAAM,WAAW,QAAQ,YAAY;CACrC,MAAM,UAAU,KAAK,IAAI,QAAQ,WAAW,KAAK,KAAK,MAAM,WAAW,CAAC,CAAC;CACzE,MAAM,UAAU,KAAK,KAAK;CAC1B,IAAI,CAAC,SAAS,OAAO,CAAC;CACtB,IAAI,QAAQ,UAAU,UAAU,OAAO,CAAC,OAAO;CAE/C,MAAM,SAAmB,CAAC;CAC1B,IAAI,QAAQ;CACZ,OAAO,QAAQ,QAAQ,QAAQ;EAC7B,IAAI,MAAM,KAAK,IAAI,QAAQ,UAAU,QAAQ,MAAM;EAEnD,IAAI,MAAM,QAAQ,QAAQ;GACxB,MAAM,YAAY,QAAQ,YAAY,KAAK,GAAG;GAC9C,IAAI,YAAY,QAAQ,WAAW,GAAG,MAAM;EAC9C;EACA,OAAO,KAAK,QAAQ,MAAM,OAAO,GAAG,EAAE,KAAK,CAAC;EAC5C,IAAI,OAAO,QAAQ,QAAQ;EAC3B,QAAQ,MAAM;CAChB;CACA,OAAO,OAAO,QAAQ,MAAM,EAAE,SAAS,CAAC;AAC1C"}
package/dist/cli.js CHANGED
@@ -5,12 +5,12 @@ import { i as writeJsonFile } from "./json-store-WWsFzXub.js";
5
5
  import { a as warning, i as success, n as error, r as info, t as bold } from "./colors-BG07TZQz.js";
6
6
  import { n as getSession } from "./session-store-CEa39Dxs.js";
7
7
  import { i as sessionCommand, r as readAllSessions } from "./session-BgGDyP2C.js";
8
- import { a as searchKbSimple, i as listKbArticles, n as getKbArticle, o as writeKbArticle, s as CAPABILITIES_TEXT, t as deleteKbArticle } from "./knowledge-base-DHNc4hVj.js";
8
+ import { a as searchKbSimple, i as listKbArticles, n as getKbArticle, o as writeKbArticle, s as CAPABILITIES_TEXT, t as deleteKbArticle } from "./knowledge-base--063Kpa3.js";
9
9
  import { a as restoreCommand, t as backupCommand } from "./backup-CTlIxUdO.js";
10
10
  import { n as readSyncState } from "./sync-state-DMZgzpez.js";
11
11
  import { n as readUnmatched } from "./unmatched-transcripts-DC-VQ9YS.js";
12
12
  import { t as AgentConfigSchema } from "./agent-config-zPvcqu07.js";
13
- import { n as appendInteraction, t as InteractionDedup } from "./interactions-writer-DbSyI2rt.js";
13
+ import { n as appendInteraction, t as InteractionDedup } from "./interactions-writer-B8XAzdqR.js";
14
14
  import { i as writeAuditEntry, n as getActor, r as readAuditLog, t as filterAuditLog } from "./audit-log-DNMY9mUZ.js";
15
15
  import { d as setActorRole, i as canWrite, s as getRbacConfig } from "./rbac-msmBc_tK.js";
16
16
  import { t as withJsonFile } from "./file-lock-CcHotQkZ.js";
@@ -240,10 +240,10 @@ mcpCommand.command("start").description("Start MCP server (stdio by default)").o
240
240
  if (opts.http) {
241
241
  const port = parseInt(opts.port, 10);
242
242
  console.error(info(`Starting MCP server in HTTP mode on port ${port}...`));
243
- const { startHttp } = await import("./server-DqSMYhSA.js");
243
+ const { startHttp } = await import("./server-DoRPPOeR.js");
244
244
  await startHttp(port);
245
245
  } else {
246
- const { startStdio } = await import("./server-DqSMYhSA.js");
246
+ const { startStdio } = await import("./server-DoRPPOeR.js");
247
247
  await startStdio();
248
248
  }
249
249
  });
@@ -1604,7 +1604,7 @@ const initCommand = new Command("init").description("Initialize CRM and configur
1604
1604
  });
1605
1605
  //#endregion
1606
1606
  //#region src/commands/sync.ts
1607
- const syncCommand = new Command("sync").argument("<slug>", "Customer slug to sync").description("Sync Gmail and transcripts for a customer").option("--since <date>", "Only sync emails/files after this date (YYYY-MM-DD)").option("--gmail", "Sync Gmail only").option("--transcripts", "Sync transcripts only").option("--provider <provider>", "Sync provider: gmail | microsoft | transcripts").action(async (slug, opts) => {
1607
+ const syncCommand = new Command("sync").argument("<slug>", "Customer slug to sync").description("Sync Gmail and transcripts for a customer").option("--since <date>", "Only sync emails/files after this date (YYYY-MM-DD)").option("--gmail", "Sync Gmail only").option("--transcripts", "Sync transcripts only").option("--provider <provider>", "Sync provider: gmail | microsoft | transcripts").option("--no-attachments", "Skip downloading/converting/indexing email attachments").action(async (slug, opts) => {
1608
1608
  const dataDir = process.env["DXCRM_DATA_DIR"] ?? process.cwd();
1609
1609
  const customerDir = path.join(dataDir, "customers", slug);
1610
1610
  if (!fs.existsSync(customerDir)) {
@@ -1631,13 +1631,14 @@ const syncCommand = new Command("sync").argument("<slug>", "Customer slug to syn
1631
1631
  else try {
1632
1632
  console.log(info(` Syncing Gmail for ${bold(slug)}...`));
1633
1633
  const { getGmailAuth } = await import("./gmail-auth-OComS92L.js");
1634
- const { syncGmail: doGmailSync } = await import("./gmail-sync-DueE6tl5.js");
1634
+ const { syncGmail: doGmailSync } = await import("./gmail-sync-B4Iu3AQb.js");
1635
1635
  const result = await doGmailSync({
1636
1636
  slug,
1637
1637
  dataDir,
1638
1638
  auth: await getGmailAuth(credPath, tokenPath),
1639
1639
  query: sources.gmail.query,
1640
- since
1640
+ since,
1641
+ includeAttachments: opts.attachments !== false
1641
1642
  });
1642
1643
  totalSynced += result.synced;
1643
1644
  console.log(success(` ✓ Gmail: +${result.synced} synced, ${result.skipped} skipped`));
@@ -1651,7 +1652,7 @@ const syncCommand = new Command("sync").argument("<slug>", "Customer slug to syn
1651
1652
  const token = await getMicrosoftToken(dataDir);
1652
1653
  if (!token) console.log(info(" Microsoft: no token found (.agentic/microsoft-token.json)"));
1653
1654
  else {
1654
- const { syncMicrosoft: doMsSync } = await import("./microsoft-sync-R_r8HL-B.js");
1655
+ const { syncMicrosoft: doMsSync } = await import("./microsoft-sync-D30_XksI.js");
1655
1656
  const emailResult = await doMsSync({
1656
1657
  slug,
1657
1658
  dataDir,
@@ -1660,7 +1661,7 @@ const syncCommand = new Command("sync").argument("<slug>", "Customer slug to syn
1660
1661
  });
1661
1662
  totalSynced += emailResult.synced;
1662
1663
  console.log(success(` ✓ Microsoft Email: +${emailResult.synced} synced, ${emailResult.skipped} skipped`));
1663
- const { syncMicrosoftCalendar } = await import("./microsoft-calendar-jIu9K5zX.js");
1664
+ const { syncMicrosoftCalendar } = await import("./microsoft-calendar-BgVR8GDv.js");
1664
1665
  const calResult = await syncMicrosoftCalendar({
1665
1666
  slug,
1666
1667
  dataDir,
@@ -1678,7 +1679,7 @@ const syncCommand = new Command("sync").argument("<slug>", "Customer slug to syn
1678
1679
  if (fs.existsSync(agenticSourcesPath)) try {
1679
1680
  const agenticSources = JSON.parse(fs.readFileSync(agenticSourcesPath, "utf-8"));
1680
1681
  if (agenticSources.transcripts?.enabled && agenticSources.transcripts.paths?.length) {
1681
- const { processTranscriptFile } = await import("./transcript-watcher-0mh2ZhmH.js");
1682
+ const { processTranscriptFile } = await import("./transcript-watcher-BoClrJAz.js");
1682
1683
  const exts = agenticSources.transcripts.extensions ?? [".txt", ".vtt"];
1683
1684
  let transcriptSynced = 0;
1684
1685
  for (const watchPath of agenticSources.transcripts.paths) {
@@ -1707,7 +1708,7 @@ const syncCommand = new Command("sync").argument("<slug>", "Customer slug to syn
1707
1708
  if (!accessToken) console.log(info(" Google Drive: accessToken not found in token file"));
1708
1709
  else {
1709
1710
  console.log(info(` Syncing Google Drive for ${bold(slug)}...`));
1710
- const { syncGoogleDriveFiles } = await import("./google-drive-sync-D1n7WKZn.js");
1711
+ const { syncGoogleDriveFiles } = await import("./google-drive-sync-B_I1d54Y.js");
1711
1712
  const result = await syncGoogleDriveFiles({
1712
1713
  slug,
1713
1714
  dataDir,
@@ -2229,7 +2230,7 @@ async function runImport(sourcePath, opts, dataDir) {
2229
2230
  if (opts.from === "salesforce" && opts.mode === "api") return runSalesforceApiImport(opts, dir);
2230
2231
  if (opts.from === "pipedrive" && opts.mode === "api") return runPipedriveApiImport(opts, dir);
2231
2232
  if (opts.from === "hubspot" && sourcePath && fs.existsSync(sourcePath) && fs.statSync(sourcePath).isDirectory()) {
2232
- const { runHubSpotCsvImport } = await import("./import-hubspot-DB4n89jy.js");
2233
+ const { runHubSpotCsvImport } = await import("./import-hubspot-CTId9IGV.js");
2233
2234
  const r = await runHubSpotCsvImport(sourcePath, dir, {
2234
2235
  ...opts.dryRun ? { dryRun: true } : {},
2235
2236
  ...opts.resume ? { resume: true } : {},
@@ -2745,7 +2746,7 @@ const importCommand = new Command("import").description("Import customers and in
2745
2746
  if (hs && rep) ownerMap[hs.trim()] = rep.trim();
2746
2747
  }
2747
2748
  if (opts.analyze && opts.from === "hubspot" && sourcePath) {
2748
- const { analyzeHubSpotExport } = await import("./import-hubspot-DB4n89jy.js");
2749
+ const { analyzeHubSpotExport } = await import("./import-hubspot-CTId9IGV.js");
2749
2750
  const analysis = await analyzeHubSpotExport(sourcePath);
2750
2751
  console.log(bold("\nDatasynxOpenCRM — HubSpot Import Analysis"));
2751
2752
  console.log("==========================================");
@@ -4229,7 +4230,7 @@ function dataDir$5() {
4229
4230
  return process.env["DXCRM_DATA_DIR"] ?? process.cwd();
4230
4231
  }
4231
4232
  const askCommand = new Command("ask").description("Ask your CRM a natural-language question").argument("<question>", "The question").option("--slug <slug>", "Scope to a customer").action(async (question, opts) => {
4232
- const { askCrm } = await import("./ask-D8iYqDAr.js");
4233
+ const { askCrm } = await import("./ask-CDysGnRg.js");
4233
4234
  const res = await askCrm(dataDir$5(), question, opts.slug);
4234
4235
  if (res.answer) {
4235
4236
  console.log(bold("Answer:"));
@@ -4248,7 +4249,7 @@ function dataDir$4() {
4248
4249
  return process.env["DXCRM_DATA_DIR"] ?? process.cwd();
4249
4250
  }
4250
4251
  const nbaCommand = new Command("nba").description("Next-best-action recommendations for a customer").argument("<slug>", "Customer slug").action(async (slug) => {
4251
- const { nextBestAction } = await import("./nba-mTJ4yEqD.js");
4252
+ const { nextBestAction } = await import("./nba-DwdfM93s.js");
4252
4253
  const actions = await nextBestAction(dataDir$4(), slug);
4253
4254
  if (actions.length === 0) {
4254
4255
  console.log(info("No recommendations."));