Skip to content

Commit eb019ba

Browse files
committed
Avoid redundant lineage shadow scans
1 parent d364597 commit eb019ba

4 files changed

Lines changed: 59 additions & 11 deletions

File tree

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,5 @@
11
// Generated by Scripts/regenerate-codex-parser-hash.sh. Do not edit by hand.
22

33
enum CodexParserHash {
4-
static let value = "adea6d0a163c51e2"
4+
static let value = "a22a4756d8f471d4"
55
}

Sources/CodexBarCore/Providers/Codex/CodexLineageLedger.swift

Lines changed: 14 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -96,18 +96,24 @@ enum CodexLineageLedger {
9696
}
9797

9898
var acceptedByComponent: [String: [ObservationIdentity: AcceptedObservation]] = [:]
99+
var acceptedFingerprintByComponentOwner: [String: [String: [Fingerprint: ObservationIdentity]]] = [:]
99100
var physicalObservationCount = 0
100101
for document in documents {
101102
try checkCancellation?()
102103
let componentID = graph.find(document.ownerID)
103104
var accepted = acceptedByComponent[componentID] ?? [:]
105+
var acceptedFingerprintByOwner = acceptedFingerprintByComponentOwner[componentID] ?? [:]
104106
for observation in document.observations {
105107
try checkCancellation?()
106108
physicalObservationCount += 1
107109
let date = try Self.date(from: observation.timestamp)
108-
let identity = ObservationIdentity(
110+
let fingerprint = Fingerprint(last: observation.last, total: observation.total)
111+
let proposedIdentity = ObservationIdentity(
109112
eventID: Self.nonEmpty(observation.eventID),
110-
fingerprint: Fingerprint(last: observation.last, total: observation.total))
113+
fingerprint: fingerprint)
114+
let identity = accepted[proposedIdentity] == nil
115+
? acceptedFingerprintByOwner[document.ownerID]?[fingerprint] ?? proposedIdentity
116+
: proposedIdentity
111117
if let existing = accepted[identity] {
112118
if existing.date < date {
113119
continue
@@ -122,8 +128,12 @@ enum CodexLineageLedger {
122128
date: date,
123129
model: observation.model,
124130
last: observation.last)
131+
if identity == proposedIdentity {
132+
acceptedFingerprintByOwner[document.ownerID, default: [:]][fingerprint] = identity
133+
}
125134
}
126135
acceptedByComponent[componentID] = accepted
136+
acceptedFingerprintByComponentOwner[componentID] = acceptedFingerprintByOwner
127137
}
128138

129139
var utcDays: [String: Totals] = [:]
@@ -159,11 +169,11 @@ enum CodexLineageLedger {
159169
}
160170

161171
private enum ObservationIdentity: Equatable, Hashable {
162-
case event(String)
172+
case event(String, Fingerprint)
163173
case fingerprint(Fingerprint)
164174

165175
init(eventID: String?, fingerprint: Fingerprint) {
166-
self = eventID.map(Self.event) ?? .fingerprint(fingerprint)
176+
self = eventID.map { .event($0, fingerprint) } ?? .fingerprint(fingerprint)
167177
}
168178
}
169179

Sources/CodexBarCore/Vendored/CostUsage/CostUsageScanner.swift

Lines changed: 12 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -80,6 +80,7 @@ enum CostUsageScanner {
8080
var contributingSessionIds: Set<String> = []
8181
var seenFileIds: Set<String> = []
8282
var seenCodexUsageRowKeys: Set<String> = []
83+
var changedLineageInputs = false
8384
}
8485

8586
struct CodexScannedSession {
@@ -2473,6 +2474,7 @@ enum CostUsageScanner {
24732474
if Self.keepCachedCodexFileIfFresh(input: input, context: context, cache: &cache, state: &state) {
24742475
return
24752476
}
2477+
state.changedLineageInputs = true
24762478
if try Self.appendCodexFileIncrementIfPossible(input: input, context: context, cache: &cache, state: &state) {
24772479
return
24782480
}
@@ -2682,6 +2684,7 @@ enum CostUsageScanner {
26822684
let shouldDrop = shouldDropAllUnscannedFiles ||
26832685
old.touchesCodexScanWindow(sinceKey: range.scanSinceKey, untilKey: range.scanUntilKey)
26842686
guard shouldDrop else { continue }
2687+
scanState.changedLineageInputs = true
26852688
Self.applyFileDays(cache: &cache, fileDays: old.days, sign: -1)
26862689
cache.files.removeValue(forKey: key)
26872690
}
@@ -2692,6 +2695,7 @@ enum CostUsageScanner {
26922695
guard old.touchesCodexScanWindow(sinceKey: range.scanSinceKey, untilKey: range.scanUntilKey)
26932696
else { continue }
26942697
guard FileManager.default.fileExists(atPath: key) else {
2698+
scanState.changedLineageInputs = true
26952699
Self.applyFileDays(cache: &cache, fileDays: old.days, sign: -1)
26962700
cache.files.removeValue(forKey: key)
26972701
continue
@@ -2708,12 +2712,14 @@ enum CostUsageScanner {
27082712
? [cachedUntilKey, range.scanUntilKey].compactMap(\.self).max() ?? range.scanUntilKey
27092713
: range.scanUntilKey
27102714
Self.pruneDays(cache: &cache, sinceKey: retainedSinceKey, untilKey: retainedUntilKey)
2711-
try Self.recordCodexLineageShadow(
2712-
files: files,
2713-
roots: plan.roots,
2714-
cache: cache,
2715-
range: range,
2716-
checkCancellation: checkCancellation)
2715+
if scanState.changedLineageInputs {
2716+
try Self.recordCodexLineageShadow(
2717+
files: files,
2718+
roots: plan.roots,
2719+
cache: cache,
2720+
range: range,
2721+
checkCancellation: checkCancellation)
2722+
}
27172723
cache.roots = plan.rootsFingerprint
27182724
cache.scanSinceKey = retainedSinceKey
27192725
cache.scanUntilKey = retainedUntilKey

Tests/CodexBarTests/CodexLineageLedgerTests.swift

Lines changed: 32 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -244,6 +244,36 @@ struct CodexLineageLedgerTests {
244244
#expect(report.duplicateObservationCount == 2)
245245
}
246246

247+
@Test
248+
func `matching event hints with different token states remain distinct`() throws {
249+
let first = Self.observation(
250+
eventID: "turn-a:0", timestamp: "2026-07-09T12:00:00Z", input: 100, totalInput: 100)
251+
let forked = Self.observation(
252+
eventID: "turn-a:0", timestamp: "2026-07-09T12:01:00Z", input: 25, totalInput: 125)
253+
let report = try CodexLineageLedger.reconcile(
254+
documents: [Self.document(owner: "root", observations: [first, forked])],
255+
localTimeZone: .gmt)
256+
257+
#expect(report.utcDays["2026-07-09"]?.input == 125)
258+
#expect(report.acceptedObservationCount == 2)
259+
#expect(report.duplicateObservationCount == 0)
260+
}
261+
262+
@Test
263+
func `different event ordinals do not revive an unchanged owner state`() throws {
264+
let first = Self.observation(
265+
eventID: "turn-a:0", timestamp: "2026-07-09T12:00:00Z", input: 100, totalInput: 100)
266+
let repeated = Self.observation(
267+
eventID: "turn-a:1", timestamp: "2026-07-09T12:01:00Z", input: 100, totalInput: 100)
268+
let report = try CodexLineageLedger.reconcile(
269+
documents: [Self.document(owner: "root", observations: [first, repeated])],
270+
localTimeZone: .gmt)
271+
272+
#expect(report.utcDays["2026-07-09"]?.input == 100)
273+
#expect(report.acceptedObservationCount == 1)
274+
#expect(report.duplicateObservationCount == 1)
275+
}
276+
247277
@Test
248278
func `complete token state distinguishes observations within a lineage`() throws {
249279
let first = Self.observation(
@@ -353,6 +383,7 @@ struct CodexLineageLedgerTests {
353383
}
354384

355385
private static func observation(
386+
eventID: String? = nil,
356387
timestamp: String,
357388
model: String = CostUsagePricing.codexUnattributedModel,
358389
input: Int,
@@ -361,6 +392,7 @@ struct CodexLineageLedgerTests {
361392
totalInput: Int) -> CodexLineageLedger.Observation
362393
{
363394
.init(
395+
eventID: eventID,
364396
timestamp: timestamp,
365397
model: model,
366398
last: .init(input: input, cached: cached, output: output),

0 commit comments

Comments
 (0)