opencode-tps-meter 0.1.5 → 0.1.6
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/constants.d.ts +9 -3
- package/dist/constants.d.ts.map +1 -1
- package/dist/index.d.ts +1 -1
- package/dist/index.d.ts.map +1 -1
- package/dist/index.js +340 -66
- package/dist/index.mjs +340 -66
- package/dist/tracker.d.ts.map +1 -1
- package/dist/types.d.ts +37 -1
- package/dist/types.d.ts.map +1 -1
- package/dist/ui.d.ts.map +1 -1
- package/package.json +1 -1
package/dist/constants.d.ts
CHANGED
|
@@ -15,11 +15,17 @@ export declare const MAX_BUFFER_SIZE = 100;
|
|
|
15
15
|
/** Minimum window duration for TPS calculation (seconds) to avoid division by near-zero */
|
|
16
16
|
export declare const MIN_WINDOW_DURATION_SECONDS = 0.1;
|
|
17
17
|
/** Token count threshold to trigger burst smoothing (tokens) */
|
|
18
|
-
export declare const BURST_TOKEN_THRESHOLD =
|
|
18
|
+
export declare const BURST_TOKEN_THRESHOLD = 50;
|
|
19
19
|
/** Default EWMA half-life (ms) for smoothing normal streaming */
|
|
20
20
|
export declare const DEFAULT_EWMA_HALF_LIFE_MS = 500;
|
|
21
|
-
/** EWMA half-life (ms) applied during bursts */
|
|
22
|
-
export declare const BURST_EWMA_HALF_LIFE_MS =
|
|
21
|
+
/** EWMA half-life (ms) applied during medium bursts (50-200 tokens) */
|
|
22
|
+
export declare const BURST_EWMA_HALF_LIFE_MS = 3000;
|
|
23
|
+
/** Token count threshold for very large bursts (tool outputs) */
|
|
24
|
+
export declare const LARGE_BURST_THRESHOLD = 200;
|
|
25
|
+
/** EWMA half-life (ms) for very large bursts */
|
|
26
|
+
export declare const LARGE_BURST_EWMA_HALF_LIFE_MS = 5000;
|
|
27
|
+
/** Maximum initial TPS value to prevent startup spikes */
|
|
28
|
+
export declare const MAX_INITIAL_TPS = 100;
|
|
23
29
|
/** Default UI update interval in milliseconds */
|
|
24
30
|
export declare const DEFAULT_UPDATE_INTERVAL_MS = 50;
|
|
25
31
|
/** Minimum interval between toast updates (ms) - prevents UI flooding */
|
package/dist/constants.d.ts.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"constants.d.ts","sourceRoot":"","sources":["../src/constants.ts"],"names":[],"mappings":"AAAA;;;;;;;GAOG;AAMH,8EAA8E;AAC9E,eAAO,MAAM,kBAAkB,MAAM,CAAC;AAEtC,+DAA+D;AAC/D,eAAO,MAAM,yBAAyB,OAAO,CAAC;AAE9C,mDAAmD;AACnD,eAAO,MAAM,eAAe,MAAM,CAAC;AAEnC,2FAA2F;AAC3F,eAAO,MAAM,2BAA2B,MAAM,CAAC;AAE/C,gEAAgE;AAChE,eAAO,MAAM,qBAAqB,
|
|
1
|
+
{"version":3,"file":"constants.d.ts","sourceRoot":"","sources":["../src/constants.ts"],"names":[],"mappings":"AAAA;;;;;;;GAOG;AAMH,8EAA8E;AAC9E,eAAO,MAAM,kBAAkB,MAAM,CAAC;AAEtC,+DAA+D;AAC/D,eAAO,MAAM,yBAAyB,OAAO,CAAC;AAE9C,mDAAmD;AACnD,eAAO,MAAM,eAAe,MAAM,CAAC;AAEnC,2FAA2F;AAC3F,eAAO,MAAM,2BAA2B,MAAM,CAAC;AAE/C,gEAAgE;AAChE,eAAO,MAAM,qBAAqB,KAAK,CAAC;AAExC,iEAAiE;AACjE,eAAO,MAAM,yBAAyB,MAAM,CAAC;AAE7C,uEAAuE;AACvE,eAAO,MAAM,uBAAuB,OAAO,CAAC;AAE5C,iEAAiE;AACjE,eAAO,MAAM,qBAAqB,MAAM,CAAC;AAEzC,gDAAgD;AAChD,eAAO,MAAM,6BAA6B,OAAO,CAAC;AAElD,0DAA0D;AAC1D,eAAO,MAAM,eAAe,MAAM,CAAC;AAMnC,iDAAiD;AACjD,eAAO,MAAM,0BAA0B,KAAK,CAAC;AAE7C,yEAAyE;AACzE,eAAO,MAAM,qBAAqB,MAAM,CAAC;AAEzC,qDAAqD;AACrD,eAAO,MAAM,yBAAyB,QAAQ,CAAC;AAE/C,qDAAqD;AACrD,eAAO,MAAM,uBAAuB,OAAO,CAAC;AAM5C,sEAAsE;AACtE,eAAO,MAAM,kBAAkB,QAAgB,CAAC;AAEhD,qEAAqE;AACrE,eAAO,MAAM,mBAAmB,QAAQ,CAAC;AAMzC,yEAAyE;AACzE,eAAO,MAAM,WAAW,IAAI,CAAC;AAE7B,sEAAsE;AACtE,eAAO,MAAM,WAAW,IAAI,CAAC;AAE7B,qEAAqE;AACrE,eAAO,MAAM,cAAc,OAAO,CAAC;AAMnC,uDAAuD;AACvD,eAAO,MAAM,0BAA0B,KAAK,CAAC;AAE7C,yDAAyD;AACzD,eAAO,MAAM,0BAA0B,KAAK,CAAC;AAM7C,2DAA2D;AAC3D,eAAO,MAAM,sBAAsB,aAAqC,CAAC;AAEzE,0DAA0D;AAC1D,eAAO,MAAM,oBAAoB,aAAiC,CAAC"}
|
package/dist/index.d.ts
CHANGED
|
@@ -13,5 +13,5 @@ import type { PluginContext, PluginHandlers } from "./types.js";
|
|
|
13
13
|
* @returns {PluginHandlers | Record<string, never>} - Event handlers or empty object if disabled
|
|
14
14
|
*/
|
|
15
15
|
export default function TpsMeterPlugin(context: PluginContext): PluginHandlers | Record<string, never>;
|
|
16
|
-
export type { BufferEntry, TPSTrackerOptions, TPSTracker, UIManager, TokenCounter, Config, OpenCodeClient, DisplayState, PluginContext, Logger, MessageEvent, PluginHandlers, } from "./types.js";
|
|
16
|
+
export type { BufferEntry, TPSTrackerOptions, TPSTracker, UIManager, TokenCounter, Config, OpenCodeClient, DisplayState, AgentDisplayState, AgentIdentity, PluginContext, Logger, MessageEvent, PluginHandlers, } from "./types.js";
|
|
17
17
|
//# sourceMappingURL=index.d.ts.map
|
package/dist/index.d.ts.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAAA;;;;;;GAMG;AAEH,OAAO,KAAK,EACV,aAAa,EACb,cAAc,
|
|
1
|
+
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAAA;;;;;;GAMG;AAEH,OAAO,KAAK,EACV,aAAa,EACb,cAAc,EAOf,MAAM,YAAY,CAAC;AAoHpB;;;;;GAKG;AACH,MAAM,CAAC,OAAO,UAAU,cAAc,CACpC,OAAO,EAAE,aAAa,GACrB,cAAc,GAAG,MAAM,CAAC,MAAM,EAAE,KAAK,CAAC,CAmwBxC;AAGD,YAAY,EACV,WAAW,EACX,iBAAiB,EACjB,UAAU,EACV,SAAS,EACT,YAAY,EACZ,MAAM,EACN,cAAc,EACd,YAAY,EACZ,iBAAiB,EACjB,aAAa,EACb,aAAa,EACb,MAAM,EACN,YAAY,EACZ,cAAc,GACf,MAAM,YAAY,CAAC"}
|
package/dist/index.js
CHANGED
|
@@ -50,9 +50,12 @@ var MIN_TPS_ELAPSED_MS = 250;
|
|
|
50
50
|
var DEFAULT_ROLLING_WINDOW_MS = 1000;
|
|
51
51
|
var MAX_BUFFER_SIZE = 100;
|
|
52
52
|
var MIN_WINDOW_DURATION_SECONDS = 0.1;
|
|
53
|
-
var BURST_TOKEN_THRESHOLD =
|
|
53
|
+
var BURST_TOKEN_THRESHOLD = 50;
|
|
54
54
|
var DEFAULT_EWMA_HALF_LIFE_MS = 500;
|
|
55
|
-
var BURST_EWMA_HALF_LIFE_MS =
|
|
55
|
+
var BURST_EWMA_HALF_LIFE_MS = 3000;
|
|
56
|
+
var LARGE_BURST_THRESHOLD = 200;
|
|
57
|
+
var LARGE_BURST_EWMA_HALF_LIFE_MS = 5000;
|
|
58
|
+
var MAX_INITIAL_TPS = 100;
|
|
56
59
|
var DEFAULT_UPDATE_INTERVAL_MS = 50;
|
|
57
60
|
var MIN_TOAST_INTERVAL_MS = 150;
|
|
58
61
|
var DEFAULT_TOAST_DURATION_MS = 20000;
|
|
@@ -124,11 +127,18 @@ function createTracker(options = {}) {
|
|
|
124
127
|
pruneBuffer(ts);
|
|
125
128
|
const rawTPS = calculateRawTPS(ts);
|
|
126
129
|
if (!hasSmoothedValue) {
|
|
127
|
-
smoothedTps = rawTPS;
|
|
130
|
+
smoothedTps = Math.min(rawTPS, MAX_INITIAL_TPS);
|
|
128
131
|
hasSmoothedValue = true;
|
|
129
132
|
} else {
|
|
130
133
|
const timeDelta = Math.max(1, ts - lastSmoothedAt);
|
|
131
|
-
|
|
134
|
+
let halfLife;
|
|
135
|
+
if (count > LARGE_BURST_THRESHOLD) {
|
|
136
|
+
halfLife = LARGE_BURST_EWMA_HALF_LIFE_MS;
|
|
137
|
+
} else if (count > BURST_TOKEN_THRESHOLD) {
|
|
138
|
+
halfLife = BURST_EWMA_HALF_LIFE_MS;
|
|
139
|
+
} else {
|
|
140
|
+
halfLife = DEFAULT_EWMA_HALF_LIFE_MS;
|
|
141
|
+
}
|
|
132
142
|
const alpha = Math.exp(-Math.LN2 * timeDelta / halfLife);
|
|
133
143
|
smoothedTps = alpha * smoothedTps + (1 - alpha) * rawTPS;
|
|
134
144
|
}
|
|
@@ -204,7 +214,7 @@ function createUIManager(client, config) {
|
|
|
204
214
|
function formatNumberWithCommas(num) {
|
|
205
215
|
return num.toLocaleString("en-US");
|
|
206
216
|
}
|
|
207
|
-
function
|
|
217
|
+
function formatPrimaryLine(state) {
|
|
208
218
|
const parts = [];
|
|
209
219
|
if (uiConfig.showInstant || uiConfig.showAverage) {
|
|
210
220
|
const tpsParts = [];
|
|
@@ -214,7 +224,9 @@ function createUIManager(client, config) {
|
|
|
214
224
|
if (uiConfig.showAverage) {
|
|
215
225
|
tpsParts.push(`(avg ${state.avgTps.toFixed(1)})`);
|
|
216
226
|
}
|
|
217
|
-
|
|
227
|
+
if (tpsParts.length > 0) {
|
|
228
|
+
parts.push(tpsParts.join(" "));
|
|
229
|
+
}
|
|
218
230
|
}
|
|
219
231
|
if (uiConfig.showTotalTokens) {
|
|
220
232
|
parts.push(`tokens: ${formatNumberWithCommas(state.totalTokens)}`);
|
|
@@ -222,7 +234,30 @@ function createUIManager(client, config) {
|
|
|
222
234
|
if (uiConfig.showElapsed) {
|
|
223
235
|
parts.push(formatElapsedTime(state.elapsedMs));
|
|
224
236
|
}
|
|
225
|
-
return parts.join(" | ");
|
|
237
|
+
return parts.length > 0 ? parts.join(" | ") : "TPS meter";
|
|
238
|
+
}
|
|
239
|
+
function formatAgentLine(agent) {
|
|
240
|
+
const segments = [];
|
|
241
|
+
segments.push(`${agent.instantTps.toFixed(1)} (avg ${agent.avgTps.toFixed(1)})`);
|
|
242
|
+
segments.push(`tokens: ${formatNumberWithCommas(agent.totalTokens)}`);
|
|
243
|
+
if (uiConfig.showElapsed) {
|
|
244
|
+
segments.push(formatElapsedTime(agent.elapsedMs));
|
|
245
|
+
}
|
|
246
|
+
return `${agent.label} ${segments.join(" | ")}`.trim();
|
|
247
|
+
}
|
|
248
|
+
function formatDisplay(state) {
|
|
249
|
+
const lines = [];
|
|
250
|
+
const hasMainActivity = state.totalTokens > 0;
|
|
251
|
+
if (hasMainActivity) {
|
|
252
|
+
lines.push(formatPrimaryLine(state));
|
|
253
|
+
}
|
|
254
|
+
const agentLines = (state.agents ?? []).filter((agent) => agent.totalTokens > 0).map((agent) => formatAgentLine(agent));
|
|
255
|
+
lines.push(...agentLines);
|
|
256
|
+
if (lines.length === 0) {
|
|
257
|
+
return "TPS meter (idle)";
|
|
258
|
+
}
|
|
259
|
+
return lines.join(`
|
|
260
|
+
`);
|
|
226
261
|
}
|
|
227
262
|
function getColorVariant(instantTps, isFinal) {
|
|
228
263
|
if (isFinal) {
|
|
@@ -321,12 +356,13 @@ function createUIManager(client, config) {
|
|
|
321
356
|
}, delay);
|
|
322
357
|
}
|
|
323
358
|
return {
|
|
324
|
-
updateDisplay(instantTps, avgTps, totalTokens, elapsedMs) {
|
|
359
|
+
updateDisplay(instantTps, avgTps, totalTokens, elapsedMs, agents) {
|
|
325
360
|
pendingState = {
|
|
326
361
|
instantTps,
|
|
327
362
|
avgTps,
|
|
328
363
|
totalTokens,
|
|
329
|
-
elapsedMs
|
|
364
|
+
elapsedMs,
|
|
365
|
+
agents: agents && agents.length > 0 ? agents : undefined
|
|
330
366
|
};
|
|
331
367
|
scheduleFlush();
|
|
332
368
|
},
|
|
@@ -650,34 +686,234 @@ function TpsMeterPlugin(context) {
|
|
|
650
686
|
logger.debug("[TpsMeter] Plugin disabled by configuration");
|
|
651
687
|
return {};
|
|
652
688
|
}
|
|
653
|
-
const
|
|
689
|
+
const sessionTrackers = new Map;
|
|
654
690
|
const partTextCache = new Map;
|
|
655
691
|
const messageTokenCache = new Map;
|
|
656
692
|
const messageRoleCache = new Map;
|
|
657
|
-
const
|
|
658
|
-
|
|
693
|
+
const sessionAgentNameCache = new Map;
|
|
694
|
+
let primarySessionId = null;
|
|
695
|
+
const pendingDisplayTimers = new Map;
|
|
659
696
|
const resolvedConfig = config;
|
|
660
697
|
const ui = createUIManager(safeContext.client || {}, resolvedConfig);
|
|
661
698
|
const tokenizer = createTokenizer(resolvedConfig.fallbackTokenHeuristic === "words_div_0_75" ? "word" : resolvedConfig.fallbackTokenHeuristic === "chars_div_3" ? "code" : "heuristic");
|
|
662
699
|
logger.info("[TpsMeter] Plugin initialized and ready");
|
|
663
|
-
function
|
|
664
|
-
let
|
|
665
|
-
if (!
|
|
666
|
-
|
|
667
|
-
|
|
668
|
-
|
|
669
|
-
|
|
670
|
-
|
|
700
|
+
function getOrCreateSessionState(sessionId) {
|
|
701
|
+
let state = sessionTrackers.get(sessionId);
|
|
702
|
+
if (!state) {
|
|
703
|
+
state = {
|
|
704
|
+
aggregate: createTracker({
|
|
705
|
+
sessionId,
|
|
706
|
+
rollingWindowMs: resolvedConfig.rollingWindowMs
|
|
707
|
+
}),
|
|
708
|
+
aggregateFirstTokenAt: null,
|
|
709
|
+
messageTrackers: new Map
|
|
710
|
+
};
|
|
711
|
+
sessionTrackers.set(sessionId, state);
|
|
671
712
|
logger.debug(`[TpsMeter] Created tracker for session: ${sessionId}`);
|
|
672
713
|
}
|
|
673
|
-
return
|
|
714
|
+
return state;
|
|
715
|
+
}
|
|
716
|
+
function abbreviateId(id) {
|
|
717
|
+
if (!id || id.length <= 4)
|
|
718
|
+
return id;
|
|
719
|
+
return `${id.slice(0, 4)}…`;
|
|
720
|
+
}
|
|
721
|
+
function buildAgentLabel(messageId, metadata) {
|
|
722
|
+
const typeLabel = metadata?.agent?.type?.trim() || metadata?.agentType?.trim() || metadata?.agent?.name?.trim() || metadata?.name?.trim() || "Subagent";
|
|
723
|
+
const rawId = metadata?.agentId?.trim() || metadata?.agent?.id?.trim() || messageId;
|
|
724
|
+
const identifier = abbreviateId(rawId);
|
|
725
|
+
return `${typeLabel}(${identifier})`;
|
|
726
|
+
}
|
|
727
|
+
function buildTrackerKey(sessionId, messageId, partId, metadata) {
|
|
728
|
+
const agentId = metadata?.agentId?.trim() || metadata?.agent?.id?.trim() || metadata?.agentType?.trim();
|
|
729
|
+
if (agentId) {
|
|
730
|
+
return `${sessionId}:${messageId}:${agentId}`;
|
|
731
|
+
}
|
|
732
|
+
if (partId) {
|
|
733
|
+
return `${sessionId}:${messageId}:${partId}`;
|
|
734
|
+
}
|
|
735
|
+
return `${sessionId}:${messageId}`;
|
|
736
|
+
}
|
|
737
|
+
function getOrCreateMessageTrackerState(sessionId, messageId, partId, metadata) {
|
|
738
|
+
const sessionState = getOrCreateSessionState(sessionId);
|
|
739
|
+
const key = buildTrackerKey(sessionId, messageId, partId, metadata);
|
|
740
|
+
let trackerState = sessionState.messageTrackers.get(key);
|
|
741
|
+
const nextLabel = buildAgentLabel(messageId, metadata);
|
|
742
|
+
if (!trackerState) {
|
|
743
|
+
trackerState = {
|
|
744
|
+
key,
|
|
745
|
+
messageId,
|
|
746
|
+
partId,
|
|
747
|
+
tracker: createTracker({
|
|
748
|
+
sessionId: key,
|
|
749
|
+
rollingWindowMs: resolvedConfig.rollingWindowMs
|
|
750
|
+
}),
|
|
751
|
+
label: nextLabel,
|
|
752
|
+
firstTokenAt: null,
|
|
753
|
+
lastUpdated: 0,
|
|
754
|
+
agent: metadata?.agent,
|
|
755
|
+
agentId: metadata?.agentId,
|
|
756
|
+
agentType: metadata?.agentType
|
|
757
|
+
};
|
|
758
|
+
sessionState.messageTrackers.set(key, trackerState);
|
|
759
|
+
} else if (trackerState.label !== nextLabel) {
|
|
760
|
+
trackerState.label = nextLabel;
|
|
761
|
+
}
|
|
762
|
+
if (metadata?.agent) {
|
|
763
|
+
trackerState.agent = metadata.agent;
|
|
764
|
+
}
|
|
765
|
+
if (metadata?.agentId) {
|
|
766
|
+
trackerState.agentId = metadata.agentId;
|
|
767
|
+
}
|
|
768
|
+
if (metadata?.agentType) {
|
|
769
|
+
trackerState.agentType = metadata.agentType;
|
|
770
|
+
}
|
|
771
|
+
return trackerState;
|
|
772
|
+
}
|
|
773
|
+
function getAllActiveAgentsGlobally(now) {
|
|
774
|
+
const activityWindow = Math.max(resolvedConfig.rollingWindowMs, MIN_TPS_ELAPSED_MS * 4);
|
|
775
|
+
const entries = [];
|
|
776
|
+
for (const [sessionId, sessionState] of sessionTrackers) {
|
|
777
|
+
for (const [trackerKey, trackerState] of sessionState.messageTrackers) {
|
|
778
|
+
if (!trackerState.firstTokenAt)
|
|
779
|
+
continue;
|
|
780
|
+
if (now - trackerState.lastUpdated > activityWindow)
|
|
781
|
+
continue;
|
|
782
|
+
const hasAgentMetadata = Boolean(trackerState.agent || trackerState.agentId || trackerState.agentType);
|
|
783
|
+
let isSubagent = false;
|
|
784
|
+
let label = trackerState.label;
|
|
785
|
+
if (hasAgentMetadata) {
|
|
786
|
+
isSubagent = true;
|
|
787
|
+
} else if (sessionId !== primarySessionId) {
|
|
788
|
+
isSubagent = true;
|
|
789
|
+
const agentName = sessionAgentNameCache.get(sessionId) || "bg";
|
|
790
|
+
const shortId = abbreviateId(sessionId.replace(/^ses_/, ""));
|
|
791
|
+
label = `${agentName}(${shortId})`;
|
|
792
|
+
}
|
|
793
|
+
if (!isSubagent)
|
|
794
|
+
continue;
|
|
795
|
+
entries.push({
|
|
796
|
+
id: trackerKey,
|
|
797
|
+
label,
|
|
798
|
+
instantTps: trackerState.tracker.getSmoothedTPS(),
|
|
799
|
+
avgTps: trackerState.tracker.getAverageTPS(),
|
|
800
|
+
totalTokens: trackerState.tracker.getTotalTokens(),
|
|
801
|
+
elapsedMs: now - trackerState.firstTokenAt
|
|
802
|
+
});
|
|
803
|
+
}
|
|
804
|
+
}
|
|
805
|
+
entries.sort((a, b) => b.instantTps - a.instantTps);
|
|
806
|
+
return entries;
|
|
807
|
+
}
|
|
808
|
+
function isPrimarySessionActive(now) {
|
|
809
|
+
if (!primarySessionId)
|
|
810
|
+
return false;
|
|
811
|
+
const sessionState = sessionTrackers.get(primarySessionId);
|
|
812
|
+
if (!sessionState)
|
|
813
|
+
return false;
|
|
814
|
+
const activityWindow = Math.max(resolvedConfig.rollingWindowMs, MIN_TPS_ELAPSED_MS * 4);
|
|
815
|
+
for (const trackerState of sessionState.messageTrackers.values()) {
|
|
816
|
+
const hasAgentMetadata = Boolean(trackerState.agent || trackerState.agentId || trackerState.agentType);
|
|
817
|
+
if (hasAgentMetadata)
|
|
818
|
+
continue;
|
|
819
|
+
if (trackerState.firstTokenAt && now - trackerState.lastUpdated <= activityWindow) {
|
|
820
|
+
return true;
|
|
821
|
+
}
|
|
822
|
+
}
|
|
823
|
+
return false;
|
|
824
|
+
}
|
|
825
|
+
function getActiveAgentDisplayStates(sessionState, now) {
|
|
826
|
+
const activityWindow = Math.max(resolvedConfig.rollingWindowMs, MIN_TPS_ELAPSED_MS * 4);
|
|
827
|
+
const entries = [];
|
|
828
|
+
for (const trackerState of sessionState.messageTrackers.values()) {
|
|
829
|
+
if (!trackerState.firstTokenAt) {
|
|
830
|
+
continue;
|
|
831
|
+
}
|
|
832
|
+
if (now - trackerState.lastUpdated > activityWindow) {
|
|
833
|
+
continue;
|
|
834
|
+
}
|
|
835
|
+
const hasAgentMetadata = Boolean(trackerState.agent || trackerState.agentId || trackerState.agentType);
|
|
836
|
+
if (!hasAgentMetadata) {
|
|
837
|
+
continue;
|
|
838
|
+
}
|
|
839
|
+
entries.push({
|
|
840
|
+
id: trackerState.messageId,
|
|
841
|
+
label: trackerState.label,
|
|
842
|
+
instantTps: trackerState.tracker.getSmoothedTPS(),
|
|
843
|
+
avgTps: trackerState.tracker.getAverageTPS(),
|
|
844
|
+
totalTokens: trackerState.tracker.getTotalTokens(),
|
|
845
|
+
elapsedMs: now - trackerState.firstTokenAt
|
|
846
|
+
});
|
|
847
|
+
}
|
|
848
|
+
entries.sort((a, b) => b.instantTps - a.instantTps);
|
|
849
|
+
return entries;
|
|
850
|
+
}
|
|
851
|
+
function removeMessageTrackerState(sessionId, messageId) {
|
|
852
|
+
const sessionState = sessionTrackers.get(sessionId);
|
|
853
|
+
if (!sessionState) {
|
|
854
|
+
return;
|
|
855
|
+
}
|
|
856
|
+
for (const [key, state] of sessionState.messageTrackers) {
|
|
857
|
+
if (state.messageId === messageId) {
|
|
858
|
+
sessionState.messageTrackers.delete(key);
|
|
859
|
+
}
|
|
860
|
+
}
|
|
861
|
+
if (sessionState.messageTrackers.size === 0) {
|
|
862
|
+
sessionState.aggregate.reset();
|
|
863
|
+
sessionState.aggregateFirstTokenAt = null;
|
|
864
|
+
}
|
|
865
|
+
}
|
|
866
|
+
function scheduleDisplayTimer(sessionId) {
|
|
867
|
+
const existingTimer = pendingDisplayTimers.get(sessionId);
|
|
868
|
+
if (existingTimer) {
|
|
869
|
+
clearTimeout(existingTimer);
|
|
870
|
+
}
|
|
871
|
+
const timer = setTimeout(() => {
|
|
872
|
+
pendingDisplayTimers.delete(sessionId);
|
|
873
|
+
const sessionState = sessionTrackers.get(sessionId);
|
|
874
|
+
if (!sessionState || !sessionState.aggregateFirstTokenAt) {
|
|
875
|
+
return;
|
|
876
|
+
}
|
|
877
|
+
const now = Date.now();
|
|
878
|
+
const elapsedSinceFirstToken = now - sessionState.aggregateFirstTokenAt;
|
|
879
|
+
if (elapsedSinceFirstToken < MIN_TPS_ELAPSED_MS)
|
|
880
|
+
return;
|
|
881
|
+
const allAgents = getAllActiveAgentsGlobally(now);
|
|
882
|
+
const hasPrimaryActivity = isPrimarySessionActive(now);
|
|
883
|
+
if (hasPrimaryActivity) {
|
|
884
|
+
const smoothedTps = sessionState.aggregate.getSmoothedTPS();
|
|
885
|
+
const avgTps = sessionState.aggregate.getAverageTPS();
|
|
886
|
+
const totalTokens = sessionState.aggregate.getTotalTokens();
|
|
887
|
+
const elapsedMs = sessionState.aggregate.getElapsedMs();
|
|
888
|
+
if (smoothedTps >= resolvedConfig.minVisibleTPS) {
|
|
889
|
+
ui.updateDisplay(smoothedTps, avgTps, totalTokens, elapsedMs, allAgents);
|
|
890
|
+
}
|
|
891
|
+
} else if (allAgents.length > 0) {
|
|
892
|
+
ui.updateDisplay(0, 0, 0, 0, allAgents);
|
|
893
|
+
}
|
|
894
|
+
logger.debug(`[TpsMeter] Timer-triggered display for session ${sessionId}`);
|
|
895
|
+
}, MIN_TPS_ELAPSED_MS + 10);
|
|
896
|
+
pendingDisplayTimers.set(sessionId, timer);
|
|
897
|
+
}
|
|
898
|
+
function clearDisplayTimer(sessionId) {
|
|
899
|
+
const timer = pendingDisplayTimers.get(sessionId);
|
|
900
|
+
if (timer) {
|
|
901
|
+
clearTimeout(timer);
|
|
902
|
+
pendingDisplayTimers.delete(sessionId);
|
|
903
|
+
}
|
|
674
904
|
}
|
|
675
905
|
function cleanup() {
|
|
676
906
|
logger.debug("[TpsMeter] Cleaning up all trackers and UI");
|
|
677
|
-
|
|
907
|
+
for (const timer of pendingDisplayTimers.values()) {
|
|
908
|
+
clearTimeout(timer);
|
|
909
|
+
}
|
|
910
|
+
pendingDisplayTimers.clear();
|
|
911
|
+
sessionTrackers.clear();
|
|
912
|
+
partTextCache.clear();
|
|
913
|
+
messageTokenCache.clear();
|
|
678
914
|
messageRoleCache.clear();
|
|
679
|
-
|
|
680
|
-
|
|
915
|
+
sessionAgentNameCache.clear();
|
|
916
|
+
primarySessionId = null;
|
|
681
917
|
ui.clear();
|
|
682
918
|
}
|
|
683
919
|
function handleMessagePartUpdated(event) {
|
|
@@ -696,11 +932,7 @@ function TpsMeterPlugin(context) {
|
|
|
696
932
|
partTextCache.set(sessionId, sessionCache);
|
|
697
933
|
const cacheKey = `${part.messageID}:${part.id}:${part.type}`;
|
|
698
934
|
const previousText = sessionCache.get(cacheKey) || "";
|
|
699
|
-
|
|
700
|
-
delta = partText.slice(previousText.length);
|
|
701
|
-
} else {
|
|
702
|
-
delta = partText;
|
|
703
|
-
}
|
|
935
|
+
delta = partText.startsWith(previousText) ? partText.slice(previousText.length) : partText;
|
|
704
936
|
sessionCache.set(cacheKey, partText);
|
|
705
937
|
}
|
|
706
938
|
if (!delta || delta.length === 0) {
|
|
@@ -711,35 +943,52 @@ function TpsMeterPlugin(context) {
|
|
|
711
943
|
if (role !== "assistant") {
|
|
712
944
|
return;
|
|
713
945
|
}
|
|
714
|
-
const
|
|
715
|
-
const
|
|
716
|
-
|
|
717
|
-
|
|
718
|
-
|
|
719
|
-
|
|
720
|
-
}
|
|
946
|
+
const sessionState = getOrCreateSessionState(sessionId);
|
|
947
|
+
const messageTracker = getOrCreateMessageTrackerState(sessionId, part.messageID, part.id, {
|
|
948
|
+
agent: part.agent,
|
|
949
|
+
agentId: part.agentId,
|
|
950
|
+
agentType: part.agentType,
|
|
951
|
+
name: part.name
|
|
952
|
+
});
|
|
721
953
|
const now = Date.now();
|
|
722
954
|
cleanupStaleMessages(now);
|
|
723
|
-
|
|
724
|
-
|
|
725
|
-
|
|
726
|
-
|
|
727
|
-
|
|
728
|
-
|
|
955
|
+
if (!sessionState.aggregateFirstTokenAt) {
|
|
956
|
+
sessionState.aggregateFirstTokenAt = now;
|
|
957
|
+
scheduleDisplayTimer(sessionId);
|
|
958
|
+
}
|
|
959
|
+
if (!messageTracker.firstTokenAt) {
|
|
960
|
+
messageTracker.firstTokenAt = now;
|
|
961
|
+
const hasAgentMetadata = Boolean(messageTracker.agent || messageTracker.agentId || messageTracker.agentType);
|
|
962
|
+
if (!hasAgentMetadata && primarySessionId === null) {
|
|
963
|
+
primarySessionId = sessionId;
|
|
964
|
+
logger.debug(`[TpsMeter] Primary session set to: ${sessionId}`);
|
|
965
|
+
}
|
|
966
|
+
const metaLabel = messageTracker.label;
|
|
967
|
+
const metaInfo = messageTracker.agent || messageTracker.agentId || messageTracker.agentType ? `agent=${messageTracker.agent?.type ?? messageTracker.agentType ?? "?"} id=${messageTracker.agent?.id ?? messageTracker.agentId ?? "?"}` : "agent=none";
|
|
968
|
+
logger.info(`[TpsMeter][Debug] tracker initialized ${metaLabel} (${metaInfo}) session=${sessionId} message=${part.messageID} part=${part.id ?? "?"}`);
|
|
729
969
|
}
|
|
970
|
+
messageTracker.lastUpdated = now;
|
|
730
971
|
const tokenCount = tokenizer.count(delta);
|
|
731
|
-
|
|
972
|
+
sessionState.aggregate.recordTokens(tokenCount, now);
|
|
973
|
+
messageTracker.tracker.recordTokens(tokenCount, now);
|
|
732
974
|
const messageCache = messageTokenCache.get(sessionId) || new Map;
|
|
733
975
|
messageTokenCache.set(sessionId, messageCache);
|
|
734
|
-
const previousTokens = messageCache.get(
|
|
735
|
-
messageCache.set(
|
|
736
|
-
const smoothedTps =
|
|
737
|
-
const avgTps =
|
|
738
|
-
const totalTokens =
|
|
739
|
-
const elapsedMs =
|
|
740
|
-
const elapsedSinceFirstToken = Math.max(0, now -
|
|
741
|
-
if (elapsedSinceFirstToken >= MIN_TPS_ELAPSED_MS
|
|
742
|
-
|
|
976
|
+
const previousTokens = messageCache.get(part.messageID) ?? 0;
|
|
977
|
+
messageCache.set(part.messageID, previousTokens + tokenCount);
|
|
978
|
+
const smoothedTps = sessionState.aggregate.getSmoothedTPS();
|
|
979
|
+
const avgTps = sessionState.aggregate.getAverageTPS();
|
|
980
|
+
const totalTokens = sessionState.aggregate.getTotalTokens();
|
|
981
|
+
const elapsedMs = sessionState.aggregate.getElapsedMs();
|
|
982
|
+
const elapsedSinceFirstToken = sessionState.aggregateFirstTokenAt === null ? 0 : Math.max(0, now - sessionState.aggregateFirstTokenAt);
|
|
983
|
+
if (elapsedSinceFirstToken >= MIN_TPS_ELAPSED_MS) {
|
|
984
|
+
clearDisplayTimer(sessionId);
|
|
985
|
+
const allAgents = getAllActiveAgentsGlobally(now);
|
|
986
|
+
const hasPrimaryActivity = isPrimarySessionActive(now) && smoothedTps >= resolvedConfig.minVisibleTPS;
|
|
987
|
+
if (hasPrimaryActivity) {
|
|
988
|
+
ui.updateDisplay(smoothedTps, avgTps, totalTokens, elapsedMs, allAgents);
|
|
989
|
+
} else if (allAgents.length > 0) {
|
|
990
|
+
ui.updateDisplay(0, 0, 0, 0, allAgents);
|
|
991
|
+
}
|
|
743
992
|
}
|
|
744
993
|
logger.debug(`[TpsMeter] Session ${sessionId}: +${tokenCount} tokens, TPS: ${smoothedTps.toFixed(1)} (avg: ${avgTps.toFixed(1)})`);
|
|
745
994
|
}
|
|
@@ -751,25 +1000,30 @@ function TpsMeterPlugin(context) {
|
|
|
751
1000
|
const roleCache = messageRoleCache.get(info.sessionID) || new Map;
|
|
752
1001
|
messageRoleCache.set(info.sessionID, roleCache);
|
|
753
1002
|
roleCache.set(info.id, info.role);
|
|
1003
|
+
if (info.agent && typeof info.agent === "string") {
|
|
1004
|
+
sessionAgentNameCache.set(info.sessionID, info.agent);
|
|
1005
|
+
}
|
|
754
1006
|
if (info.role === "assistant") {
|
|
755
1007
|
const sessionId = info.sessionID;
|
|
756
|
-
const tracker = trackers.get(sessionId);
|
|
757
1008
|
const sessionCache = partTextCache.get(sessionId);
|
|
758
1009
|
const tokenCache = messageTokenCache.get(sessionId) || new Map;
|
|
759
1010
|
messageTokenCache.set(sessionId, tokenCache);
|
|
760
|
-
const firstTokenCache = messageFirstTokenCache.get(sessionId) || new Map;
|
|
761
|
-
messageFirstTokenCache.set(sessionId, firstTokenCache);
|
|
762
1011
|
const outputTokens = info.tokens?.output ?? 0;
|
|
763
1012
|
const reasoningTokens = info.tokens?.reasoning ?? 0;
|
|
764
1013
|
const reportedTokens = outputTokens + reasoningTokens;
|
|
765
1014
|
const messageId = info.id;
|
|
1015
|
+
const messageTracker = getOrCreateMessageTrackerState(sessionId, messageId, undefined, {
|
|
1016
|
+
agent: info.agent,
|
|
1017
|
+
agentId: info.agentId,
|
|
1018
|
+
agentType: info.agentType
|
|
1019
|
+
});
|
|
766
1020
|
const previous = tokenCache.get(messageId) ?? 0;
|
|
767
1021
|
const nextTokens = Math.max(previous, reportedTokens);
|
|
768
1022
|
tokenCache.set(messageId, nextTokens);
|
|
769
|
-
if (info.time?.completed
|
|
1023
|
+
if (info.time?.completed) {
|
|
770
1024
|
const completedAt = info.time?.completed ?? Date.now();
|
|
771
1025
|
const createdAt = info.time?.created ?? completedAt;
|
|
772
|
-
const firstTokenAt =
|
|
1026
|
+
const firstTokenAt = messageTracker.firstTokenAt ?? createdAt;
|
|
773
1027
|
const elapsedMs = Math.max(0, completedAt - firstTokenAt);
|
|
774
1028
|
const cachedTokens = tokenCache.get(messageId) ?? 0;
|
|
775
1029
|
const totalTokens = reportedTokens > 0 ? reportedTokens : cachedTokens;
|
|
@@ -791,7 +1045,7 @@ function TpsMeterPlugin(context) {
|
|
|
791
1045
|
if (info.time?.completed) {
|
|
792
1046
|
tokenCache.delete(messageId);
|
|
793
1047
|
roleCache.delete(messageId);
|
|
794
|
-
|
|
1048
|
+
removeMessageTrackerState(sessionId, messageId);
|
|
795
1049
|
}
|
|
796
1050
|
}
|
|
797
1051
|
if (info.error) {
|
|
@@ -801,13 +1055,13 @@ function TpsMeterPlugin(context) {
|
|
|
801
1055
|
function handleSessionIdle(event) {
|
|
802
1056
|
const sessionId = event.properties.sessionID || "default";
|
|
803
1057
|
logger.debug(`[TpsMeter] Session idle: ${sessionId}`);
|
|
804
|
-
|
|
1058
|
+
clearDisplayTimer(sessionId);
|
|
1059
|
+
sessionTrackers.delete(sessionId);
|
|
805
1060
|
partTextCache.delete(sessionId);
|
|
806
1061
|
messageTokenCache.delete(sessionId);
|
|
807
1062
|
messageRoleCache.delete(sessionId);
|
|
808
|
-
|
|
809
|
-
|
|
810
|
-
if (trackers.size === 0) {
|
|
1063
|
+
sessionAgentNameCache.delete(sessionId);
|
|
1064
|
+
if (sessionTrackers.size === 0) {
|
|
811
1065
|
cleanup();
|
|
812
1066
|
}
|
|
813
1067
|
}
|
|
@@ -818,17 +1072,37 @@ function TpsMeterPlugin(context) {
|
|
|
818
1072
|
}
|
|
819
1073
|
lastCleanupTime = now;
|
|
820
1074
|
let cleanedCount = 0;
|
|
821
|
-
for (const [sessionId,
|
|
1075
|
+
for (const [sessionId, sessionState] of sessionTrackers) {
|
|
822
1076
|
const tokenCache = messageTokenCache.get(sessionId);
|
|
823
1077
|
const roleCache = messageRoleCache.get(sessionId);
|
|
824
|
-
|
|
825
|
-
|
|
826
|
-
|
|
1078
|
+
const sessionCache = partTextCache.get(sessionId);
|
|
1079
|
+
const keysToDelete = [];
|
|
1080
|
+
for (const [key, messageTracker] of sessionState.messageTrackers) {
|
|
1081
|
+
if (messageTracker.lastUpdated > 0 && now - messageTracker.lastUpdated > MAX_MESSAGE_AGE_MS) {
|
|
1082
|
+
keysToDelete.push(key);
|
|
1083
|
+
}
|
|
1084
|
+
}
|
|
1085
|
+
for (const key of keysToDelete) {
|
|
1086
|
+
const messageTracker = sessionState.messageTrackers.get(key);
|
|
1087
|
+
if (messageTracker) {
|
|
1088
|
+
sessionState.messageTrackers.delete(key);
|
|
1089
|
+
const messageId = messageTracker.messageId;
|
|
827
1090
|
tokenCache?.delete(messageId);
|
|
828
1091
|
roleCache?.delete(messageId);
|
|
1092
|
+
if (sessionCache) {
|
|
1093
|
+
for (const cacheKey of sessionCache.keys()) {
|
|
1094
|
+
if (cacheKey.startsWith(`${messageId}:`)) {
|
|
1095
|
+
sessionCache.delete(cacheKey);
|
|
1096
|
+
}
|
|
1097
|
+
}
|
|
1098
|
+
}
|
|
829
1099
|
cleanedCount++;
|
|
830
1100
|
}
|
|
831
1101
|
}
|
|
1102
|
+
if (sessionState.messageTrackers.size === 0) {
|
|
1103
|
+
sessionState.aggregate.reset();
|
|
1104
|
+
sessionState.aggregateFirstTokenAt = null;
|
|
1105
|
+
}
|
|
832
1106
|
}
|
|
833
1107
|
if (cleanedCount > 0) {
|
|
834
1108
|
logger.debug(`[TpsMeter] Cleaned up ${cleanedCount} stale message entries`);
|
package/dist/index.mjs
CHANGED
|
@@ -3,9 +3,12 @@ var MIN_TPS_ELAPSED_MS = 250;
|
|
|
3
3
|
var DEFAULT_ROLLING_WINDOW_MS = 1000;
|
|
4
4
|
var MAX_BUFFER_SIZE = 100;
|
|
5
5
|
var MIN_WINDOW_DURATION_SECONDS = 0.1;
|
|
6
|
-
var BURST_TOKEN_THRESHOLD =
|
|
6
|
+
var BURST_TOKEN_THRESHOLD = 50;
|
|
7
7
|
var DEFAULT_EWMA_HALF_LIFE_MS = 500;
|
|
8
|
-
var BURST_EWMA_HALF_LIFE_MS =
|
|
8
|
+
var BURST_EWMA_HALF_LIFE_MS = 3000;
|
|
9
|
+
var LARGE_BURST_THRESHOLD = 200;
|
|
10
|
+
var LARGE_BURST_EWMA_HALF_LIFE_MS = 5000;
|
|
11
|
+
var MAX_INITIAL_TPS = 100;
|
|
9
12
|
var DEFAULT_UPDATE_INTERVAL_MS = 50;
|
|
10
13
|
var MIN_TOAST_INTERVAL_MS = 150;
|
|
11
14
|
var DEFAULT_TOAST_DURATION_MS = 20000;
|
|
@@ -77,11 +80,18 @@ function createTracker(options = {}) {
|
|
|
77
80
|
pruneBuffer(ts);
|
|
78
81
|
const rawTPS = calculateRawTPS(ts);
|
|
79
82
|
if (!hasSmoothedValue) {
|
|
80
|
-
smoothedTps = rawTPS;
|
|
83
|
+
smoothedTps = Math.min(rawTPS, MAX_INITIAL_TPS);
|
|
81
84
|
hasSmoothedValue = true;
|
|
82
85
|
} else {
|
|
83
86
|
const timeDelta = Math.max(1, ts - lastSmoothedAt);
|
|
84
|
-
|
|
87
|
+
let halfLife;
|
|
88
|
+
if (count > LARGE_BURST_THRESHOLD) {
|
|
89
|
+
halfLife = LARGE_BURST_EWMA_HALF_LIFE_MS;
|
|
90
|
+
} else if (count > BURST_TOKEN_THRESHOLD) {
|
|
91
|
+
halfLife = BURST_EWMA_HALF_LIFE_MS;
|
|
92
|
+
} else {
|
|
93
|
+
halfLife = DEFAULT_EWMA_HALF_LIFE_MS;
|
|
94
|
+
}
|
|
85
95
|
const alpha = Math.exp(-Math.LN2 * timeDelta / halfLife);
|
|
86
96
|
smoothedTps = alpha * smoothedTps + (1 - alpha) * rawTPS;
|
|
87
97
|
}
|
|
@@ -157,7 +167,7 @@ function createUIManager(client, config) {
|
|
|
157
167
|
function formatNumberWithCommas(num) {
|
|
158
168
|
return num.toLocaleString("en-US");
|
|
159
169
|
}
|
|
160
|
-
function
|
|
170
|
+
function formatPrimaryLine(state) {
|
|
161
171
|
const parts = [];
|
|
162
172
|
if (uiConfig.showInstant || uiConfig.showAverage) {
|
|
163
173
|
const tpsParts = [];
|
|
@@ -167,7 +177,9 @@ function createUIManager(client, config) {
|
|
|
167
177
|
if (uiConfig.showAverage) {
|
|
168
178
|
tpsParts.push(`(avg ${state.avgTps.toFixed(1)})`);
|
|
169
179
|
}
|
|
170
|
-
|
|
180
|
+
if (tpsParts.length > 0) {
|
|
181
|
+
parts.push(tpsParts.join(" "));
|
|
182
|
+
}
|
|
171
183
|
}
|
|
172
184
|
if (uiConfig.showTotalTokens) {
|
|
173
185
|
parts.push(`tokens: ${formatNumberWithCommas(state.totalTokens)}`);
|
|
@@ -175,7 +187,30 @@ function createUIManager(client, config) {
|
|
|
175
187
|
if (uiConfig.showElapsed) {
|
|
176
188
|
parts.push(formatElapsedTime(state.elapsedMs));
|
|
177
189
|
}
|
|
178
|
-
return parts.join(" | ");
|
|
190
|
+
return parts.length > 0 ? parts.join(" | ") : "TPS meter";
|
|
191
|
+
}
|
|
192
|
+
function formatAgentLine(agent) {
|
|
193
|
+
const segments = [];
|
|
194
|
+
segments.push(`${agent.instantTps.toFixed(1)} (avg ${agent.avgTps.toFixed(1)})`);
|
|
195
|
+
segments.push(`tokens: ${formatNumberWithCommas(agent.totalTokens)}`);
|
|
196
|
+
if (uiConfig.showElapsed) {
|
|
197
|
+
segments.push(formatElapsedTime(agent.elapsedMs));
|
|
198
|
+
}
|
|
199
|
+
return `${agent.label} ${segments.join(" | ")}`.trim();
|
|
200
|
+
}
|
|
201
|
+
function formatDisplay(state) {
|
|
202
|
+
const lines = [];
|
|
203
|
+
const hasMainActivity = state.totalTokens > 0;
|
|
204
|
+
if (hasMainActivity) {
|
|
205
|
+
lines.push(formatPrimaryLine(state));
|
|
206
|
+
}
|
|
207
|
+
const agentLines = (state.agents ?? []).filter((agent) => agent.totalTokens > 0).map((agent) => formatAgentLine(agent));
|
|
208
|
+
lines.push(...agentLines);
|
|
209
|
+
if (lines.length === 0) {
|
|
210
|
+
return "TPS meter (idle)";
|
|
211
|
+
}
|
|
212
|
+
return lines.join(`
|
|
213
|
+
`);
|
|
179
214
|
}
|
|
180
215
|
function getColorVariant(instantTps, isFinal) {
|
|
181
216
|
if (isFinal) {
|
|
@@ -274,12 +309,13 @@ function createUIManager(client, config) {
|
|
|
274
309
|
}, delay);
|
|
275
310
|
}
|
|
276
311
|
return {
|
|
277
|
-
updateDisplay(instantTps, avgTps, totalTokens, elapsedMs) {
|
|
312
|
+
updateDisplay(instantTps, avgTps, totalTokens, elapsedMs, agents) {
|
|
278
313
|
pendingState = {
|
|
279
314
|
instantTps,
|
|
280
315
|
avgTps,
|
|
281
316
|
totalTokens,
|
|
282
|
-
elapsedMs
|
|
317
|
+
elapsedMs,
|
|
318
|
+
agents: agents && agents.length > 0 ? agents : undefined
|
|
283
319
|
};
|
|
284
320
|
scheduleFlush();
|
|
285
321
|
},
|
|
@@ -603,34 +639,234 @@ function TpsMeterPlugin(context) {
|
|
|
603
639
|
logger.debug("[TpsMeter] Plugin disabled by configuration");
|
|
604
640
|
return {};
|
|
605
641
|
}
|
|
606
|
-
const
|
|
642
|
+
const sessionTrackers = new Map;
|
|
607
643
|
const partTextCache = new Map;
|
|
608
644
|
const messageTokenCache = new Map;
|
|
609
645
|
const messageRoleCache = new Map;
|
|
610
|
-
const
|
|
611
|
-
|
|
646
|
+
const sessionAgentNameCache = new Map;
|
|
647
|
+
let primarySessionId = null;
|
|
648
|
+
const pendingDisplayTimers = new Map;
|
|
612
649
|
const resolvedConfig = config;
|
|
613
650
|
const ui = createUIManager(safeContext.client || {}, resolvedConfig);
|
|
614
651
|
const tokenizer = createTokenizer(resolvedConfig.fallbackTokenHeuristic === "words_div_0_75" ? "word" : resolvedConfig.fallbackTokenHeuristic === "chars_div_3" ? "code" : "heuristic");
|
|
615
652
|
logger.info("[TpsMeter] Plugin initialized and ready");
|
|
616
|
-
function
|
|
617
|
-
let
|
|
618
|
-
if (!
|
|
619
|
-
|
|
620
|
-
|
|
621
|
-
|
|
622
|
-
|
|
623
|
-
|
|
653
|
+
function getOrCreateSessionState(sessionId) {
|
|
654
|
+
let state = sessionTrackers.get(sessionId);
|
|
655
|
+
if (!state) {
|
|
656
|
+
state = {
|
|
657
|
+
aggregate: createTracker({
|
|
658
|
+
sessionId,
|
|
659
|
+
rollingWindowMs: resolvedConfig.rollingWindowMs
|
|
660
|
+
}),
|
|
661
|
+
aggregateFirstTokenAt: null,
|
|
662
|
+
messageTrackers: new Map
|
|
663
|
+
};
|
|
664
|
+
sessionTrackers.set(sessionId, state);
|
|
624
665
|
logger.debug(`[TpsMeter] Created tracker for session: ${sessionId}`);
|
|
625
666
|
}
|
|
626
|
-
return
|
|
667
|
+
return state;
|
|
668
|
+
}
|
|
669
|
+
function abbreviateId(id) {
|
|
670
|
+
if (!id || id.length <= 4)
|
|
671
|
+
return id;
|
|
672
|
+
return `${id.slice(0, 4)}…`;
|
|
673
|
+
}
|
|
674
|
+
function buildAgentLabel(messageId, metadata) {
|
|
675
|
+
const typeLabel = metadata?.agent?.type?.trim() || metadata?.agentType?.trim() || metadata?.agent?.name?.trim() || metadata?.name?.trim() || "Subagent";
|
|
676
|
+
const rawId = metadata?.agentId?.trim() || metadata?.agent?.id?.trim() || messageId;
|
|
677
|
+
const identifier = abbreviateId(rawId);
|
|
678
|
+
return `${typeLabel}(${identifier})`;
|
|
679
|
+
}
|
|
680
|
+
function buildTrackerKey(sessionId, messageId, partId, metadata) {
|
|
681
|
+
const agentId = metadata?.agentId?.trim() || metadata?.agent?.id?.trim() || metadata?.agentType?.trim();
|
|
682
|
+
if (agentId) {
|
|
683
|
+
return `${sessionId}:${messageId}:${agentId}`;
|
|
684
|
+
}
|
|
685
|
+
if (partId) {
|
|
686
|
+
return `${sessionId}:${messageId}:${partId}`;
|
|
687
|
+
}
|
|
688
|
+
return `${sessionId}:${messageId}`;
|
|
689
|
+
}
|
|
690
|
+
function getOrCreateMessageTrackerState(sessionId, messageId, partId, metadata) {
|
|
691
|
+
const sessionState = getOrCreateSessionState(sessionId);
|
|
692
|
+
const key = buildTrackerKey(sessionId, messageId, partId, metadata);
|
|
693
|
+
let trackerState = sessionState.messageTrackers.get(key);
|
|
694
|
+
const nextLabel = buildAgentLabel(messageId, metadata);
|
|
695
|
+
if (!trackerState) {
|
|
696
|
+
trackerState = {
|
|
697
|
+
key,
|
|
698
|
+
messageId,
|
|
699
|
+
partId,
|
|
700
|
+
tracker: createTracker({
|
|
701
|
+
sessionId: key,
|
|
702
|
+
rollingWindowMs: resolvedConfig.rollingWindowMs
|
|
703
|
+
}),
|
|
704
|
+
label: nextLabel,
|
|
705
|
+
firstTokenAt: null,
|
|
706
|
+
lastUpdated: 0,
|
|
707
|
+
agent: metadata?.agent,
|
|
708
|
+
agentId: metadata?.agentId,
|
|
709
|
+
agentType: metadata?.agentType
|
|
710
|
+
};
|
|
711
|
+
sessionState.messageTrackers.set(key, trackerState);
|
|
712
|
+
} else if (trackerState.label !== nextLabel) {
|
|
713
|
+
trackerState.label = nextLabel;
|
|
714
|
+
}
|
|
715
|
+
if (metadata?.agent) {
|
|
716
|
+
trackerState.agent = metadata.agent;
|
|
717
|
+
}
|
|
718
|
+
if (metadata?.agentId) {
|
|
719
|
+
trackerState.agentId = metadata.agentId;
|
|
720
|
+
}
|
|
721
|
+
if (metadata?.agentType) {
|
|
722
|
+
trackerState.agentType = metadata.agentType;
|
|
723
|
+
}
|
|
724
|
+
return trackerState;
|
|
725
|
+
}
|
|
726
|
+
function getAllActiveAgentsGlobally(now) {
|
|
727
|
+
const activityWindow = Math.max(resolvedConfig.rollingWindowMs, MIN_TPS_ELAPSED_MS * 4);
|
|
728
|
+
const entries = [];
|
|
729
|
+
for (const [sessionId, sessionState] of sessionTrackers) {
|
|
730
|
+
for (const [trackerKey, trackerState] of sessionState.messageTrackers) {
|
|
731
|
+
if (!trackerState.firstTokenAt)
|
|
732
|
+
continue;
|
|
733
|
+
if (now - trackerState.lastUpdated > activityWindow)
|
|
734
|
+
continue;
|
|
735
|
+
const hasAgentMetadata = Boolean(trackerState.agent || trackerState.agentId || trackerState.agentType);
|
|
736
|
+
let isSubagent = false;
|
|
737
|
+
let label = trackerState.label;
|
|
738
|
+
if (hasAgentMetadata) {
|
|
739
|
+
isSubagent = true;
|
|
740
|
+
} else if (sessionId !== primarySessionId) {
|
|
741
|
+
isSubagent = true;
|
|
742
|
+
const agentName = sessionAgentNameCache.get(sessionId) || "bg";
|
|
743
|
+
const shortId = abbreviateId(sessionId.replace(/^ses_/, ""));
|
|
744
|
+
label = `${agentName}(${shortId})`;
|
|
745
|
+
}
|
|
746
|
+
if (!isSubagent)
|
|
747
|
+
continue;
|
|
748
|
+
entries.push({
|
|
749
|
+
id: trackerKey,
|
|
750
|
+
label,
|
|
751
|
+
instantTps: trackerState.tracker.getSmoothedTPS(),
|
|
752
|
+
avgTps: trackerState.tracker.getAverageTPS(),
|
|
753
|
+
totalTokens: trackerState.tracker.getTotalTokens(),
|
|
754
|
+
elapsedMs: now - trackerState.firstTokenAt
|
|
755
|
+
});
|
|
756
|
+
}
|
|
757
|
+
}
|
|
758
|
+
entries.sort((a, b) => b.instantTps - a.instantTps);
|
|
759
|
+
return entries;
|
|
760
|
+
}
|
|
761
|
+
function isPrimarySessionActive(now) {
|
|
762
|
+
if (!primarySessionId)
|
|
763
|
+
return false;
|
|
764
|
+
const sessionState = sessionTrackers.get(primarySessionId);
|
|
765
|
+
if (!sessionState)
|
|
766
|
+
return false;
|
|
767
|
+
const activityWindow = Math.max(resolvedConfig.rollingWindowMs, MIN_TPS_ELAPSED_MS * 4);
|
|
768
|
+
for (const trackerState of sessionState.messageTrackers.values()) {
|
|
769
|
+
const hasAgentMetadata = Boolean(trackerState.agent || trackerState.agentId || trackerState.agentType);
|
|
770
|
+
if (hasAgentMetadata)
|
|
771
|
+
continue;
|
|
772
|
+
if (trackerState.firstTokenAt && now - trackerState.lastUpdated <= activityWindow) {
|
|
773
|
+
return true;
|
|
774
|
+
}
|
|
775
|
+
}
|
|
776
|
+
return false;
|
|
777
|
+
}
|
|
778
|
+
function getActiveAgentDisplayStates(sessionState, now) {
|
|
779
|
+
const activityWindow = Math.max(resolvedConfig.rollingWindowMs, MIN_TPS_ELAPSED_MS * 4);
|
|
780
|
+
const entries = [];
|
|
781
|
+
for (const trackerState of sessionState.messageTrackers.values()) {
|
|
782
|
+
if (!trackerState.firstTokenAt) {
|
|
783
|
+
continue;
|
|
784
|
+
}
|
|
785
|
+
if (now - trackerState.lastUpdated > activityWindow) {
|
|
786
|
+
continue;
|
|
787
|
+
}
|
|
788
|
+
const hasAgentMetadata = Boolean(trackerState.agent || trackerState.agentId || trackerState.agentType);
|
|
789
|
+
if (!hasAgentMetadata) {
|
|
790
|
+
continue;
|
|
791
|
+
}
|
|
792
|
+
entries.push({
|
|
793
|
+
id: trackerState.messageId,
|
|
794
|
+
label: trackerState.label,
|
|
795
|
+
instantTps: trackerState.tracker.getSmoothedTPS(),
|
|
796
|
+
avgTps: trackerState.tracker.getAverageTPS(),
|
|
797
|
+
totalTokens: trackerState.tracker.getTotalTokens(),
|
|
798
|
+
elapsedMs: now - trackerState.firstTokenAt
|
|
799
|
+
});
|
|
800
|
+
}
|
|
801
|
+
entries.sort((a, b) => b.instantTps - a.instantTps);
|
|
802
|
+
return entries;
|
|
803
|
+
}
|
|
804
|
+
function removeMessageTrackerState(sessionId, messageId) {
|
|
805
|
+
const sessionState = sessionTrackers.get(sessionId);
|
|
806
|
+
if (!sessionState) {
|
|
807
|
+
return;
|
|
808
|
+
}
|
|
809
|
+
for (const [key, state] of sessionState.messageTrackers) {
|
|
810
|
+
if (state.messageId === messageId) {
|
|
811
|
+
sessionState.messageTrackers.delete(key);
|
|
812
|
+
}
|
|
813
|
+
}
|
|
814
|
+
if (sessionState.messageTrackers.size === 0) {
|
|
815
|
+
sessionState.aggregate.reset();
|
|
816
|
+
sessionState.aggregateFirstTokenAt = null;
|
|
817
|
+
}
|
|
818
|
+
}
|
|
819
|
+
function scheduleDisplayTimer(sessionId) {
|
|
820
|
+
const existingTimer = pendingDisplayTimers.get(sessionId);
|
|
821
|
+
if (existingTimer) {
|
|
822
|
+
clearTimeout(existingTimer);
|
|
823
|
+
}
|
|
824
|
+
const timer = setTimeout(() => {
|
|
825
|
+
pendingDisplayTimers.delete(sessionId);
|
|
826
|
+
const sessionState = sessionTrackers.get(sessionId);
|
|
827
|
+
if (!sessionState || !sessionState.aggregateFirstTokenAt) {
|
|
828
|
+
return;
|
|
829
|
+
}
|
|
830
|
+
const now = Date.now();
|
|
831
|
+
const elapsedSinceFirstToken = now - sessionState.aggregateFirstTokenAt;
|
|
832
|
+
if (elapsedSinceFirstToken < MIN_TPS_ELAPSED_MS)
|
|
833
|
+
return;
|
|
834
|
+
const allAgents = getAllActiveAgentsGlobally(now);
|
|
835
|
+
const hasPrimaryActivity = isPrimarySessionActive(now);
|
|
836
|
+
if (hasPrimaryActivity) {
|
|
837
|
+
const smoothedTps = sessionState.aggregate.getSmoothedTPS();
|
|
838
|
+
const avgTps = sessionState.aggregate.getAverageTPS();
|
|
839
|
+
const totalTokens = sessionState.aggregate.getTotalTokens();
|
|
840
|
+
const elapsedMs = sessionState.aggregate.getElapsedMs();
|
|
841
|
+
if (smoothedTps >= resolvedConfig.minVisibleTPS) {
|
|
842
|
+
ui.updateDisplay(smoothedTps, avgTps, totalTokens, elapsedMs, allAgents);
|
|
843
|
+
}
|
|
844
|
+
} else if (allAgents.length > 0) {
|
|
845
|
+
ui.updateDisplay(0, 0, 0, 0, allAgents);
|
|
846
|
+
}
|
|
847
|
+
logger.debug(`[TpsMeter] Timer-triggered display for session ${sessionId}`);
|
|
848
|
+
}, MIN_TPS_ELAPSED_MS + 10);
|
|
849
|
+
pendingDisplayTimers.set(sessionId, timer);
|
|
850
|
+
}
|
|
851
|
+
function clearDisplayTimer(sessionId) {
|
|
852
|
+
const timer = pendingDisplayTimers.get(sessionId);
|
|
853
|
+
if (timer) {
|
|
854
|
+
clearTimeout(timer);
|
|
855
|
+
pendingDisplayTimers.delete(sessionId);
|
|
856
|
+
}
|
|
627
857
|
}
|
|
628
858
|
function cleanup() {
|
|
629
859
|
logger.debug("[TpsMeter] Cleaning up all trackers and UI");
|
|
630
|
-
|
|
860
|
+
for (const timer of pendingDisplayTimers.values()) {
|
|
861
|
+
clearTimeout(timer);
|
|
862
|
+
}
|
|
863
|
+
pendingDisplayTimers.clear();
|
|
864
|
+
sessionTrackers.clear();
|
|
865
|
+
partTextCache.clear();
|
|
866
|
+
messageTokenCache.clear();
|
|
631
867
|
messageRoleCache.clear();
|
|
632
|
-
|
|
633
|
-
|
|
868
|
+
sessionAgentNameCache.clear();
|
|
869
|
+
primarySessionId = null;
|
|
634
870
|
ui.clear();
|
|
635
871
|
}
|
|
636
872
|
function handleMessagePartUpdated(event) {
|
|
@@ -649,11 +885,7 @@ function TpsMeterPlugin(context) {
|
|
|
649
885
|
partTextCache.set(sessionId, sessionCache);
|
|
650
886
|
const cacheKey = `${part.messageID}:${part.id}:${part.type}`;
|
|
651
887
|
const previousText = sessionCache.get(cacheKey) || "";
|
|
652
|
-
|
|
653
|
-
delta = partText.slice(previousText.length);
|
|
654
|
-
} else {
|
|
655
|
-
delta = partText;
|
|
656
|
-
}
|
|
888
|
+
delta = partText.startsWith(previousText) ? partText.slice(previousText.length) : partText;
|
|
657
889
|
sessionCache.set(cacheKey, partText);
|
|
658
890
|
}
|
|
659
891
|
if (!delta || delta.length === 0) {
|
|
@@ -664,35 +896,52 @@ function TpsMeterPlugin(context) {
|
|
|
664
896
|
if (role !== "assistant") {
|
|
665
897
|
return;
|
|
666
898
|
}
|
|
667
|
-
const
|
|
668
|
-
const
|
|
669
|
-
|
|
670
|
-
|
|
671
|
-
|
|
672
|
-
|
|
673
|
-
}
|
|
899
|
+
const sessionState = getOrCreateSessionState(sessionId);
|
|
900
|
+
const messageTracker = getOrCreateMessageTrackerState(sessionId, part.messageID, part.id, {
|
|
901
|
+
agent: part.agent,
|
|
902
|
+
agentId: part.agentId,
|
|
903
|
+
agentType: part.agentType,
|
|
904
|
+
name: part.name
|
|
905
|
+
});
|
|
674
906
|
const now = Date.now();
|
|
675
907
|
cleanupStaleMessages(now);
|
|
676
|
-
|
|
677
|
-
|
|
678
|
-
|
|
679
|
-
if (firstTokenAt === undefined) {
|
|
680
|
-
firstTokenAt = now;
|
|
681
|
-
firstTokenCache.set(messageId, firstTokenAt);
|
|
908
|
+
if (!sessionState.aggregateFirstTokenAt) {
|
|
909
|
+
sessionState.aggregateFirstTokenAt = now;
|
|
910
|
+
scheduleDisplayTimer(sessionId);
|
|
682
911
|
}
|
|
912
|
+
if (!messageTracker.firstTokenAt) {
|
|
913
|
+
messageTracker.firstTokenAt = now;
|
|
914
|
+
const hasAgentMetadata = Boolean(messageTracker.agent || messageTracker.agentId || messageTracker.agentType);
|
|
915
|
+
if (!hasAgentMetadata && primarySessionId === null) {
|
|
916
|
+
primarySessionId = sessionId;
|
|
917
|
+
logger.debug(`[TpsMeter] Primary session set to: ${sessionId}`);
|
|
918
|
+
}
|
|
919
|
+
const metaLabel = messageTracker.label;
|
|
920
|
+
const metaInfo = messageTracker.agent || messageTracker.agentId || messageTracker.agentType ? `agent=${messageTracker.agent?.type ?? messageTracker.agentType ?? "?"} id=${messageTracker.agent?.id ?? messageTracker.agentId ?? "?"}` : "agent=none";
|
|
921
|
+
logger.info(`[TpsMeter][Debug] tracker initialized ${metaLabel} (${metaInfo}) session=${sessionId} message=${part.messageID} part=${part.id ?? "?"}`);
|
|
922
|
+
}
|
|
923
|
+
messageTracker.lastUpdated = now;
|
|
683
924
|
const tokenCount = tokenizer.count(delta);
|
|
684
|
-
|
|
925
|
+
sessionState.aggregate.recordTokens(tokenCount, now);
|
|
926
|
+
messageTracker.tracker.recordTokens(tokenCount, now);
|
|
685
927
|
const messageCache = messageTokenCache.get(sessionId) || new Map;
|
|
686
928
|
messageTokenCache.set(sessionId, messageCache);
|
|
687
|
-
const previousTokens = messageCache.get(
|
|
688
|
-
messageCache.set(
|
|
689
|
-
const smoothedTps =
|
|
690
|
-
const avgTps =
|
|
691
|
-
const totalTokens =
|
|
692
|
-
const elapsedMs =
|
|
693
|
-
const elapsedSinceFirstToken = Math.max(0, now -
|
|
694
|
-
if (elapsedSinceFirstToken >= MIN_TPS_ELAPSED_MS
|
|
695
|
-
|
|
929
|
+
const previousTokens = messageCache.get(part.messageID) ?? 0;
|
|
930
|
+
messageCache.set(part.messageID, previousTokens + tokenCount);
|
|
931
|
+
const smoothedTps = sessionState.aggregate.getSmoothedTPS();
|
|
932
|
+
const avgTps = sessionState.aggregate.getAverageTPS();
|
|
933
|
+
const totalTokens = sessionState.aggregate.getTotalTokens();
|
|
934
|
+
const elapsedMs = sessionState.aggregate.getElapsedMs();
|
|
935
|
+
const elapsedSinceFirstToken = sessionState.aggregateFirstTokenAt === null ? 0 : Math.max(0, now - sessionState.aggregateFirstTokenAt);
|
|
936
|
+
if (elapsedSinceFirstToken >= MIN_TPS_ELAPSED_MS) {
|
|
937
|
+
clearDisplayTimer(sessionId);
|
|
938
|
+
const allAgents = getAllActiveAgentsGlobally(now);
|
|
939
|
+
const hasPrimaryActivity = isPrimarySessionActive(now) && smoothedTps >= resolvedConfig.minVisibleTPS;
|
|
940
|
+
if (hasPrimaryActivity) {
|
|
941
|
+
ui.updateDisplay(smoothedTps, avgTps, totalTokens, elapsedMs, allAgents);
|
|
942
|
+
} else if (allAgents.length > 0) {
|
|
943
|
+
ui.updateDisplay(0, 0, 0, 0, allAgents);
|
|
944
|
+
}
|
|
696
945
|
}
|
|
697
946
|
logger.debug(`[TpsMeter] Session ${sessionId}: +${tokenCount} tokens, TPS: ${smoothedTps.toFixed(1)} (avg: ${avgTps.toFixed(1)})`);
|
|
698
947
|
}
|
|
@@ -704,25 +953,30 @@ function TpsMeterPlugin(context) {
|
|
|
704
953
|
const roleCache = messageRoleCache.get(info.sessionID) || new Map;
|
|
705
954
|
messageRoleCache.set(info.sessionID, roleCache);
|
|
706
955
|
roleCache.set(info.id, info.role);
|
|
956
|
+
if (info.agent && typeof info.agent === "string") {
|
|
957
|
+
sessionAgentNameCache.set(info.sessionID, info.agent);
|
|
958
|
+
}
|
|
707
959
|
if (info.role === "assistant") {
|
|
708
960
|
const sessionId = info.sessionID;
|
|
709
|
-
const tracker = trackers.get(sessionId);
|
|
710
961
|
const sessionCache = partTextCache.get(sessionId);
|
|
711
962
|
const tokenCache = messageTokenCache.get(sessionId) || new Map;
|
|
712
963
|
messageTokenCache.set(sessionId, tokenCache);
|
|
713
|
-
const firstTokenCache = messageFirstTokenCache.get(sessionId) || new Map;
|
|
714
|
-
messageFirstTokenCache.set(sessionId, firstTokenCache);
|
|
715
964
|
const outputTokens = info.tokens?.output ?? 0;
|
|
716
965
|
const reasoningTokens = info.tokens?.reasoning ?? 0;
|
|
717
966
|
const reportedTokens = outputTokens + reasoningTokens;
|
|
718
967
|
const messageId = info.id;
|
|
968
|
+
const messageTracker = getOrCreateMessageTrackerState(sessionId, messageId, undefined, {
|
|
969
|
+
agent: info.agent,
|
|
970
|
+
agentId: info.agentId,
|
|
971
|
+
agentType: info.agentType
|
|
972
|
+
});
|
|
719
973
|
const previous = tokenCache.get(messageId) ?? 0;
|
|
720
974
|
const nextTokens = Math.max(previous, reportedTokens);
|
|
721
975
|
tokenCache.set(messageId, nextTokens);
|
|
722
|
-
if (info.time?.completed
|
|
976
|
+
if (info.time?.completed) {
|
|
723
977
|
const completedAt = info.time?.completed ?? Date.now();
|
|
724
978
|
const createdAt = info.time?.created ?? completedAt;
|
|
725
|
-
const firstTokenAt =
|
|
979
|
+
const firstTokenAt = messageTracker.firstTokenAt ?? createdAt;
|
|
726
980
|
const elapsedMs = Math.max(0, completedAt - firstTokenAt);
|
|
727
981
|
const cachedTokens = tokenCache.get(messageId) ?? 0;
|
|
728
982
|
const totalTokens = reportedTokens > 0 ? reportedTokens : cachedTokens;
|
|
@@ -744,7 +998,7 @@ function TpsMeterPlugin(context) {
|
|
|
744
998
|
if (info.time?.completed) {
|
|
745
999
|
tokenCache.delete(messageId);
|
|
746
1000
|
roleCache.delete(messageId);
|
|
747
|
-
|
|
1001
|
+
removeMessageTrackerState(sessionId, messageId);
|
|
748
1002
|
}
|
|
749
1003
|
}
|
|
750
1004
|
if (info.error) {
|
|
@@ -754,13 +1008,13 @@ function TpsMeterPlugin(context) {
|
|
|
754
1008
|
function handleSessionIdle(event) {
|
|
755
1009
|
const sessionId = event.properties.sessionID || "default";
|
|
756
1010
|
logger.debug(`[TpsMeter] Session idle: ${sessionId}`);
|
|
757
|
-
|
|
1011
|
+
clearDisplayTimer(sessionId);
|
|
1012
|
+
sessionTrackers.delete(sessionId);
|
|
758
1013
|
partTextCache.delete(sessionId);
|
|
759
1014
|
messageTokenCache.delete(sessionId);
|
|
760
1015
|
messageRoleCache.delete(sessionId);
|
|
761
|
-
|
|
762
|
-
|
|
763
|
-
if (trackers.size === 0) {
|
|
1016
|
+
sessionAgentNameCache.delete(sessionId);
|
|
1017
|
+
if (sessionTrackers.size === 0) {
|
|
764
1018
|
cleanup();
|
|
765
1019
|
}
|
|
766
1020
|
}
|
|
@@ -771,17 +1025,37 @@ function TpsMeterPlugin(context) {
|
|
|
771
1025
|
}
|
|
772
1026
|
lastCleanupTime = now;
|
|
773
1027
|
let cleanedCount = 0;
|
|
774
|
-
for (const [sessionId,
|
|
1028
|
+
for (const [sessionId, sessionState] of sessionTrackers) {
|
|
775
1029
|
const tokenCache = messageTokenCache.get(sessionId);
|
|
776
1030
|
const roleCache = messageRoleCache.get(sessionId);
|
|
777
|
-
|
|
778
|
-
|
|
779
|
-
|
|
1031
|
+
const sessionCache = partTextCache.get(sessionId);
|
|
1032
|
+
const keysToDelete = [];
|
|
1033
|
+
for (const [key, messageTracker] of sessionState.messageTrackers) {
|
|
1034
|
+
if (messageTracker.lastUpdated > 0 && now - messageTracker.lastUpdated > MAX_MESSAGE_AGE_MS) {
|
|
1035
|
+
keysToDelete.push(key);
|
|
1036
|
+
}
|
|
1037
|
+
}
|
|
1038
|
+
for (const key of keysToDelete) {
|
|
1039
|
+
const messageTracker = sessionState.messageTrackers.get(key);
|
|
1040
|
+
if (messageTracker) {
|
|
1041
|
+
sessionState.messageTrackers.delete(key);
|
|
1042
|
+
const messageId = messageTracker.messageId;
|
|
780
1043
|
tokenCache?.delete(messageId);
|
|
781
1044
|
roleCache?.delete(messageId);
|
|
1045
|
+
if (sessionCache) {
|
|
1046
|
+
for (const cacheKey of sessionCache.keys()) {
|
|
1047
|
+
if (cacheKey.startsWith(`${messageId}:`)) {
|
|
1048
|
+
sessionCache.delete(cacheKey);
|
|
1049
|
+
}
|
|
1050
|
+
}
|
|
1051
|
+
}
|
|
782
1052
|
cleanedCount++;
|
|
783
1053
|
}
|
|
784
1054
|
}
|
|
1055
|
+
if (sessionState.messageTrackers.size === 0) {
|
|
1056
|
+
sessionState.aggregate.reset();
|
|
1057
|
+
sessionState.aggregateFirstTokenAt = null;
|
|
1058
|
+
}
|
|
785
1059
|
}
|
|
786
1060
|
if (cleanedCount > 0) {
|
|
787
1061
|
logger.debug(`[TpsMeter] Cleaned up ${cleanedCount} stale message entries`);
|
package/dist/tracker.d.ts.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"tracker.d.ts","sourceRoot":"","sources":["../src/tracker.ts"],"names":[],"mappings":"AAAA;;;;GAIG;AAEH,OAAO,KAAK,EAAE,iBAAiB,EAAe,UAAU,EAAE,MAAM,YAAY,CAAC;AAG7E;;;;;;;;;GASG;AACH,wBAAgB,aAAa,CAAC,OAAO,GAAE,iBAAsB,GAAG,UAAU,
|
|
1
|
+
{"version":3,"file":"tracker.d.ts","sourceRoot":"","sources":["../src/tracker.ts"],"names":[],"mappings":"AAAA;;;;GAIG;AAEH,OAAO,KAAK,EAAE,iBAAiB,EAAe,UAAU,EAAE,MAAM,YAAY,CAAC;AAG7E;;;;;;;;;GASG;AACH,wBAAgB,aAAa,CAAC,OAAO,GAAE,iBAAsB,GAAG,UAAU,CAkOzE"}
|
package/dist/types.d.ts
CHANGED
|
@@ -150,6 +150,15 @@ export interface FilePartSource {
|
|
|
150
150
|
name?: string;
|
|
151
151
|
uri?: string;
|
|
152
152
|
}
|
|
153
|
+
/**
|
|
154
|
+
* Agent identity metadata for primary and sub-agents
|
|
155
|
+
*/
|
|
156
|
+
export interface AgentIdentity {
|
|
157
|
+
id?: string;
|
|
158
|
+
type?: string;
|
|
159
|
+
name?: string;
|
|
160
|
+
description?: string;
|
|
161
|
+
}
|
|
153
162
|
export interface Part {
|
|
154
163
|
id: string;
|
|
155
164
|
sessionID: string;
|
|
@@ -169,6 +178,10 @@ export interface Part {
|
|
|
169
178
|
name?: string;
|
|
170
179
|
error?: unknown;
|
|
171
180
|
auto?: boolean;
|
|
181
|
+
metadata?: Record<string, unknown>;
|
|
182
|
+
agent?: AgentIdentity;
|
|
183
|
+
agentId?: string;
|
|
184
|
+
agentType?: string;
|
|
172
185
|
}
|
|
173
186
|
/**
|
|
174
187
|
* Logger interface for plugin logging
|
|
@@ -216,6 +229,10 @@ export interface MessageEvent {
|
|
|
216
229
|
};
|
|
217
230
|
finish?: string;
|
|
218
231
|
error?: unknown;
|
|
232
|
+
agent?: AgentIdentity;
|
|
233
|
+
metadata?: Record<string, unknown>;
|
|
234
|
+
agentId?: string;
|
|
235
|
+
agentType?: string;
|
|
219
236
|
};
|
|
220
237
|
sessionID?: string;
|
|
221
238
|
};
|
|
@@ -254,6 +271,25 @@ export interface DisplayState {
|
|
|
254
271
|
totalTokens: number;
|
|
255
272
|
/** Elapsed time in milliseconds */
|
|
256
273
|
elapsedMs: number;
|
|
274
|
+
/** Optional per-agent display entries */
|
|
275
|
+
agents?: AgentDisplayState[];
|
|
276
|
+
}
|
|
277
|
+
/**
|
|
278
|
+
* Display data for an individual agent/subagent stream
|
|
279
|
+
*/
|
|
280
|
+
export interface AgentDisplayState {
|
|
281
|
+
/** Unique identifier (message ID or agent ID) */
|
|
282
|
+
id: string;
|
|
283
|
+
/** Label describing the agent/subagent */
|
|
284
|
+
label: string;
|
|
285
|
+
/** Instantaneous TPS value */
|
|
286
|
+
instantTps: number;
|
|
287
|
+
/** Average TPS value */
|
|
288
|
+
avgTps: number;
|
|
289
|
+
/** Total tokens processed */
|
|
290
|
+
totalTokens: number;
|
|
291
|
+
/** Elapsed time since first token */
|
|
292
|
+
elapsedMs: number;
|
|
257
293
|
}
|
|
258
294
|
/**
|
|
259
295
|
* TPS Tracker options
|
|
@@ -313,7 +349,7 @@ export interface TPSTracker {
|
|
|
313
349
|
*/
|
|
314
350
|
export interface UIManager {
|
|
315
351
|
/** Updates the display with current TPS statistics */
|
|
316
|
-
updateDisplay(instantTps: number, avgTps: number, totalTokens: number, elapsedMs: number): void;
|
|
352
|
+
updateDisplay(instantTps: number, avgTps: number, totalTokens: number, elapsedMs: number, agents?: AgentDisplayState[]): void;
|
|
317
353
|
/** Displays final statistics immediately */
|
|
318
354
|
showFinalStats(totalTokens: number, avgTps: number, elapsedMs: number): void;
|
|
319
355
|
/** Clears the display and cleans up resources */
|
package/dist/types.d.ts.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"types.d.ts","sourceRoot":"","sources":["../src/types.ts"],"names":[],"mappings":"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
|
|
1
|
+
{"version":3,"file":"types.d.ts","sourceRoot":"","sources":["../src/types.ts"],"names":[],"mappings":"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"}
|
package/dist/ui.d.ts.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"ui.d.ts","sourceRoot":"","sources":["../src/ui.ts"],"names":[],"mappings":"AAAA;;;GAGG;AAEH,OAAO,KAAK,EAAE,MAAM,EAAE,cAAc,
|
|
1
|
+
{"version":3,"file":"ui.d.ts","sourceRoot":"","sources":["../src/ui.ts"],"names":[],"mappings":"AAAA;;;GAGG;AAEH,OAAO,KAAK,EAAE,MAAM,EAAE,cAAc,EAAmC,SAAS,IAAI,UAAU,EAAE,MAAM,YAAY,CAAC;AAGnH;;;;;;;;;GASG;AACH,wBAAgB,eAAe,CAC7B,MAAM,EAAE,cAAc,EACtB,MAAM,EAAE,MAAM,GACb,UAAU,CA2UZ;AAED,eAAe,eAAe,CAAC"}
|