fix: materialize stationary yutong daily mileage
This commit is contained in:
@@ -1838,6 +1838,107 @@ func TestWriterSkipsConsecutiveDuplicateMileageSamples(t *testing.T) {
|
||||
}
|
||||
}
|
||||
|
||||
func TestWriterCarriesPreviousYutongMileageIntoStationaryDay(t *testing.T) {
|
||||
exec := &recordingExec{}
|
||||
loc := time.FixedZone("Asia/Shanghai", 8*3600)
|
||||
writer := NewWriter(exec, loc)
|
||||
eventTime := time.Date(2026, 7, 19, 6, 5, 42, 0, loc)
|
||||
previousTime := time.Date(2026, 7, 18, 16, 48, 10, 0, loc)
|
||||
vin := "LMRKH9AC9R1004099"
|
||||
sourceKey := "YUTONG_MQTT:" + vin + "@PLATFORM:yutong"
|
||||
sample := MetricSample{
|
||||
VIN: vin,
|
||||
Protocol: envelope.ProtocolYutongMQTT,
|
||||
StatDate: "2026-07-19",
|
||||
SourceKey: sourceKey,
|
||||
}
|
||||
writer.baselineCache[mileageCacheKey(sample)] = sourceBaselineCacheEntry{
|
||||
baseline: sourceBaseline{
|
||||
LatestTotalKM: 24245,
|
||||
LatestEventTime: previousTime,
|
||||
QualityReason: QualityReasonHistorical,
|
||||
},
|
||||
found: true,
|
||||
cachedAt: time.Now(),
|
||||
}
|
||||
event := managedTestSource(envelope.FrameEnvelope{
|
||||
Protocol: envelope.ProtocolYutongMQTT,
|
||||
VIN: vin,
|
||||
DeviceID: vin,
|
||||
SourceEndpoint: "mqtt://yutong/ytforward/shln/2",
|
||||
SourceCode: "yutong",
|
||||
PlatformName: "宇通",
|
||||
EventTimeMS: eventTime.UnixMilli(),
|
||||
ReceivedAtMS: eventTime.UnixMilli(),
|
||||
Fields: map[string]any{
|
||||
"yutong_mqtt.data.latitude": "30.645438",
|
||||
"yutong_mqtt.data.longitude": "114.435672",
|
||||
"yutong_mqtt.data.meter_speed": "0",
|
||||
},
|
||||
})
|
||||
|
||||
result, err := writer.AppendWithResult(context.Background(), event)
|
||||
if err != nil {
|
||||
t.Fatalf("AppendWithResult() error = %v", err)
|
||||
}
|
||||
if result.SamplesRecoveredStationary != 1 || result.SamplesWritten != 1 || result.ProjectionsWritten != 1 {
|
||||
t.Fatalf("stationary carry result = %+v", result)
|
||||
}
|
||||
if result.SamplesSkippedMissingMileage != 1 {
|
||||
t.Fatalf("source-data evidence must retain the missing-mileage counter: %+v", result)
|
||||
}
|
||||
if len(exec.calls) != 7 {
|
||||
t.Fatalf("exec calls = %d, want source touch plus six mileage writes", len(exec.calls))
|
||||
}
|
||||
sourceWrite := exec.calls[1]
|
||||
if !strings.Contains(sourceWrite.query, "INSERT INTO vehicle_daily_mileage_source") {
|
||||
t.Fatalf("source mileage write missing: %s", sourceWrite.query)
|
||||
}
|
||||
if got := sourceWrite.args[9]; got != float64(24245) {
|
||||
t.Fatalf("first total mileage = %#v, want carried 24245", got)
|
||||
}
|
||||
if got := sourceWrite.args[10]; got != float64(24245) {
|
||||
t.Fatalf("latest total mileage = %#v, want carried 24245", got)
|
||||
}
|
||||
if got := sourceWrite.args[11]; got != float64(0) {
|
||||
t.Fatalf("daily mileage = %#v, want explicit zero", got)
|
||||
}
|
||||
if got := sourceWrite.args[16]; got != QualityReasonStationaryCarry {
|
||||
t.Fatalf("quality reason = %#v, want %q", got, QualityReasonStationaryCarry)
|
||||
}
|
||||
}
|
||||
|
||||
func TestWriterDoesNotCarryMileageForMovingYutongFrame(t *testing.T) {
|
||||
exec := &recordingExec{}
|
||||
loc := time.FixedZone("Asia/Shanghai", 8*3600)
|
||||
writer := NewWriter(exec, loc)
|
||||
eventTime := time.Date(2026, 7, 19, 8, 0, 0, 0, loc)
|
||||
event := managedTestSource(envelope.FrameEnvelope{
|
||||
Protocol: envelope.ProtocolYutongMQTT,
|
||||
VIN: "LMRKH9AC9R1004099",
|
||||
DeviceID: "LMRKH9AC9R1004099",
|
||||
SourceEndpoint: "mqtt://yutong/ytforward/shln/2",
|
||||
SourceCode: "yutong",
|
||||
EventTimeMS: eventTime.UnixMilli(),
|
||||
Fields: map[string]any{
|
||||
"yutong_mqtt.data.latitude": "30.645438",
|
||||
"yutong_mqtt.data.longitude": "114.435672",
|
||||
"yutong_mqtt.data.meter_speed": "12",
|
||||
},
|
||||
})
|
||||
|
||||
result, err := writer.AppendWithResult(context.Background(), event)
|
||||
if err != nil {
|
||||
t.Fatalf("AppendWithResult() error = %v", err)
|
||||
}
|
||||
if result.SamplesRecoveredStationary != 0 || result.SamplesWritten != 0 || result.SamplesSkippedMissingMileage != 1 {
|
||||
t.Fatalf("moving frame must remain missing-mileage evidence: %+v", result)
|
||||
}
|
||||
if len(exec.calls) != 1 || !strings.Contains(exec.calls[0].query, "INSERT INTO vehicle_data_source") {
|
||||
t.Fatalf("moving frame writes = %+v, want source touch only", exec.calls)
|
||||
}
|
||||
}
|
||||
|
||||
func TestWriterAppendWithResultReportsDuplicateMileage(t *testing.T) {
|
||||
exec := &recordingExec{}
|
||||
writer := NewWriter(exec, time.FixedZone("Asia/Shanghai", 8*3600))
|
||||
|
||||
Reference in New Issue
Block a user