@sentry/junior 0.61.0 → 0.63.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.
@@ -1,7 +1,8 @@
1
1
  import {
2
+ SANDBOX_WORKSPACE_ROOT,
2
3
  getStateAdapter,
3
4
  toOptionalTrimmed
4
- } from "./chunk-FKEKRBUB.js";
5
+ } from "./chunk-PEF6UXTY.js";
5
6
  import {
6
7
  getPluginRuntimeDependencies,
7
8
  getPluginRuntimePostinstall,
@@ -128,27 +129,6 @@ function createSandboxInstance(sandbox) {
128
129
  };
129
130
  }
130
131
 
131
- // src/chat/sandbox/paths.ts
132
- function normalizeWorkspaceRoot(input) {
133
- const candidate = (input ?? "").trim();
134
- if (!candidate) {
135
- return "/vercel/sandbox";
136
- }
137
- const normalized = candidate.replace(/\/+$/, "");
138
- return normalized.startsWith("/") ? normalized : `/${normalized}`;
139
- }
140
- var SANDBOX_WORKSPACE_ROOT = normalizeWorkspaceRoot(
141
- process.env.VERCEL_SANDBOX_WORKSPACE_DIR
142
- );
143
- var SANDBOX_SKILLS_ROOT = `${SANDBOX_WORKSPACE_ROOT}/skills`;
144
- var SANDBOX_DATA_ROOT = `${SANDBOX_WORKSPACE_ROOT}/data`;
145
- function sandboxSkillDir(skillName) {
146
- return `${SANDBOX_SKILLS_ROOT}/${skillName}`;
147
- }
148
- function sandboxSkillFile(skillName) {
149
- return `${sandboxSkillDir(skillName)}/SKILL.md`;
150
- }
151
-
152
132
  // src/chat/sandbox/runtime-dependency-snapshots.ts
153
133
  var SNAPSHOT_CACHE_PREFIX = "junior:sandbox_snapshot_profile";
154
134
  var SNAPSHOT_LOCK_PREFIX = "junior:sandbox_snapshot_lock";
@@ -693,11 +673,6 @@ function isSnapshotMissingError(error) {
693
673
  }
694
674
 
695
675
  export {
696
- SANDBOX_WORKSPACE_ROOT,
697
- SANDBOX_SKILLS_ROOT,
698
- SANDBOX_DATA_ROOT,
699
- sandboxSkillDir,
700
- sandboxSkillFile,
701
676
  buildNonInteractiveShellScript,
702
677
  runNonInteractiveCommand,
703
678
  getVercelSandboxCredentials,
@@ -896,6 +896,27 @@ async function disconnectStateAdapter() {
896
896
  }
897
897
  }
898
898
 
