feat: 推广 V3.5 实时氢耗并完善导出

This commit is contained in:
lingniu
2026-09-04 15:42:02 +08:00
parent a26179c8fe
commit e402eb5e60
53 changed files with 2855 additions and 320 deletions
@@ -91,7 +91,7 @@ const HydrogenSegmentStreamStateTableSQL = `CREATE TABLE IF NOT EXISTS vehicle_o
last_event_time DATETIME(3) NOT NULL,
last_event_id VARCHAR(128) NOT NULL DEFAULT '',
state_json JSON NOT NULL,
calculation_method VARCHAR(48) NOT NULL DEFAULT 'PRESSURE_NIST_SEGMENT_MEDIAN_5',
calculation_method VARCHAR(80) NOT NULL DEFAULT 'PRESSURE_NIST_VALID_BOUNDARY_CHARGE_CYCLE_V3_5',
quality_status VARCHAR(24) NOT NULL DEFAULT 'NO_DATA',
quality_reason VARCHAR(255) NOT NULL DEFAULT '有效工作段关键帧不足10条',
created_at DATETIME(3) NOT NULL DEFAULT CURRENT_TIMESTAMP(3),
@@ -116,6 +116,18 @@ type HydrogenStreamSample struct {
FuelCellActive bool
FuelCellStateKnown bool
ConsumptionEligible bool
MileageKM float64
MileageKnown bool
SOCPercent float64
SOCKnown bool
VehicleState int
VehicleStateKnown bool
ChargeState int
ChargeStateKnown bool
RunningMode int
RunningModeKnown bool
FuelCellPowerKW float64
FuelCellPowerKnown bool
}
type HydrogenStreamResult struct {
@@ -453,6 +465,26 @@ func HydrogenStreamSampleFromEnvelope(env envelope.FrameEnvelope, loc *time.Loca
fuelCellStateKnown = true
}
}
mileageKM, mileageKnown := firstHydrogenNumber(env.Fields, []string{
envelope.FieldTotalMileageKM, "gb32960.vehicle.total_mileage_km",
})
socPercent, socKnown := firstHydrogenNumber(env.Fields, []string{
envelope.FieldSOCPercent, "gb32960.vehicle.soc_percent",
})
vehicleStateValue, vehicleStateKnown := firstHydrogenNumber(env.Fields, []string{
"vehicle_status", "gb32960.vehicle.vehicle_status",
})
chargeStateValue, chargeStateKnown := firstHydrogenNumber(env.Fields, []string{
"charge_status", "gb32960.vehicle.charge_status",
})
runningModeValue, runningModeKnown := firstHydrogenNumber(env.Fields, []string{
envelope.FieldVehicleRunningMode, "gb32960.vehicle.running_mode",
})
fuelCellVoltage, voltageKnown := firstHydrogenNumber(env.Fields, []string{
"fuel_cell_voltage_v", "gb32960.fuel_cell.fuel_cell_voltage_v",
})
fuelCellCurrent, currentKnown := firstHydrogenNumber(env.Fields, hydrogenCurrentFieldKeys)
fuelCellPowerKnown := voltageKnown && currentKnown && fuelCellVoltage >= 0 && fuelCellCurrent >= 0
if loc == nil {
loc = time.FixedZone("Asia/Shanghai", 8*3600)
}
@@ -475,6 +507,12 @@ func HydrogenStreamSampleFromEnvelope(env envelope.FrameEnvelope, loc *time.Loca
NoiseKG: noiseKG, RefuelThresholdKG: refuelThresholdKG,
FuelCellActive: fuelCellActive, FuelCellStateKnown: fuelCellStateKnown,
ConsumptionEligible: !fuelCellStateKnown || fuelCellActive,
MileageKM: mileageKM, MileageKnown: mileageKnown,
SOCPercent: socPercent, SOCKnown: socKnown && socPercent >= 0 && socPercent <= 100,
VehicleState: int(vehicleStateValue), VehicleStateKnown: vehicleStateKnown,
ChargeState: int(chargeStateValue), ChargeStateKnown: chargeStateKnown,
RunningMode: int(runningModeValue), RunningModeKnown: runningModeKnown,
FuelCellPowerKW: fuelCellVoltage * fuelCellCurrent / 1000, FuelCellPowerKnown: fuelCellPowerKnown,
}, "", true
}
@@ -647,13 +685,13 @@ const insertHydrogenSegmentStreamStateSQL = `INSERT INTO vehicle_open_hydrogen_s
vin,stat_date,source_endpoint,finalized_consumption_kg,projected_consumption_kg,
sample_count,refuel_count,abnormal_drop_count,eligible_interval_count,qualified_segment_count,
last_mass_kg,last_event_time,last_event_id,state_json,calculation_method,quality_status,quality_reason
) VALUES(?,?,?,?,?,?,?,?,?,?,?,?,?,?,'PRESSURE_NIST_SEGMENT_MEDIAN_5',?,?)`
) VALUES(?,?,?,?,?,?,?,?,?,?,?,?,?,?,'PRESSURE_NIST_VALID_BOUNDARY_CHARGE_CYCLE_V3_5',?,?)`
const updateHydrogenSegmentStreamStateSQL = `UPDATE vehicle_open_hydrogen_segment_stream_state
SET source_endpoint=?,finalized_consumption_kg=?,projected_consumption_kg=?,sample_count=?,
refuel_count=?,abnormal_drop_count=?,eligible_interval_count=?,qualified_segment_count=?,
last_mass_kg=?,last_event_time=?,last_event_id=?,state_json=?,
calculation_method='PRESSURE_NIST_SEGMENT_MEDIAN_5',quality_status=?,quality_reason=?
calculation_method='PRESSURE_NIST_VALID_BOUNDARY_CHARGE_CYCLE_V3_5',quality_status=?,quality_reason=?
WHERE vin=? AND stat_date=?`
const projectHydrogenSegmentStreamDailySQL = `INSERT INTO vehicle_open_daily_energy(