@tonyclaw/agent-inspector 2.0.36 → 2.0.38
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/.output/nitro.json +1 -1
- package/.output/public/assets/{CompareDrawer-Bg2mo0NZ.js → CompareDrawer-hc5OoAls.js} +1 -1
- package/.output/public/assets/{ProxyViewerContainer-C_Lq5T5V.js → ProxyViewerContainer-BMKBs8Qz.js} +35 -35
- package/.output/public/assets/{ReplayDialog-Bns-ayOg.js → ReplayDialog-CN-KM2nu.js} +1 -1
- package/.output/public/assets/{RequestAnatomy-BBcPAIWx.js → RequestAnatomy-B1kTlAUk.js} +1 -1
- package/.output/public/assets/{ResponseView-DSRS3rHt.js → ResponseView-BchUjKjt.js} +1 -1
- package/.output/public/assets/{StreamingChunkSequence-CzZxKE5-.js → StreamingChunkSequence-BQOxI9Hi.js} +1 -1
- package/.output/public/assets/_sessionId-CVw5e8TK.js +1 -0
- package/.output/public/assets/index-BdUTMQL6.js +1 -0
- package/.output/public/assets/{main-BVKRHBUl.js → main-Blykwzsn.js} +2 -2
- package/.output/server/_libs/lucide-react.mjs +114 -94
- package/.output/server/{_sessionId-Dsd36Yhc.mjs → _sessionId-BUNZz2zZ.mjs} +2 -2
- package/.output/server/_ssr/{CompareDrawer-BbJ5UdYD.mjs → CompareDrawer-VaDYPM5G.mjs} +3 -3
- package/.output/server/_ssr/{ProxyViewerContainer-7igCY291.mjs → ProxyViewerContainer-CpdWs7Pk.mjs} +801 -785
- package/.output/server/_ssr/{ReplayDialog-CgWweshq.mjs → ReplayDialog-DbfIjJhb.mjs} +4 -4
- package/.output/server/_ssr/{RequestAnatomy-BAyM_j7a.mjs → RequestAnatomy-CrD8h6As.mjs} +3 -3
- package/.output/server/_ssr/{ResponseView-iZQH7EYu.mjs → ResponseView-BalvDwtU.mjs} +3 -3
- package/.output/server/_ssr/{StreamingChunkSequence-BU6hyHMg.mjs → StreamingChunkSequence-RxatDbPV.mjs} +2 -2
- package/.output/server/_ssr/{index-D7QF4E6v.mjs → index-11qAtV9d.mjs} +2 -2
- package/.output/server/_ssr/index.mjs +2 -2
- package/.output/server/_ssr/{router-DLLY6gv_.mjs → router-C4OdRnqX.mjs} +138 -138
- package/.output/server/{_tanstack-start-manifest_v-CHmIZaVV.mjs → _tanstack-start-manifest_v-F6bwcl33.mjs} +1 -1
- package/.output/server/index.mjs +60 -60
- package/README.md +1 -1
- package/package.json +1 -1
- package/src/components/ProxyViewer.tsx +43 -9
- package/src/components/ProxyViewerContainer.tsx +1 -1
- package/src/components/providers/ProviderForm.tsx +2 -2
- package/src/components/proxy-viewer/AgentTraceSummary.tsx +1 -1
- package/src/components/proxy-viewer/CompareDrawer.tsx +1 -1
- package/src/components/proxy-viewer/ConversationGroup.tsx +1 -1
- package/src/components/proxy-viewer/ConversationGroupList.tsx +1 -1
- package/src/components/proxy-viewer/ConversationHeader.tsx +11 -7
- package/src/components/proxy-viewer/LogEntry.tsx +1 -1
- package/src/components/proxy-viewer/LogEntryHeader.tsx +1 -1
- package/src/components/proxy-viewer/ReplayDialog.tsx +1 -1
- package/src/components/proxy-viewer/ResponseView.tsx +2 -2
- package/src/components/proxy-viewer/StreamingChunkSequence.tsx +1 -1
- package/src/components/proxy-viewer/TurnGroup.tsx +1 -1
- package/src/components/proxy-viewer/anatomy/sessionContextSummary.ts +1 -1
- package/src/components/proxy-viewer/formats/anthropic/ContentBlocks.tsx +1 -1
- package/src/components/proxy-viewer/formats/anthropic/ResponseView.tsx +2 -2
- package/src/components/proxy-viewer/formats/index.tsx +5 -3
- package/src/components/proxy-viewer/formats/openai/ResponseView.tsx +1 -1
- package/src/components/proxy-viewer/log-formats/anthropic.ts +1 -4
- package/src/components/proxy-viewer/log-formats/index.ts +6 -6
- package/src/components/proxy-viewer/log-formats/openai.ts +1 -1
- package/src/components/proxy-viewer/log-formats/types.ts +2 -2
- package/src/components/proxy-viewer/viewerState.ts +1 -1
- package/src/contracts/anthropic.ts +235 -0
- package/src/contracts/index.ts +27 -0
- package/src/contracts/json.ts +32 -0
- package/src/contracts/log.ts +72 -0
- package/src/contracts/openai.ts +176 -0
- package/src/knowledge/distiller.ts +1 -1
- package/src/lib/export-logs.ts +1 -1
- package/src/lib/groupContract.ts +1 -1
- package/src/lib/objectUtils.ts +3 -3
- package/src/lib/providerTestContract.ts +1 -1
- package/src/lib/runContract.ts +1 -1
- package/src/lib/stopReason.ts +1 -1
- package/src/mcp/previewExtractor.ts +4 -7
- package/src/mcp/server.ts +1 -1
- package/src/mcp/toolHandlers.ts +1 -1
- package/src/proxy/formats/anthropic/anthropicProvider.ts +2 -2
- package/src/proxy/formats/anthropic/schemas.ts +12 -235
- package/src/proxy/formats/handler.ts +2 -2
- package/src/proxy/formats/index.ts +1 -1
- package/src/proxy/formats/jsonSchema.ts +2 -36
- package/src/proxy/formats/openai/alibabaProvider.ts +2 -2
- package/src/proxy/formats/openai/provider.ts +2 -2
- package/src/proxy/formats/openai/schemas.ts +14 -187
- package/src/proxy/formats/openai/zhipuProvider.ts +2 -2
- package/src/proxy/formats/{protocol.ts → providerAdapter.ts} +5 -5
- package/src/proxy/formats/providerRegistry.ts +7 -7
- package/src/proxy/formats/providers/index.ts +1 -1
- package/src/proxy/formats/registry.ts +20 -11
- package/src/proxy/handler.ts +1 -1
- package/src/proxy/openaiOrphanToolStrip.ts +1 -1
- package/src/proxy/providers.ts +1 -1
- package/src/proxy/schemas.ts +18 -80
- package/src/proxy/store.ts +14 -11
- package/src/proxy/upstream.ts +1 -1
- package/src/routes/api/logs.stream.ts +1 -1
- package/.output/public/assets/_sessionId-DurHDwM1.js +0 -1
- package/.output/public/assets/index-sGphugFR.js +0 -1
package/.output/server/index.mjs
CHANGED
|
@@ -38,100 +38,100 @@ const assets = {
|
|
|
38
38
|
"/assets/alibaba-TTwafVwX.svg": {
|
|
39
39
|
"type": "image/svg+xml",
|
|
40
40
|
"etag": '"171b-6dyV5K8QjiaY35sN9qNprh9zDIs"',
|
|
41
|
-
"mtime": "2026-07-
|
|
41
|
+
"mtime": "2026-07-01T07:15:57.121Z",
|
|
42
42
|
"size": 5915,
|
|
43
43
|
"path": "../public/assets/alibaba-TTwafVwX.svg"
|
|
44
44
|
},
|
|
45
|
-
"/assets/CompareDrawer-
|
|
45
|
+
"/assets/CompareDrawer-hc5OoAls.js": {
|
|
46
46
|
"type": "text/javascript; charset=utf-8",
|
|
47
|
-
"etag": '"49fe-
|
|
48
|
-
"mtime": "2026-07-
|
|
47
|
+
"etag": '"49fe-BHtwU/NjhFJzLdwy953kVTz0OMs"',
|
|
48
|
+
"mtime": "2026-07-01T07:15:57.121Z",
|
|
49
49
|
"size": 18942,
|
|
50
|
-
"path": "../public/assets/CompareDrawer-
|
|
50
|
+
"path": "../public/assets/CompareDrawer-hc5OoAls.js"
|
|
51
51
|
},
|
|
52
|
-
"/assets/index-
|
|
53
|
-
"type": "text/
|
|
54
|
-
"etag": '"
|
|
55
|
-
"mtime": "2026-07-
|
|
56
|
-
"size":
|
|
57
|
-
"path": "../public/assets/index-
|
|
52
|
+
"/assets/index-BdUTMQL6.js": {
|
|
53
|
+
"type": "text/javascript; charset=utf-8",
|
|
54
|
+
"etag": '"74-62iPuuX47jLXNHf/ZV6ct/elkTk"',
|
|
55
|
+
"mtime": "2026-07-01T07:15:57.121Z",
|
|
56
|
+
"size": 116,
|
|
57
|
+
"path": "../public/assets/index-BdUTMQL6.js"
|
|
58
58
|
},
|
|
59
59
|
"/assets/minimax-BPMzvuL-.jpeg": {
|
|
60
60
|
"type": "image/jpeg",
|
|
61
61
|
"etag": '"1b06-IwivU89ko5UTMUM1/t7hn4sQK9A"',
|
|
62
|
-
"mtime": "2026-07-
|
|
62
|
+
"mtime": "2026-07-01T07:15:57.121Z",
|
|
63
63
|
"size": 6918,
|
|
64
64
|
"path": "../public/assets/minimax-BPMzvuL-.jpeg"
|
|
65
65
|
},
|
|
66
|
-
"/assets/index-
|
|
67
|
-
"type": "text/
|
|
68
|
-
"etag": '"
|
|
69
|
-
"mtime": "2026-07-
|
|
70
|
-
"size":
|
|
71
|
-
"path": "../public/assets/index-
|
|
72
|
-
},
|
|
73
|
-
"/assets/ReplayDialog-Bns-ayOg.js": {
|
|
74
|
-
"type": "text/javascript; charset=utf-8",
|
|
75
|
-
"etag": '"318c-PpbkTF95foTOdbkrWMMu2juYBfw"',
|
|
76
|
-
"mtime": "2026-07-01T04:58:19.202Z",
|
|
77
|
-
"size": 12684,
|
|
78
|
-
"path": "../public/assets/ReplayDialog-Bns-ayOg.js"
|
|
79
|
-
},
|
|
80
|
-
"/assets/RequestAnatomy-BBcPAIWx.js": {
|
|
81
|
-
"type": "text/javascript; charset=utf-8",
|
|
82
|
-
"etag": '"4485-1vjOocGpUTcM93Vi7PdBPHFM1B4"',
|
|
83
|
-
"mtime": "2026-07-01T04:58:19.203Z",
|
|
84
|
-
"size": 17541,
|
|
85
|
-
"path": "../public/assets/RequestAnatomy-BBcPAIWx.js"
|
|
66
|
+
"/assets/index-BfGJEb-2.css": {
|
|
67
|
+
"type": "text/css; charset=utf-8",
|
|
68
|
+
"etag": '"1acc9-JrjZs7fIRGuBr66cqP9miLHcLKk"',
|
|
69
|
+
"mtime": "2026-07-01T07:15:57.121Z",
|
|
70
|
+
"size": 109769,
|
|
71
|
+
"path": "../public/assets/index-BfGJEb-2.css"
|
|
86
72
|
},
|
|
87
|
-
"/assets/main-
|
|
73
|
+
"/assets/main-Blykwzsn.js": {
|
|
88
74
|
"type": "text/javascript; charset=utf-8",
|
|
89
|
-
"etag": '"517d9-
|
|
90
|
-
"mtime": "2026-07-
|
|
75
|
+
"etag": '"517d9-1RW0upmMLsMivL5FlKjWPPFMbb8"',
|
|
76
|
+
"mtime": "2026-07-01T07:15:57.121Z",
|
|
91
77
|
"size": 333785,
|
|
92
|
-
"path": "../public/assets/main-
|
|
78
|
+
"path": "../public/assets/main-Blykwzsn.js"
|
|
93
79
|
},
|
|
94
|
-
"/assets/
|
|
80
|
+
"/assets/ReplayDialog-CN-KM2nu.js": {
|
|
95
81
|
"type": "text/javascript; charset=utf-8",
|
|
96
|
-
"etag": '"
|
|
97
|
-
"mtime": "2026-07-
|
|
98
|
-
"size":
|
|
99
|
-
"path": "../public/assets/
|
|
82
|
+
"etag": '"318c-bHppq4F90VcBylI8MEq9phZKKYY"',
|
|
83
|
+
"mtime": "2026-07-01T07:15:57.121Z",
|
|
84
|
+
"size": 12684,
|
|
85
|
+
"path": "../public/assets/ReplayDialog-CN-KM2nu.js"
|
|
100
86
|
},
|
|
101
|
-
"/assets/
|
|
87
|
+
"/assets/StreamingChunkSequence-BQOxI9Hi.js": {
|
|
102
88
|
"type": "text/javascript; charset=utf-8",
|
|
103
|
-
"etag": '"
|
|
104
|
-
"mtime": "2026-07-
|
|
105
|
-
"size":
|
|
106
|
-
"path": "../public/assets/
|
|
89
|
+
"etag": '"d57-VudeFeolN8IfFVek6HMLmXTmPQY"',
|
|
90
|
+
"mtime": "2026-07-01T07:15:57.121Z",
|
|
91
|
+
"size": 3415,
|
|
92
|
+
"path": "../public/assets/StreamingChunkSequence-BQOxI9Hi.js"
|
|
107
93
|
},
|
|
108
94
|
"/assets/zhipuai-BPNAnxo-.svg": {
|
|
109
95
|
"type": "image/svg+xml",
|
|
110
96
|
"etag": '"2bf8-hNaLCTi89nOFCsIIfWpP/jrfo0s"',
|
|
111
|
-
"mtime": "2026-07-
|
|
97
|
+
"mtime": "2026-07-01T07:15:57.121Z",
|
|
112
98
|
"size": 11256,
|
|
113
99
|
"path": "../public/assets/zhipuai-BPNAnxo-.svg"
|
|
114
100
|
},
|
|
101
|
+
"/assets/RequestAnatomy-B1kTlAUk.js": {
|
|
102
|
+
"type": "text/javascript; charset=utf-8",
|
|
103
|
+
"etag": '"4485-zOrU17hrJUbuuYLZW8HdqHozpuE"',
|
|
104
|
+
"mtime": "2026-07-01T07:15:57.121Z",
|
|
105
|
+
"size": 17541,
|
|
106
|
+
"path": "../public/assets/RequestAnatomy-B1kTlAUk.js"
|
|
107
|
+
},
|
|
108
|
+
"/assets/_sessionId-CVw5e8TK.js": {
|
|
109
|
+
"type": "text/javascript; charset=utf-8",
|
|
110
|
+
"etag": '"d2-cV8zzbK+/RUFmfT5dWvK333bSe8"',
|
|
111
|
+
"mtime": "2026-07-01T07:15:57.121Z",
|
|
112
|
+
"size": 210,
|
|
113
|
+
"path": "../public/assets/_sessionId-CVw5e8TK.js"
|
|
114
|
+
},
|
|
115
|
+
"/assets/ResponseView-BchUjKjt.js": {
|
|
116
|
+
"type": "text/javascript; charset=utf-8",
|
|
117
|
+
"etag": '"30d0-i5IJUGuKCFfLsaiZy5PG5wFw9NM"',
|
|
118
|
+
"mtime": "2026-07-01T07:15:57.121Z",
|
|
119
|
+
"size": 12496,
|
|
120
|
+
"path": "../public/assets/ResponseView-BchUjKjt.js"
|
|
121
|
+
},
|
|
115
122
|
"/assets/qwen-CONDcHqt.png": {
|
|
116
123
|
"type": "image/png",
|
|
117
124
|
"etag": '"572c3-cdJAPaHdOvFCGzuaQjagdgOu6XE"',
|
|
118
|
-
"mtime": "2026-07-
|
|
125
|
+
"mtime": "2026-07-01T07:15:57.121Z",
|
|
119
126
|
"size": 357059,
|
|
120
127
|
"path": "../public/assets/qwen-CONDcHqt.png"
|
|
121
128
|
},
|
|
122
|
-
"/assets/
|
|
123
|
-
"type": "text/javascript; charset=utf-8",
|
|
124
|
-
"etag": '"d57-tTBqrJv/i9tGh9Lr7MzVvOm88mA"',
|
|
125
|
-
"mtime": "2026-07-01T04:58:19.203Z",
|
|
126
|
-
"size": 3415,
|
|
127
|
-
"path": "../public/assets/StreamingChunkSequence-CzZxKE5-.js"
|
|
128
|
-
},
|
|
129
|
-
"/assets/ProxyViewerContainer-C_Lq5T5V.js": {
|
|
129
|
+
"/assets/ProxyViewerContainer-BMKBs8Qz.js": {
|
|
130
130
|
"type": "text/javascript; charset=utf-8",
|
|
131
|
-
"etag": '"
|
|
132
|
-
"mtime": "2026-07-
|
|
133
|
-
"size":
|
|
134
|
-
"path": "../public/assets/ProxyViewerContainer-
|
|
131
|
+
"etag": '"b5a7d-eALnI6HNEToSu0yqva+VFivYgJA"',
|
|
132
|
+
"mtime": "2026-07-01T07:15:57.121Z",
|
|
133
|
+
"size": 744061,
|
|
134
|
+
"path": "../public/assets/ProxyViewerContainer-BMKBs8Qz.js"
|
|
135
135
|
}
|
|
136
136
|
};
|
|
137
137
|
function readAsset(id) {
|
package/README.md
CHANGED
|
@@ -139,7 +139,7 @@ needed for the session timeline, request/response views, token usage, provider
|
|
|
139
139
|
routing, errors, and knowledge workflows, but it does not retain raw request
|
|
140
140
|
headers, upstream headers, or detailed streaming chunk artifacts.
|
|
141
141
|
|
|
142
|
-
Use `full` mode when you need
|
|
142
|
+
Use `full` mode when you need API-format-level diagnostics:
|
|
143
143
|
|
|
144
144
|
```bash
|
|
145
145
|
agent-inspector --mode full
|
package/package.json
CHANGED
|
@@ -1,7 +1,17 @@
|
|
|
1
1
|
import { type JSX, useCallback, useEffect, useMemo, useRef, useState, Suspense } from "react";
|
|
2
|
-
import {
|
|
2
|
+
import {
|
|
3
|
+
ArrowDownRight,
|
|
4
|
+
ArrowLeft,
|
|
5
|
+
ArrowUpRight,
|
|
6
|
+
Check,
|
|
7
|
+
Copy,
|
|
8
|
+
Download,
|
|
9
|
+
FileJson,
|
|
10
|
+
Plus,
|
|
11
|
+
Trash2,
|
|
12
|
+
} from "lucide-react";
|
|
3
13
|
|
|
4
|
-
import type { CapturedLog } from "../
|
|
14
|
+
import type { CapturedLog } from "../contracts";
|
|
5
15
|
import { exportLogsAsZip, type ExportMode } from "../lib/export-logs";
|
|
6
16
|
import type { CaptureMode, TimeDisplayFormat } from "../lib/runtimeConfig";
|
|
7
17
|
import { formatTimestampRange } from "../lib/timeDisplay";
|
|
@@ -43,6 +53,22 @@ export function shouldShowRawExport(captureMode: CaptureMode): boolean {
|
|
|
43
53
|
return captureMode === "full";
|
|
44
54
|
}
|
|
45
55
|
|
|
56
|
+
export type ExportActionVisibility = {
|
|
57
|
+
redacted: boolean;
|
|
58
|
+
raw: boolean;
|
|
59
|
+
};
|
|
60
|
+
|
|
61
|
+
export function getExportActionVisibility(
|
|
62
|
+
captureMode: CaptureMode,
|
|
63
|
+
logCount: number,
|
|
64
|
+
): ExportActionVisibility {
|
|
65
|
+
const hasLogs = logCount > 0;
|
|
66
|
+
return {
|
|
67
|
+
redacted: hasLogs,
|
|
68
|
+
raw: hasLogs && shouldShowRawExport(captureMode),
|
|
69
|
+
};
|
|
70
|
+
}
|
|
71
|
+
|
|
46
72
|
function computeTokenSummary(logs: CapturedLog[]): { totalIn: number; totalOut: number } {
|
|
47
73
|
let totalIn = 0;
|
|
48
74
|
let totalOut = 0;
|
|
@@ -714,7 +740,7 @@ export function ProxyViewer({
|
|
|
714
740
|
);
|
|
715
741
|
const cacheTrends = useMemo(() => computeCacheTrends(groups), [groups]);
|
|
716
742
|
const comparisonPredecessors = useMemo(() => buildValidPredecessors(groups), [groups]);
|
|
717
|
-
const
|
|
743
|
+
const exportActionVisibility = getExportActionVisibility(captureMode, logs.length);
|
|
718
744
|
const handleCompareWithPrevious = useCallback(
|
|
719
745
|
(log: CapturedLog) => {
|
|
720
746
|
const predecessor = comparisonPredecessors.get(log.id);
|
|
@@ -881,7 +907,7 @@ export function ProxyViewer({
|
|
|
881
907
|
: ""}
|
|
882
908
|
</span>
|
|
883
909
|
)}
|
|
884
|
-
{
|
|
910
|
+
{exportActionVisibility.redacted && (
|
|
885
911
|
<button
|
|
886
912
|
type="button"
|
|
887
913
|
onClick={() => {
|
|
@@ -901,26 +927,34 @@ export function ProxyViewer({
|
|
|
901
927
|
)}
|
|
902
928
|
</button>
|
|
903
929
|
)}
|
|
904
|
-
{
|
|
930
|
+
{exportActionVisibility.raw && (
|
|
905
931
|
<button
|
|
906
932
|
type="button"
|
|
907
933
|
onClick={() => {
|
|
908
934
|
void handleExport("raw");
|
|
909
935
|
}}
|
|
910
936
|
disabled={exporting !== null}
|
|
911
|
-
className="h-8 px-2 text-xs text-muted-foreground hover:text-foreground transition-colors cursor-pointer disabled:opacity-50 disabled:cursor-not-allowed rounded-md hover:bg-muted"
|
|
937
|
+
className="h-8 px-2.5 text-xs text-muted-foreground hover:text-foreground transition-colors cursor-pointer disabled:opacity-50 disabled:cursor-not-allowed inline-flex items-center gap-1.5 rounded-md hover:bg-muted"
|
|
912
938
|
title="Export raw logs without redaction"
|
|
913
939
|
>
|
|
914
|
-
{exporting === "raw" ?
|
|
940
|
+
{exporting === "raw" ? (
|
|
941
|
+
<span>Exporting...</span>
|
|
942
|
+
) : (
|
|
943
|
+
<>
|
|
944
|
+
<FileJson className="size-3.5" />
|
|
945
|
+
<span>Raw</span>
|
|
946
|
+
</>
|
|
947
|
+
)}
|
|
915
948
|
</button>
|
|
916
949
|
)}
|
|
917
950
|
<button
|
|
918
951
|
type="button"
|
|
919
952
|
onClick={onClearAll}
|
|
920
|
-
className="h-8 px-3 text-xs text-muted-foreground hover:text-foreground transition-colors cursor-pointer rounded-md hover:bg-muted"
|
|
953
|
+
className="h-8 px-3 text-xs text-muted-foreground hover:text-foreground transition-colors cursor-pointer inline-flex items-center gap-1.5 rounded-md hover:bg-muted"
|
|
921
954
|
title="Clear all logs"
|
|
922
955
|
>
|
|
923
|
-
|
|
956
|
+
<Trash2 className="size-3.5" />
|
|
957
|
+
<span>Clear</span>
|
|
924
958
|
</button>
|
|
925
959
|
</div>
|
|
926
960
|
{exportError !== null && (
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
import { useState, useEffect, useCallback, useRef, useMemo, type JSX } from "react";
|
|
2
2
|
import { z } from "zod";
|
|
3
|
-
import { CapturedLogSchema, type CapturedLog } from "../
|
|
3
|
+
import { CapturedLogSchema, type CapturedLog } from "../contracts";
|
|
4
4
|
import { useStripConfig } from "../lib/useStripConfig";
|
|
5
5
|
import { OnboardingBanner } from "./OnboardingBanner";
|
|
6
6
|
import { ProxyViewer } from "./ProxyViewer";
|
|
@@ -845,7 +845,7 @@ export function ProviderForm({ provider, onSubmit, onCancel }: ProviderFormProps
|
|
|
845
845
|
Anthropic Format
|
|
846
846
|
</button>
|
|
847
847
|
</TooltipTrigger>
|
|
848
|
-
<TooltipContent>Anthropic Messages API
|
|
848
|
+
<TooltipContent>Anthropic Messages API format</TooltipContent>
|
|
849
849
|
</Tooltip>
|
|
850
850
|
</TooltipProvider>
|
|
851
851
|
<TooltipProvider>
|
|
@@ -863,7 +863,7 @@ export function ProviderForm({ provider, onSubmit, onCancel }: ProviderFormProps
|
|
|
863
863
|
OpenAI Format
|
|
864
864
|
</button>
|
|
865
865
|
</TooltipTrigger>
|
|
866
|
-
<TooltipContent>OpenAI Chat Completions API
|
|
866
|
+
<TooltipContent>OpenAI Chat Completions API format</TooltipContent>
|
|
867
867
|
</Tooltip>
|
|
868
868
|
</TooltipProvider>
|
|
869
869
|
</div>
|
|
@@ -29,7 +29,7 @@ import {
|
|
|
29
29
|
type KnowledgeCandidate,
|
|
30
30
|
type KnowledgeCandidateStatus,
|
|
31
31
|
} from "../../knowledge/types";
|
|
32
|
-
import type { CapturedLog } from "../../
|
|
32
|
+
import type { CapturedLog } from "../../contracts";
|
|
33
33
|
import { Badge } from "../ui/badge";
|
|
34
34
|
import { Button } from "../ui/button";
|
|
35
35
|
import { buildTraceSummary, extractToolTraceEvents, type TraceSummary } from "./viewerState";
|
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
import { useState, memo, useCallback, useEffect, useMemo } from "react";
|
|
2
2
|
import type { JSX } from "react";
|
|
3
3
|
import type { TimeDisplayFormat } from "../../lib/runtimeConfig";
|
|
4
|
-
import type { CapturedLog } from "../../
|
|
4
|
+
import type { CapturedLog } from "../../contracts";
|
|
5
5
|
import {
|
|
6
6
|
ConversationHeader,
|
|
7
7
|
getGroupApiFormat,
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
import { type JSX, useCallback, useEffect, useMemo, useState } from "react";
|
|
2
2
|
import { useWindowVirtualizer } from "@tanstack/react-virtual";
|
|
3
|
-
import type { CapturedLog } from "../../
|
|
3
|
+
import type { CapturedLog } from "../../contracts";
|
|
4
4
|
import { ConversationGroup, type ConversationGroupProps } from "./ConversationGroup";
|
|
5
5
|
import type { ConversationGroupData } from "./ConversationHeader";
|
|
6
6
|
import { LOG_FOCUS_REQUEST_EVENT, readLogFocusRequest } from "./logFocus";
|
|
@@ -15,9 +15,10 @@ import { getSessionPath } from "../../lib/sessionUrl";
|
|
|
15
15
|
import type { TimeDisplayFormat } from "../../lib/runtimeConfig";
|
|
16
16
|
import { formatTimestampRange } from "../../lib/timeDisplay";
|
|
17
17
|
import { cn, formatTokens } from "../../lib/utils";
|
|
18
|
-
import type { CapturedLog } from "../../
|
|
18
|
+
import type { CapturedLog } from "../../contracts";
|
|
19
19
|
import { Badge } from "../ui/badge";
|
|
20
20
|
import { ConfirmDialog } from "../ui/confirm-dialog";
|
|
21
|
+
import { resolveLogFormat } from "./log-formats";
|
|
21
22
|
|
|
22
23
|
const API_FORMAT_LABELS: Record<"anthropic" | "openai" | "unknown", string> = {
|
|
23
24
|
anthropic: "Anthropic",
|
|
@@ -231,11 +232,13 @@ export type ConversationGroupData = {
|
|
|
231
232
|
};
|
|
232
233
|
|
|
233
234
|
export function getGroupApiFormat(logs: CapturedLog[]): "anthropic" | "openai" | "unknown" {
|
|
234
|
-
const
|
|
235
|
-
|
|
236
|
-
|
|
235
|
+
for (const log of logs) {
|
|
236
|
+
const apiFormat = resolveLogFormat(log);
|
|
237
|
+
if (apiFormat !== "unknown") {
|
|
238
|
+
return apiFormat;
|
|
239
|
+
}
|
|
237
240
|
}
|
|
238
|
-
return
|
|
241
|
+
return "unknown";
|
|
239
242
|
}
|
|
240
243
|
|
|
241
244
|
/**
|
|
@@ -248,8 +251,9 @@ export function hasMixedApiFormat(logs: CapturedLog[]): boolean {
|
|
|
248
251
|
let hasAnthropic = false;
|
|
249
252
|
let hasOpenai = false;
|
|
250
253
|
for (const log of logs) {
|
|
251
|
-
|
|
252
|
-
|
|
254
|
+
const apiFormat = resolveLogFormat(log);
|
|
255
|
+
if (apiFormat === "anthropic") hasAnthropic = true;
|
|
256
|
+
else if (apiFormat === "openai") hasOpenai = true;
|
|
253
257
|
if (hasAnthropic && hasOpenai) return true;
|
|
254
258
|
}
|
|
255
259
|
return false;
|
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
import { GitCompareArrows } from "lucide-react";
|
|
2
2
|
import { Suspense, type JSX } from "react";
|
|
3
3
|
import { useEffect, useMemo, useRef, useState, memo } from "react";
|
|
4
|
-
import type { CapturedLog } from "../../
|
|
4
|
+
import type { CapturedLog } from "../../contracts";
|
|
5
5
|
import type { TimeDisplayFormat } from "../../lib/runtimeConfig";
|
|
6
6
|
import { stripClaudeCodeBillingHeader } from "../../proxy/claudeCodeStrip";
|
|
7
7
|
import { Button } from "../ui/button";
|
|
@@ -27,7 +27,7 @@ import { memo } from "react";
|
|
|
27
27
|
import type { TimeDisplayFormat } from "../../lib/runtimeConfig";
|
|
28
28
|
import { formatTimestamp } from "../../lib/timeDisplay";
|
|
29
29
|
import { cn, formatTokens, getStatusCategory, type StatusCategory } from "../../lib/utils";
|
|
30
|
-
import type { CapturedLog } from "../../
|
|
30
|
+
import type { CapturedLog } from "../../contracts";
|
|
31
31
|
import { Badge } from "../ui/badge";
|
|
32
32
|
import { Button } from "../ui/button";
|
|
33
33
|
import { ProviderLogo, detectProvider } from "../providers/ProviderLogo";
|
|
@@ -8,7 +8,7 @@ import { Tooltip, TooltipTrigger, TooltipContent, TooltipProvider } from "../ui/
|
|
|
8
8
|
import { Dialog, DialogContent, DialogHeader, DialogTitle } from "../ui/dialog";
|
|
9
9
|
import { Tabs, TabsContent, TabsList, TabsTrigger } from "../ui/tabs";
|
|
10
10
|
import { ResponseView } from "./ResponseView";
|
|
11
|
-
import { CapturedLogSchema, type CapturedLog } from "../../
|
|
11
|
+
import { CapturedLogSchema, type CapturedLog } from "../../contracts";
|
|
12
12
|
import { dispatchLogFocusRequest } from "./logFocus";
|
|
13
13
|
import {
|
|
14
14
|
buildReplayComparisons,
|
|
@@ -3,7 +3,7 @@ import type { JSX } from "react";
|
|
|
3
3
|
import { memo } from "react";
|
|
4
4
|
import { useMemo } from "react";
|
|
5
5
|
import { cn, formatTokens, getStatusCategory, type StatusCategory } from "../../lib/utils";
|
|
6
|
-
import type {
|
|
6
|
+
import type { ApiFormat } from "../../contracts";
|
|
7
7
|
import { AnswerMarkdown } from "./AnswerMarkdown";
|
|
8
8
|
import { formatViewFor } from "./formats";
|
|
9
9
|
import { getLogFormatAdapter } from "./log-formats";
|
|
@@ -16,7 +16,7 @@ export type ResponseViewProps = {
|
|
|
16
16
|
outputTokens: number | null;
|
|
17
17
|
cacheCreationInputTokens?: number | null;
|
|
18
18
|
cacheReadInputTokens?: number | null;
|
|
19
|
-
apiFormat?:
|
|
19
|
+
apiFormat?: ApiFormat;
|
|
20
20
|
/** SSE error message from streaming response */
|
|
21
21
|
error?: string | null;
|
|
22
22
|
};
|
|
@@ -3,7 +3,7 @@ import { ChevronDown, ChevronRight, Loader2 } from "lucide-react";
|
|
|
3
3
|
import { Badge } from "../ui/badge";
|
|
4
4
|
import { JsonViewer } from "../ui/json-viewer";
|
|
5
5
|
import { Tooltip, TooltipTrigger, TooltipContent, TooltipProvider } from "../ui/tooltip";
|
|
6
|
-
import type { StreamingChunk } from "../../
|
|
6
|
+
import type { StreamingChunk } from "../../contracts";
|
|
7
7
|
|
|
8
8
|
export type StreamingChunkSequenceProps = {
|
|
9
9
|
logId: number;
|
|
@@ -3,7 +3,7 @@ import { AlertTriangle, ChevronRight, Clock, Zap } from "lucide-react";
|
|
|
3
3
|
import { isTurnBoundary } from "../../lib/stopReason";
|
|
4
4
|
import type { TimeDisplayFormat } from "../../lib/runtimeConfig";
|
|
5
5
|
import { cn, formatTokens } from "../../lib/utils";
|
|
6
|
-
import type { CapturedLog } from "../../
|
|
6
|
+
import type { CapturedLog } from "../../contracts";
|
|
7
7
|
import { getCrabVariant } from "../ui/crab-variants";
|
|
8
8
|
import { ProviderLogo, detectProvider, type Provider } from "../providers/ProviderLogo";
|
|
9
9
|
import { Tooltip, TooltipContent, TooltipProvider, TooltipTrigger } from "../ui/tooltip";
|
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
import type { ProviderConfig } from "../../../lib/providerContract";
|
|
2
|
-
import type { CapturedLog } from "../../../
|
|
2
|
+
import type { CapturedLog } from "../../../contracts";
|
|
3
3
|
import { getLogFormatAdapter, resolveLogFormat } from "../log-formats";
|
|
4
4
|
import {
|
|
5
5
|
analyzeContextIntelligence,
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
import { Brain, ChevronDown, ChevronRight, Terminal } from "lucide-react";
|
|
2
2
|
import { type JSX, memo, useState } from "react";
|
|
3
|
-
import type { ResponseContentBlockType } from "../../../../
|
|
3
|
+
import type { ResponseContentBlockType } from "../../../../contracts/anthropic";
|
|
4
4
|
import { AnswerMarkdown } from "../../AnswerMarkdown";
|
|
5
5
|
import { Badge } from "../../../ui/badge";
|
|
6
6
|
import { Collapsible, CollapsibleContent, CollapsibleTrigger } from "../../../ui/collapsible";
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
import { StopCircle, Zap } from "lucide-react";
|
|
2
2
|
import { memo, type JSX } from "react";
|
|
3
|
-
import type {
|
|
3
|
+
import type { AnthropicResponse } from "../../../../contracts/anthropic";
|
|
4
4
|
import { formatTokens } from "../../../../lib/utils";
|
|
5
5
|
import { Badge } from "../../../ui/badge";
|
|
6
6
|
import { Separator } from "../../../ui/separator";
|
|
@@ -9,7 +9,7 @@ import { ResponseContentBlockRenderer } from "./ContentBlocks";
|
|
|
9
9
|
export const StructuredResponseViewAnthropic = memo(function StructuredResponseViewAnthropic({
|
|
10
10
|
response,
|
|
11
11
|
}: {
|
|
12
|
-
response:
|
|
12
|
+
response: AnthropicResponse;
|
|
13
13
|
}): JSX.Element {
|
|
14
14
|
return (
|
|
15
15
|
<div className="space-y-3">
|
|
@@ -1,5 +1,7 @@
|
|
|
1
1
|
import type { JSX } from "react";
|
|
2
|
-
import type {
|
|
2
|
+
import type { ApiFormat } from "../../../contracts";
|
|
3
|
+
import type { AnthropicResponse } from "../../../contracts/anthropic";
|
|
4
|
+
import type { OpenAIResponse } from "../../../contracts/openai";
|
|
3
5
|
import { StructuredResponseViewAnthropic } from "./anthropic/ResponseView";
|
|
4
6
|
import { OpenAIResponseView } from "./openai/ResponseView";
|
|
5
7
|
|
|
@@ -15,12 +17,12 @@ function isOpenAIResponse(response: unknown): response is OpenAIResponse {
|
|
|
15
17
|
return isRecord(response) && response.object === "chat.completion";
|
|
16
18
|
}
|
|
17
19
|
|
|
18
|
-
function isAnthropicResponse(response: unknown): response is
|
|
20
|
+
function isAnthropicResponse(response: unknown): response is AnthropicResponse {
|
|
19
21
|
return isRecord(response) && response.type === "message" && Array.isArray(response.content);
|
|
20
22
|
}
|
|
21
23
|
|
|
22
24
|
export function formatViewFor(
|
|
23
|
-
apiFormat:
|
|
25
|
+
apiFormat: ApiFormat | undefined,
|
|
24
26
|
response: unknown,
|
|
25
27
|
): JSX.Element | null {
|
|
26
28
|
if (apiFormat === "openai" && isOpenAIResponse(response)) {
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
import { StopCircle, Terminal, Zap } from "lucide-react";
|
|
2
2
|
import { memo, useState, type JSX } from "react";
|
|
3
|
-
import type { OpenAIResponse, OpenAIToolCall } from "../../../../
|
|
3
|
+
import type { OpenAIResponse, OpenAIToolCall } from "../../../../contracts/openai";
|
|
4
4
|
import { formatTokens } from "../../../../lib/utils";
|
|
5
5
|
import { AnswerMarkdown } from "../../AnswerMarkdown";
|
|
6
6
|
import { Badge } from "../../../ui/badge";
|
|
@@ -1,7 +1,4 @@
|
|
|
1
|
-
import {
|
|
2
|
-
AnthropicRequestSchema,
|
|
3
|
-
AnthropicResponseSchema,
|
|
4
|
-
} from "../../../proxy/formats/anthropic/schemas";
|
|
1
|
+
import { AnthropicRequestSchema, AnthropicResponseSchema } from "../../../contracts/anthropic";
|
|
5
2
|
import type { AnatomySegment } from "../anatomy/types";
|
|
6
3
|
import { countCharacters, estimateTokens } from "../anatomy/tokenEstimate";
|
|
7
4
|
import type { LogFormatAdapter } from "./types";
|
|
@@ -1,22 +1,22 @@
|
|
|
1
|
-
import {
|
|
2
|
-
import type {
|
|
1
|
+
import { apiFormatForPath } from "../../../proxy/formats";
|
|
2
|
+
import type { ApiFormat, CapturedLog } from "../../../contracts";
|
|
3
3
|
import { anthropicLogFormatAdapter } from "./anthropic";
|
|
4
4
|
import { openAILogFormatAdapter } from "./openai";
|
|
5
5
|
import type { LogFormatAdapter } from "./types";
|
|
6
6
|
import { unknownLogFormatAdapter } from "./unknown";
|
|
7
7
|
|
|
8
|
-
const ADAPTERS: Record<
|
|
8
|
+
const ADAPTERS: Record<ApiFormat, LogFormatAdapter> = {
|
|
9
9
|
anthropic: anthropicLogFormatAdapter,
|
|
10
10
|
openai: openAILogFormatAdapter,
|
|
11
11
|
unknown: unknownLogFormatAdapter,
|
|
12
12
|
};
|
|
13
13
|
|
|
14
|
-
export function getLogFormatAdapter(format:
|
|
14
|
+
export function getLogFormatAdapter(format: ApiFormat): LogFormatAdapter {
|
|
15
15
|
return ADAPTERS[format];
|
|
16
16
|
}
|
|
17
17
|
|
|
18
|
-
export function resolveLogFormat(log: Pick<CapturedLog, "path" | "apiFormat">):
|
|
19
|
-
const pathFormat =
|
|
18
|
+
export function resolveLogFormat(log: Pick<CapturedLog, "path" | "apiFormat">): ApiFormat {
|
|
19
|
+
const pathFormat = apiFormatForPath(log.path);
|
|
20
20
|
return pathFormat === "unknown" ? log.apiFormat : pathFormat;
|
|
21
21
|
}
|
|
22
22
|
|
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import { OpenAIRequestSchema, parseOpenAIResponse } from "../../../
|
|
1
|
+
import { OpenAIRequestSchema, parseOpenAIResponse } from "../../../contracts/openai";
|
|
2
2
|
import type { AnatomySegment } from "../anatomy/types";
|
|
3
3
|
import { countCharacters, estimateTokens } from "../anatomy/tokenEstimate";
|
|
4
4
|
import type { LogFormatAdapter } from "./types";
|
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import type {
|
|
1
|
+
import type { ApiFormat } from "../../../contracts";
|
|
2
2
|
import type { AnatomySegment } from "../anatomy/types";
|
|
3
3
|
|
|
4
4
|
export type RequestAnalysis = {
|
|
@@ -14,7 +14,7 @@ export type ResponseAnalysis = {
|
|
|
14
14
|
};
|
|
15
15
|
|
|
16
16
|
export type LogFormatAdapter = {
|
|
17
|
-
readonly format:
|
|
17
|
+
readonly format: ApiFormat;
|
|
18
18
|
analyzeRequest(rawBody: string | null): RequestAnalysis;
|
|
19
19
|
analyzeResponse(responseText: string | null): ResponseAnalysis;
|
|
20
20
|
/**
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
import { extractStopReason, isTurnBoundary, type StopReason } from "../../lib/stopReason";
|
|
2
2
|
import { safeGetOwnProperty } from "../../lib/objectUtils";
|
|
3
|
-
import type { CapturedLog } from "../../
|
|
3
|
+
import type { CapturedLog } from "../../contracts";
|
|
4
4
|
import { resolveLogFormat } from "./log-formats";
|
|
5
5
|
|
|
6
6
|
export type TurnEntry = {
|