899
+ // src/chat/sandbox/paths.ts
900
+ function normalizeWorkspaceRoot(input) {
901
+ const candidate = (input ?? "").trim();
902
+ if (!candidate) {
903
+ return "/vercel/sandbox";
904
+ }
905
+ const normalized = candidate.replace(/\/+$/, "");
906
+ return normalized.startsWith("/") ? normalized : `/${normalized}`;
907
+ }
908
+ var SANDBOX_WORKSPACE_ROOT = normalizeWorkspaceRoot(
909
+ process.env.VERCEL_SANDBOX_WORKSPACE_DIR
910
+ );
911
+ var SANDBOX_SKILLS_ROOT = `${SANDBOX_WORKSPACE_ROOT}/skills`;
912
+ var SANDBOX_DATA_ROOT = `${SANDBOX_WORKSPACE_ROOT}/data`;
913
+ function sandboxSkillDir(skillName) {
914
+ return `${SANDBOX_SKILLS_ROOT}/${skillName}`;
915
+ }
916
+ function sandboxSkillFile(skillName) {
917
+ return `${sandboxSkillDir(skillName)}/SKILL.md`;
918
+ }
919
+
899
920
  export {
900
921
  toOptionalTrimmed,
901
922
  parseSlackThreadId,
@@ -927,5 +948,10 @@ export {
927
948
  ACTIVE_LOCK_TTL_MS,
928
949
  getConnectedStateContext,
929
950
  getStateAdapter,
930
- disconnectStateAdapter
951
+ disconnectStateAdapter,
952
+ SANDBOX_WORKSPACE_ROOT,
953
+ SANDBOX_SKILLS_ROOT,
954
+ SANDBOX_DATA_ROOT,
955
+ sandboxSkillDir,
956
+ sandboxSkillFile
931
957
  };
@@ -1,9 +1,9 @@
1
1
  import {
2
2
  resolveRuntimeDependencySnapshot
3
- } from "../chunk-QDGD5WVN.js";
3
+ } from "../chunk-LRVKJAR2.js";
4
4
  import {
5
5
  disconnectStateAdapter
6
- } from "../chunk-FKEKRBUB.js";
6
+ } from "../chunk-PEF6UXTY.js";
7
7
  import {
8
8
  getPluginProviders,
9
9
  getPluginRuntimeDependencies,
@@ -1,6 +1,4 @@
1
- import type { AgentTurnUsage } from "@/chat/usage";
2
1
  import { getPluginPackageContent } from "@/chat/plugins/registry";
3
- import { type AgentTurnRequester } from "@/chat/state/turn-session";
4
2
  export interface HealthReport {
5
3
  status: "ok";
6
4
  service: string;
@@ -21,27 +19,42 @@ export interface RuntimeInfoReport {
21
19
  skills: SkillReport[];
22
20
  packagedContent: ReturnType<typeof getPluginPackageContent>;
23
21
  }
22
+ export type DashboardSessionStatus = "active" | "completed" | "failed" | "hung" | "superseded";
23
+ export type DashboardSurface = "slack" | "api" | "scheduler" | "internal";
24
+ export interface DashboardTurnUsage {
25
+ inputTokens?: number;
26
+ outputTokens?: number;
27
+ cachedInputTokens?: number;
28
+ cacheCreationTokens?: number;
29
+ totalTokens?: number;
30
+ }
31
+ export interface DashboardRequesterIdentity {
32
+ email?: string;
33
+ fullName?: string;
34
+ slackUserId?: string;
35
+ slackUserName?: string;
36
+ }
24
37
  export interface DashboardSessionReport {
25
38
  conversationTitle?: string;
26
39
  cumulativeDurationMs?: number;
27
- cumulativeUsage?: AgentTurnUsage;
40
+ cumulativeUsage?: DashboardTurnUsage;
28
41
  conversationId: string;
29
42
  id: string;
30
- status: "active" | "completed" | "failed" | "hung" | "superseded";
43
+ status: DashboardSessionStatus;
31
44
  startedAt: string;
32
45
  lastSeenAt: string;
33
46
  lastProgressAt: string;
34
47
  completedAt?: string;
35
- surface?: "slack" | "api" | "scheduler" | "internal";
36
- title?: string;
37
- requester?: string;
38
- requesterIdentity?: AgentTurnRequester;
48
+ surface: DashboardSurface;
49
+ title: string;
50
+ requesterIdentity?: DashboardRequesterIdentity;
39
51
  channel?: string;
40
52
  channelName?: string;
41
53
  sentryConversationUrl?: string;
42
54
  sentryTraceUrl?: string;
43
55
  traceId?: string;
44
56
  }
57
+ export type DashboardTranscriptPartType = "text" | "thinking" | "tool_call" | "tool_result" | "unknown";
45
58
  export interface DashboardTranscriptPart {
46
59
  bytes?: number;
47
60
  chars?: number;
@@ -58,12 +71,14 @@ export interface DashboardTranscriptPart {
58
71
  outputSizeChars?: number;
59
72
  outputType?: string;
60
73
  redacted?: boolean;
74
+ sourceType?: string;
61
75
  text?: string;
62
- type: string;
76
+ type: DashboardTranscriptPartType;
63
77
  }
78
+ export type DashboardTranscriptRole = "assistant" | "system" | "tool" | "toolResult" | "unknown" | "user";
64
79
  export interface DashboardTranscriptMessage {
65
80
  parts: DashboardTranscriptPart[];
66
- role: string;
81
+ role: DashboardTranscriptRole;
67
82
  timestamp?: number;
68
83
  }
69
84
  export interface DashboardTurnReport extends DashboardSessionReport {
package/dist/reporting.js CHANGED
@@ -2,10 +2,11 @@ import {
2
2
  GET,
3
3
  buildSentryConversationUrl,
4
4
  buildSentryTraceUrl,
5
+ buildSystemPrompt,
5
6
  getAgentTurnSessionRecord,
6
7
  listAgentTurnSessionSummaries,
7
8
  listAgentTurnSessionSummariesForConversation
8
- } from "./chunk-I4FDGMFI.js";
9
+ } from "./chunk-ITZ2F7UE.js";
9
10
  import {
10
11
  discoverSkills
11
12
  } from "./chunk-ITOW4DED.js";
@@ -13,7 +14,7 @@ import {
13
14
  canExposeConversationPayload,
14
15
  parseSlackThreadId,
15
16
  resolveConversationPrivacy
16
- } from "./chunk-FKEKRBUB.js";
17
+ } from "./chunk-PEF6UXTY.js";
17
18
  import {
18
19
  getPluginPackageContent,
19
20
  getPluginProviders,
@@ -79,10 +80,6 @@ function titleFromSummary(summary) {
79
80
  }
80
81
  return `Turn ${summary.sessionId}`;
81
82
  }
82
- function requesterLabel(requester) {
83
- if (!requester) return void 0;
84
- return requester.email ?? requester.slackUserName ?? requester.fullName ?? requester.slackUserId;
85
- }
86
83
  function safePrivateLabel(summary) {
87
84
  const slackThread = parseSlackThreadId(summary.conversationId);
88
85
  if (slackThread?.channelId.startsWith("D")) {
@@ -93,6 +90,27 @@ function safePrivateLabel(summary) {
93
90
  }
94
91
  return "Private Channel";
95
92
  }
93
+ function requesterIdentityReport(requester) {
94
+ if (!requester) return void 0;
95
+ const identity = {
96
+ ...requester.email !== void 0 ? { email: requester.email } : {},
97
+ ...requester.fullName !== void 0 ? { fullName: requester.fullName } : {},
98
+ ...requester.slackUserId !== void 0 ? { slackUserId: requester.slackUserId } : {},
99
+ ...requester.slackUserName !== void 0 ? { slackUserName: requester.slackUserName } : {}
100
+ };
101
+ return Object.keys(identity).length > 0 ? identity : void 0;
102
+ }
103
+ function turnUsageReport(usage) {
104
+ if (!usage) return void 0;
105
+ const report = {
106
+ ...usage.inputTokens !== void 0 ? { inputTokens: usage.inputTokens } : {},
107
+ ...usage.outputTokens !== void 0 ? { outputTokens: usage.outputTokens } : {},
108
+ ...usage.cachedInputTokens !== void 0 ? { cachedInputTokens: usage.cachedInputTokens } : {},
109
+ ...usage.cacheCreationTokens !== void 0 ? { cacheCreationTokens: usage.cacheCreationTokens } : {},
110
+ ...usage.totalTokens !== void 0 ? { totalTokens: usage.totalTokens } : {}
111
+ };
112
+ return Object.keys(report).length > 0 ? report : void 0;
113
+ }
96
114
  function sessionReportFromSummary(summary) {
97
115
  const slackThread = parseSlackThreadId(summary.conversationId);
98
116
  const privacy = resolveConversationPrivacy({
@@ -101,11 +119,12 @@ function sessionReportFromSummary(summary) {
101
119
  const privateLabel = privacy !== "public" ? safePrivateLabel(summary) : void 0;
102
120
  const conversationTitle = privateLabel ?? summary.conversationTitle;
103
121
  const channelName = privateLabel ?? summary.channelName;
104
- const requester = requesterLabel(summary.requester);
105
122
  const sentryConversationUrl = buildSentryConversationUrl(
106
123
  summary.conversationId
107
124
  );
108
125
  const sentryTraceUrl = summary.traceId ? buildSentryTraceUrl(summary.traceId) : void 0;
126
+ const requesterIdentity = requesterIdentityReport(summary.requester);
127
+ const cumulativeUsage = turnUsageReport(summary.cumulativeUsage);
109
128
  return {
110
129
  conversationId: summary.conversationId,
111
130
  ...conversationTitle ? { conversationTitle } : {},
@@ -116,11 +135,10 @@ function sessionReportFromSummary(summary) {
116
135
  lastSeenAt: new Date(summary.updatedAtMs).toISOString(),
117
136
  ...summary.state === "completed" ? { completedAt: new Date(summary.updatedAtMs).toISOString() } : {},
118
137
  ...summary.cumulativeDurationMs !== void 0 ? { cumulativeDurationMs: summary.cumulativeDurationMs } : {},
119
- ...summary.cumulativeUsage ? { cumulativeUsage: summary.cumulativeUsage } : {},
138
+ ...cumulativeUsage ? { cumulativeUsage } : {},
120
139
  surface: surfaceFromConversationId(summary.conversationId),
121
140
  title: titleFromSummary(summary),
122
- ...requester ? { requester } : {},
123
- ...summary.requester ? { requesterIdentity: summary.requester } : {},
141
+ ...requesterIdentity ? { requesterIdentity } : {},
124
142
  ...slackThread ? { channel: slackThread.channelId } : {},
125
143
  ...channelName ? { channelName } : {},
126
144
  ...sentryConversationUrl ? { sentryConversationUrl } : {},
@@ -181,7 +199,8 @@ function normalizeTranscriptPart(part) {
181
199
  };
182
200
  }
183
201
  return {
184
- type: rawType,
202
+ type: "unknown",
203
+ ...rawType !== "unknown" ? { sourceType: rawType } : {},
185
204
  output: part
186
205
  };
187
206
  }
@@ -207,13 +226,16 @@ function normalizeToolResultMessage(record) {
207
226
  function normalizeTranscriptMessage(message) {
208
227
  const record = message;
209
228
  const content = record.content;
210
- const role = typeof record.role === "string" ? record.role : "unknown";
229
+ const role = transcriptRole(record.role);
211
230
  return {
212
231
  role,
213
232
  ...typeof record.timestamp === "number" ? { timestamp: record.timestamp } : {},
214
233
  parts: role === "toolResult" ? [normalizeToolResultMessage(record)] : Array.isArray(content) ? content.map(normalizeTranscriptPart) : [normalizeTranscriptPart(content)]
215
234
  };
216
235
  }
236
+ function transcriptRole(role) {
237
+ return role === "assistant" || role === "system" || role === "tool" || role === "toolResult" || role === "user" ? role : "unknown";
238
+ }
217
239
  function serializedChars(value) {
218
240
  if (typeof value === "string") return value.length;
219
241
  return JSON.stringify(value)?.length ?? 0;
@@ -279,8 +301,9 @@ function redactTranscriptPart(part) {
279
301
  };
280
302
  }
281
303
  return {
282
- type: part.type,
304
+ type: "unknown",
283
305
  redacted: true,
306
+ ...part.sourceType ? { sourceType: part.sourceType } : {},
284
307
  ...redactedPayloadFields("output", part.output ?? part.input ?? part.text)
285
308
  };
286
309
  }
@@ -292,8 +315,7 @@ function redactTranscriptMessage(message) {
292
315
  };
293
316
  }
294
317
  function isConversationMessageRole(role) {
295
- const normalized = role.toLowerCase();
296
- return normalized === "user" || normalized === "assistant";
318
+ return role === "user" || role === "assistant";
297
319
  }
298
320
  function hasTextPart(message) {
299
321
  return message.parts.some((part) => {
@@ -304,12 +326,18 @@ function hasTextPart(message) {
304
326
  }
305
327
  function isConversationMessage(message) {
306
328
  if (!isConversationMessageRole(message.role)) return false;
307
- if (message.role.toLowerCase() === "assistant") return hasTextPart(message);
329
+ if (message.role === "assistant") return hasTextPart(message);
308
330
  return message.parts.length > 0;
309
331
  }
310
332
  function countConversationMessages(transcript) {
311
333
  return transcript.filter(isConversationMessage).length;
312
334
  }
335
+ function systemPromptMessage() {
336
+ return {
337
+ role: "system",
338
+ parts: [{ type: "text", text: buildSystemPrompt() }]
339
+ };
340
+ }
313
341
  function turnScopedMessages(messages) {
314
342
  for (let index = messages.length - 1; index >= 0; index -= 1) {
315
343
  const record = messages[index];
@@ -357,7 +385,7 @@ async function readConversation(conversationId) {
357
385
  normalizeTranscriptMessage
358
386
  );
359
387
  const transcriptMessageCount = countConversationMessages(normalizedTranscript);
360
- const transcript = canExposeTranscript ? normalizedTranscript : [];
388
+ const transcript = canExposeTranscript ? [systemPromptMessage(), ...normalizedTranscript] : [];
361
389
  const transcriptMetadata = canExposeTranscript ? void 0 : normalizedTranscript.map(redactTranscriptMessage);
362
390
  const traceId = summary.traceId ?? sessionRecord?.traceId ?? (canExposeTranscript ? traceIdFromTranscript(transcript) : void 0);
363
391
  const sentryTraceUrl = traceId ? buildSentryTraceUrl(traceId) : void 0;
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@sentry/junior",
3
- "version": "0.61.0",
3
+ "version": "0.63.0",
4
4
  "private": false,
5
5
  "publishConfig": {
6
6
  "access": "public"
@@ -64,7 +64,7 @@
64
64
  "node-html-markdown": "^2.0.0",
65
65
  "yaml": "^2.9.0",
66
66
  "zod": "^4.4.3",
67
- "@sentry/junior-plugin-api": "0.61.0"
67
+ "@sentry/junior-plugin-api": "0.63.0"
68
68
  },
69
69
  "devDependencies": {
70
70
  "@types/node": "^25.9.1",
@@ -76,7 +76,7 @@
76
76
  "typescript": "^6.0.3",
77
77
  "vercel": "^54.4.0",
78
78
  "vitest": "^4.1.7",
79
- "@sentry/junior-scheduler": "0.61.0"
79
+ "@sentry/junior-scheduler": "0.63.0"
80
80
  },
81
81
  "scripts": {
82
82
  "build": "tsup && tsc -p tsconfig.build.json --emitDeclarationOnly",