@prbe.ai/electron-sdk 0.1.6 → 0.1.7

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.d.mts CHANGED
@@ -1,5 +1,5 @@
1
- import { P as PRBEToolDeclaration, a as PRBEToolParameter, b as PRBEInteractionRequester, F as FlaggedFileIn, c as PRBEAgentState, d as PRBEAgentConfig, I as InvestigationSource, e as InteractionPayload, f as InteractionResponse, g as PollResponse, T as TicketInfoOut } from './types-DHT-JxMT.mjs';
2
- export { A as API_URL, h as AskQuestionPayload, i as AskQuestionResponse, C as ContextRequestOut, D as DEFAULT_PRBE_STATE, j as InteractionType, k as InvestigationResult, M as MIDDLEWARE_URL, l as PRBEAgentConfigKey, m as PRBEAgentError, n as PRBEAgentErrorType, o as PRBEAgentStatus, p as PRBEAgentStatusType, q as PRBECRInvestigation, r as PRBECompletedInvestigation, s as PRBEInteractionHandler, t as PRBESerializedCR, u as PRBESerializedCompletedInvestigation, v as PRBESerializedState, w as PRBESerializedTicket, x as PRBEStateEvent, y as PRBEStatusEvent, z as PollRequest, R as RequestPathAccessPayload, B as RequestPathAccessResponse, E as RequestPermissionPayload, G as RequestPermissionResponse, H as ResolvedInteraction, J as TicketInfoRequest, K as TicketInfoResponse, L as TicketStatusOut, N as ToolName, O as ToolParamType, W as WSMessage, Q as WSMessageType, S as redactPII, U as serializePRBEState } from './types-DHT-JxMT.mjs';
1
+ import { P as PRBEToolDeclaration, a as PRBEToolParameter, b as PRBEInteractionRequester, F as FlaggedFileIn, c as PRBEAgentState, d as PRBEAgentConfig, I as InvestigationSource, e as InteractionPayload, f as InteractionResponse, g as PollResponse, T as TicketInfoOut } from './types-CwYRJCG0.mjs';
2
+ export { A as API_URL, h as AskQuestionPayload, i as AskQuestionResponse, C as ContextRequestOut, D as DEFAULT_PRBE_STATE, j as InteractionType, k as InvestigationResult, M as MIDDLEWARE_URL, l as PRBEAgentConfigKey, m as PRBEAgentError, n as PRBEAgentErrorType, o as PRBEAgentStatus, p as PRBEAgentStatusType, q as PRBECRInvestigation, r as PRBECompletedInvestigation, s as PRBEInteractionHandler, t as PRBESerializedCR, u as PRBESerializedCompletedInvestigation, v as PRBESerializedState, w as PRBESerializedTicket, x as PRBEStateEvent, y as PRBEStatusEvent, z as PollRequest, R as RequestPathAccessPayload, B as RequestPathAccessResponse, E as RequestPermissionPayload, G as RequestPermissionResponse, H as ResolvedInteraction, J as TicketInfoRequest, K as TicketInfoResponse, L as TicketStatusOut, N as ToolName, O as ToolParamType, W as WSMessage, Q as WSMessageType, S as redactPII, U as serializePRBEState } from './types-CwYRJCG0.mjs';
3
3
  import 'events';
4
4
 
5
5
  /**
@@ -144,6 +144,7 @@ declare class PRBEAgent implements PRBEInteractionRequester {
144
144
  private fetchAbortController;
145
145
  private currentInvestigationSource;
146
146
  private currentCRId;
147
+ private readonly historyStore;
147
148
  /** Files flagged during the current tool call — uploaded immediately after the tool returns. */
148
149
  private pendingFlaggedFiles;
149
150
  private get agentID();
package/dist/index.d.ts CHANGED
@@ -1,5 +1,5 @@
1
- import { P as PRBEToolDeclaration, a as PRBEToolParameter, b as PRBEInteractionRequester, F as FlaggedFileIn, c as PRBEAgentState, d as PRBEAgentConfig, I as InvestigationSource, e as InteractionPayload, f as InteractionResponse, g as PollResponse, T as TicketInfoOut } from './types-DHT-JxMT.js';
2
- export { A as API_URL, h as AskQuestionPayload, i as AskQuestionResponse, C as ContextRequestOut, D as DEFAULT_PRBE_STATE, j as InteractionType, k as InvestigationResult, M as MIDDLEWARE_URL, l as PRBEAgentConfigKey, m as PRBEAgentError, n as PRBEAgentErrorType, o as PRBEAgentStatus, p as PRBEAgentStatusType, q as PRBECRInvestigation, r as PRBECompletedInvestigation, s as PRBEInteractionHandler, t as PRBESerializedCR, u as PRBESerializedCompletedInvestigation, v as PRBESerializedState, w as PRBESerializedTicket, x as PRBEStateEvent, y as PRBEStatusEvent, z as PollRequest, R as RequestPathAccessPayload, B as RequestPathAccessResponse, E as RequestPermissionPayload, G as RequestPermissionResponse, H as ResolvedInteraction, J as TicketInfoRequest, K as TicketInfoResponse, L as TicketStatusOut, N as ToolName, O as ToolParamType, W as WSMessage, Q as WSMessageType, S as redactPII, U as serializePRBEState } from './types-DHT-JxMT.js';
1
+ import { P as PRBEToolDeclaration, a as PRBEToolParameter, b as PRBEInteractionRequester, F as FlaggedFileIn, c as PRBEAgentState, d as PRBEAgentConfig, I as InvestigationSource, e as InteractionPayload, f as InteractionResponse, g as PollResponse, T as TicketInfoOut } from './types-CwYRJCG0.js';
2
+ export { A as API_URL, h as AskQuestionPayload, i as AskQuestionResponse, C as ContextRequestOut, D as DEFAULT_PRBE_STATE, j as InteractionType, k as InvestigationResult, M as MIDDLEWARE_URL, l as PRBEAgentConfigKey, m as PRBEAgentError, n as PRBEAgentErrorType, o as PRBEAgentStatus, p as PRBEAgentStatusType, q as PRBECRInvestigation, r as PRBECompletedInvestigation, s as PRBEInteractionHandler, t as PRBESerializedCR, u as PRBESerializedCompletedInvestigation, v as PRBESerializedState, w as PRBESerializedTicket, x as PRBEStateEvent, y as PRBEStatusEvent, z as PollRequest, R as RequestPathAccessPayload, B as RequestPathAccessResponse, E as RequestPermissionPayload, G as RequestPermissionResponse, H as ResolvedInteraction, J as TicketInfoRequest, K as TicketInfoResponse, L as TicketStatusOut, N as ToolName, O as ToolParamType, W as WSMessage, Q as WSMessageType, S as redactPII, U as serializePRBEState } from './types-CwYRJCG0.js';
3
3
  import 'events';
4
4
 
5
5
  /**
@@ -144,6 +144,7 @@ declare class PRBEAgent implements PRBEInteractionRequester {
144
144
  private fetchAbortController;
145
145
  private currentInvestigationSource;
146
146
  private currentCRId;
147
+ private readonly historyStore;
147
148
  /** Files flagged during the current tool call — uploaded immediately after the tool returns. */
148
149
  private pendingFlaggedFiles;
149
150
  private get agentID();
package/dist/index.js CHANGED
@@ -69,9 +69,9 @@ __export(src_exports, {
69
69
  module.exports = __toCommonJS(src_exports);
70
70
 
71
71
  // src/agent.ts
72
- var fs2 = __toESM(require("fs"));
73
- var path4 = __toESM(require("path"));
74
- var os = __toESM(require("os"));
72
+ var fs3 = __toESM(require("fs"));
73
+ var path5 = __toESM(require("path"));
74
+ var os2 = __toESM(require("os"));
75
75
  var import_crypto5 = require("crypto");
76
76
 
77
77
  // src/models.ts
@@ -250,7 +250,7 @@ var PRBEAgentState = class extends import_events.EventEmitter {
250
250
  this.emit("status" /* STATUS */);
251
251
  }
252
252
  }
253
- completeInvestigation(report, summary) {
253
+ completeInvestigation(report, summary, ticketId) {
254
254
  if (this.events.length > 0) {
255
255
  this.events[this.events.length - 1].isCompleted = true;
256
256
  }
@@ -260,6 +260,9 @@ var PRBEAgentState = class extends import_events.EventEmitter {
260
260
  query: this.currentQuery,
261
261
  report,
262
262
  summary,
263
+ ticketId,
264
+ events: [...this.events],
265
+ resolvedInteractions: [...this.resolvedInteractions],
263
266
  completedAt: /* @__PURE__ */ new Date()
264
267
  });
265
268
  this.report = report;
@@ -335,11 +338,12 @@ var PRBEAgentState = class extends import_events.EventEmitter {
335
338
  }
336
339
  }
337
340
  // ---------- CR state mutations ----------
338
- beginCR(id, query, slug) {
341
+ beginCR(id, query, slug, ticketId) {
339
342
  const cr = {
340
343
  id,
341
344
  query,
342
345
  slug,
346
+ ticketId,
343
347
  events: [],
344
348
  resolvedInteractions: [],
345
349
  isRunning: true,
@@ -1569,20 +1573,196 @@ var BashExecuteTool = class {
1569
1573
  }
1570
1574
  };
1571
1575
 
1572
- // src/agent.ts
1573
- function getPersistencePath() {
1576
+ // src/history.ts
1577
+ var fs2 = __toESM(require("fs"));
1578
+ var path4 = __toESM(require("path"));
1579
+ var os = __toESM(require("os"));
1580
+ var crypto = __toESM(require("crypto"));
1581
+ var HKDF_SALT = Buffer.from("prbe-history-encryption-salt", "utf-8");
1582
+ var HKDF_INFO = Buffer.from("prbe-history-v1", "utf-8");
1583
+ function getAppDataDir() {
1574
1584
  const appData = process.env["APPDATA"] || (process.platform === "darwin" ? path4.join(os.homedir(), "Library", "Application Support") : path4.join(os.homedir(), ".local", "share"));
1575
- const dir = path4.join(appData, "prbe-agent");
1585
+ return path4.join(appData, "prbe-agent");
1586
+ }
1587
+ function getHistoryDir() {
1588
+ const dir = path4.join(getAppDataDir(), "history" /* HISTORY_DIR */);
1576
1589
  if (!fs2.existsSync(dir)) {
1577
1590
  fs2.mkdirSync(dir, { recursive: true });
1578
1591
  }
1579
- return path4.join(dir, "agent-state.json");
1592
+ return dir;
1593
+ }
1594
+ function deriveKey(apiKey) {
1595
+ return Buffer.from(
1596
+ crypto.hkdfSync(
1597
+ "sha256",
1598
+ Buffer.from(apiKey, "utf-8"),
1599
+ HKDF_SALT,
1600
+ HKDF_INFO,
1601
+ 32 /* KEY_LENGTH */
1602
+ )
1603
+ );
1604
+ }
1605
+ function encrypt(plaintext, key) {
1606
+ const iv = crypto.randomBytes(12 /* IV_LENGTH */);
1607
+ const cipher = crypto.createCipheriv(
1608
+ "aes-256-gcm" /* ALGORITHM */,
1609
+ key,
1610
+ iv,
1611
+ { authTagLength: 16 /* AUTH_TAG_LENGTH */ }
1612
+ );
1613
+ const encrypted = Buffer.concat([cipher.update(plaintext, "utf-8"), cipher.final()]);
1614
+ const authTag = cipher.getAuthTag();
1615
+ return Buffer.concat([iv, authTag, encrypted]);
1616
+ }
1617
+ function decrypt(data, key) {
1618
+ const iv = data.subarray(0, 12 /* IV_LENGTH */);
1619
+ const authTag = data.subarray(
1620
+ 12 /* IV_LENGTH */,
1621
+ 12 /* IV_LENGTH */ + 16 /* AUTH_TAG_LENGTH */
1622
+ );
1623
+ const ciphertext = data.subarray(
1624
+ 12 /* IV_LENGTH */ + 16 /* AUTH_TAG_LENGTH */
1625
+ );
1626
+ const decipher = crypto.createDecipheriv(
1627
+ "aes-256-gcm" /* ALGORITHM */,
1628
+ key,
1629
+ iv,
1630
+ { authTagLength: 16 /* AUTH_TAG_LENGTH */ }
1631
+ );
1632
+ decipher.setAuthTag(authTag);
1633
+ return decipher.update(ciphertext) + decipher.final("utf-8");
1634
+ }
1635
+ var HistoryStore = class {
1636
+ key;
1637
+ constructor(apiKey) {
1638
+ this.key = deriveKey(apiKey);
1639
+ }
1640
+ load() {
1641
+ const investigations = [];
1642
+ const crs = [];
1643
+ try {
1644
+ const dir = getHistoryDir();
1645
+ let files;
1646
+ try {
1647
+ files = fs2.readdirSync(dir);
1648
+ } catch {
1649
+ return { investigations, crs };
1650
+ }
1651
+ for (const filename of files) {
1652
+ try {
1653
+ const filePath = path4.join(dir, filename);
1654
+ const raw = fs2.readFileSync(filePath);
1655
+ const json = decrypt(raw, this.key);
1656
+ if (filename.startsWith("inv-") && filename.endsWith(".json")) {
1657
+ const item = JSON.parse(json);
1658
+ investigations.push({
1659
+ ...item,
1660
+ completedAt: new Date(item.completedAt)
1661
+ });
1662
+ } else if (filename.startsWith("cr-") && filename.endsWith(".json")) {
1663
+ const item = JSON.parse(json);
1664
+ crs.push({
1665
+ ...item,
1666
+ startedAt: new Date(item.startedAt),
1667
+ resolvedInteractions: item.resolvedInteractions ?? []
1668
+ });
1669
+ }
1670
+ } catch {
1671
+ console.warn(`[PRBEAgent] Skipping unreadable history file: ${filename}`);
1672
+ }
1673
+ }
1674
+ } catch {
1675
+ }
1676
+ investigations.sort(
1677
+ (a, b) => b.completedAt.getTime() - a.completedAt.getTime()
1678
+ );
1679
+ crs.sort((a, b) => b.startedAt.getTime() - a.startedAt.getTime());
1680
+ return { investigations, crs };
1681
+ }
1682
+ save(investigations, crs) {
1683
+ try {
1684
+ const dir = getHistoryDir();
1685
+ const desiredFiles = /* @__PURE__ */ new Set();
1686
+ for (const inv of investigations) {
1687
+ const filename = `inv-${inv.id}.json`;
1688
+ desiredFiles.add(filename);
1689
+ const data = {
1690
+ id: inv.id,
1691
+ query: inv.query,
1692
+ report: inv.report,
1693
+ summary: inv.summary,
1694
+ ticketId: inv.ticketId,
1695
+ events: inv.events,
1696
+ resolvedInteractions: inv.resolvedInteractions,
1697
+ completedAt: inv.completedAt.toISOString()
1698
+ };
1699
+ fs2.writeFileSync(
1700
+ path4.join(dir, filename),
1701
+ encrypt(JSON.stringify(data), this.key)
1702
+ );
1703
+ }
1704
+ for (const cr of crs) {
1705
+ const filename = `cr-${cr.id}.json`;
1706
+ desiredFiles.add(filename);
1707
+ const data = {
1708
+ id: cr.id,
1709
+ query: cr.query,
1710
+ slug: cr.slug,
1711
+ ticketId: cr.ticketId,
1712
+ events: cr.events,
1713
+ isRunning: cr.isRunning,
1714
+ isCompleted: cr.isCompleted,
1715
+ isFailed: cr.isFailed,
1716
+ report: cr.report,
1717
+ summary: cr.summary,
1718
+ errorMessage: cr.errorMessage,
1719
+ startedAt: cr.startedAt.toISOString(),
1720
+ pendingInteraction: cr.pendingInteraction,
1721
+ resolvedInteractions: cr.resolvedInteractions ?? []
1722
+ };
1723
+ fs2.writeFileSync(
1724
+ path4.join(dir, filename),
1725
+ encrypt(JSON.stringify(data), this.key)
1726
+ );
1727
+ }
1728
+ try {
1729
+ const existing = fs2.readdirSync(dir);
1730
+ for (const filename of existing) {
1731
+ if (!desiredFiles.has(filename)) {
1732
+ fs2.unlinkSync(path4.join(dir, filename));
1733
+ }
1734
+ }
1735
+ } catch {
1736
+ }
1737
+ } catch {
1738
+ console.error("[PRBEAgent] Failed to save investigation history");
1739
+ }
1740
+ }
1741
+ static clear() {
1742
+ try {
1743
+ const dir = path4.join(getAppDataDir(), "history" /* HISTORY_DIR */);
1744
+ if (fs2.existsSync(dir)) {
1745
+ fs2.rmSync(dir, { recursive: true, force: true });
1746
+ }
1747
+ } catch {
1748
+ }
1749
+ }
1750
+ };
1751
+
1752
+ // src/agent.ts
1753
+ function getPersistencePath() {
1754
+ const appData = process.env["APPDATA"] || (process.platform === "darwin" ? path5.join(os2.homedir(), "Library", "Application Support") : path5.join(os2.homedir(), ".local", "share"));
1755
+ const dir = path5.join(appData, "prbe-agent");
1756
+ if (!fs3.existsSync(dir)) {
1757
+ fs3.mkdirSync(dir, { recursive: true });
1758
+ }
1759
+ return path5.join(dir, "agent-state.json");
1580
1760
  }
1581
1761
  function loadPersistedData() {
1582
1762
  try {
1583
1763
  const filePath = getPersistencePath();
1584
- if (fs2.existsSync(filePath)) {
1585
- const raw = fs2.readFileSync(filePath, "utf-8");
1764
+ if (fs3.existsSync(filePath)) {
1765
+ const raw = fs3.readFileSync(filePath, "utf-8");
1586
1766
  return JSON.parse(raw);
1587
1767
  }
1588
1768
  } catch {
@@ -1592,7 +1772,7 @@ function loadPersistedData() {
1592
1772
  function savePersistedData(data) {
1593
1773
  try {
1594
1774
  const filePath = getPersistencePath();
1595
- fs2.writeFileSync(filePath, JSON.stringify(data, null, 2), "utf-8");
1775
+ fs3.writeFileSync(filePath, JSON.stringify(data, null, 2), "utf-8");
1596
1776
  } catch {
1597
1777
  console.error("[PRBEAgent] Failed to save persisted data");
1598
1778
  }
@@ -1612,6 +1792,7 @@ var PRBEAgent = class _PRBEAgent {
1612
1792
  fetchAbortController = null;
1613
1793
  currentInvestigationSource = "user" /* USER */;
1614
1794
  currentCRId = null;
1795
+ historyStore;
1615
1796
  /** Files flagged during the current tool call — uploaded immediately after the tool returns. */
1616
1797
  pendingFlaggedFiles = [];
1617
1798
  // ---------- Persistence ----------
@@ -1673,6 +1854,10 @@ var PRBEAgent = class _PRBEAgent {
1673
1854
  this.state = new PRBEAgentState();
1674
1855
  this.logCapture = new PRBELogCapture(this.config.maxLogEntries);
1675
1856
  this.persistedData = loadPersistedData();
1857
+ this.historyStore = new HistoryStore(this.config.apiKey);
1858
+ const history = this.historyStore.load();
1859
+ this.state.completedInvestigations = history.investigations;
1860
+ this.state.completedCRs = history.crs;
1676
1861
  const roots = this.config.autoApprovedDirs;
1677
1862
  const requester = this.interactionHandler ? this : void 0;
1678
1863
  const grantedPaths = this.grantedPaths;
@@ -1823,7 +2008,8 @@ var PRBEAgent = class _PRBEAgent {
1823
2008
  this.state.appendEvent("Thinking", status.text);
1824
2009
  break;
1825
2010
  case "completed" /* COMPLETED */:
1826
- this.state.completeInvestigation(status.report, status.userSummary);
2011
+ this.state.completeInvestigation(status.report, status.userSummary, status.ticketId);
2012
+ this.historyStore.save(this.state.completedInvestigations, this.state.completedCRs);
1827
2013
  break;
1828
2014
  case "error" /* ERROR */:
1829
2015
  this.state.failInvestigation(status.message);
@@ -1965,6 +2151,7 @@ var PRBEAgent = class _PRBEAgent {
1965
2151
  this.stopPolling();
1966
2152
  this.persistedData = {};
1967
2153
  savePersistedData(this.persistedData);
2154
+ HistoryStore.clear();
1968
2155
  this.state.resetInvestigation();
1969
2156
  this.state.completedInvestigations = [];
1970
2157
  this.state.activeCRs.clear();
@@ -1979,9 +2166,10 @@ var PRBEAgent = class _PRBEAgent {
1979
2166
  static clearPersistedData() {
1980
2167
  try {
1981
2168
  const filePath = getPersistencePath();
1982
- if (fs2.existsSync(filePath)) {
1983
- fs2.unlinkSync(filePath);
2169
+ if (fs3.existsSync(filePath)) {
2170
+ fs3.unlinkSync(filePath);
1984
2171
  }
2172
+ HistoryStore.clear();
1985
2173
  } catch {
1986
2174
  }
1987
2175
  }
@@ -1990,7 +2178,7 @@ var PRBEAgent = class _PRBEAgent {
1990
2178
  const crID = cr.id;
1991
2179
  this.currentInvestigationSource = "context_request" /* CONTEXT_REQUEST */;
1992
2180
  this.currentCRId = crID;
1993
- this.state.beginCR(crID, cr.query, cr.slug ?? void 0);
2181
+ this.state.beginCR(crID, cr.query, cr.slug ?? void 0, ticketId);
1994
2182
  const emitter = (status) => {
1995
2183
  switch (status.type) {
1996
2184
  case "started" /* STARTED */:
@@ -2009,9 +2197,11 @@ var PRBEAgent = class _PRBEAgent {
2009
2197
  break;
2010
2198
  case "completed" /* COMPLETED */:
2011
2199
  this.state.completeCR(crID, status.report, status.userSummary);
2200
+ this.historyStore.save(this.state.completedInvestigations, this.state.completedCRs);
2012
2201
  break;
2013
2202
  case "error" /* ERROR */:
2014
2203
  this.state.failCR(crID, status.message);
2204
+ this.historyStore.save(this.state.completedInvestigations, this.state.completedCRs);
2015
2205
  break;
2016
2206
  }
2017
2207
  };
@@ -2150,7 +2340,7 @@ var PRBEAgent = class _PRBEAgent {
2150
2340
  const uploadPrefix = this.extractUploadPrefix(uploadBaseUrl);
2151
2341
  const uploadedRefs = [];
2152
2342
  for (const file of this.pendingFlaggedFiles) {
2153
- const filename = path4.basename(file.originalPath);
2343
+ const filename = path5.basename(file.originalPath);
2154
2344
  const safeName = encodeURIComponent(filename);
2155
2345
  const storagePath = `${uploadPrefix}/${safeName}`;
2156
2346
  uploadedRefs.push({
@@ -2206,7 +2396,8 @@ var PRBEAgent = class _PRBEAgent {
2206
2396
  emit({
2207
2397
  type: "completed" /* COMPLETED */,
2208
2398
  report,
2209
- userSummary
2399
+ userSummary,
2400
+ ticketId: ticketId2
2210
2401
  });
2211
2402
  ws.close(1e3, "Complete");
2212
2403
  finish({ report, userSummary, ticketId: ticketId2 });
@@ -2389,6 +2580,7 @@ function serializeCR(cr) {
2389
2580
  id: cr.id,
2390
2581
  query: cr.query,
2391
2582
  slug: cr.slug,
2583
+ ticketId: cr.ticketId,
2392
2584
  events: cr.events,
2393
2585
  isRunning: cr.isRunning,
2394
2586
  isCompleted: cr.isCompleted,
@@ -2416,6 +2608,9 @@ function serializePRBEState(state) {
2416
2608
  query: inv.query,
2417
2609
  report: inv.report,
2418
2610
  summary: inv.summary,
2611
+ ticketId: inv.ticketId,
2612
+ events: inv.events,
2613
+ resolvedInteractions: inv.resolvedInteractions,
2419
2614
  completedAt: inv.completedAt.toISOString()
2420
2615
  })),
2421
2616
  activeCRs: Array.from(state.activeCRs.values()).map(serializeCR),