[upstream-fix] le repli sur ChargingModeEco emportait des modes sans échéance

prepareInformation() repliait sur ChargingModeEco toute borne dont
nextEndTime() est invalide, dès lors que son mode n'était pas
ChargingModeNormal. Or ce repli n'a de sens que pour les modes qui EXIGENT
une échéance — c'est bien ce que font les deux autres sites du même repli
(planSpotMarketCharging, planSurplusCharging), qui testent explicitement
EcoWithTargetTime / EcoMinWithTargetTime. C'est ce site-ci qui a perdu la
garde en 2070b0d, quand les deux modes ETM ont été ajoutés.

Deux conséquences, toutes deux silencieuses :

  - ChargingModeEcoWithMinCurrent était réécrit en ChargingModeEco au cycle
    suivant, PERSISTÉ et notifié par chargingInfoChanged. Le mode « éco +
    courant minimum garanti » ne survivait donc jamais à un cycle, et la
    branche d'adjustEvChargers() qui l'applique était morte. Du point de vue
    de l'app, un réglage posé par l'utilisateur disparaissait tout seul.
  - ChargingModeEco était « replié » sur lui-même à CHAQUE cycle :
    setChargingMode, storeChargingInfo (écriture disque) et une notification
    chargingInfoChanged, sans qu'aucune valeur ne change. Un *Changed qui ne
    change rien, à chaque tour, pour chaque borne en éco.

Trouvé en écrivant le test d'aller-retour de SetChargingInfo, qui échouait
sur la réécriture du mode.

Suite charging 16/16, simulation `run` 16/16.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_017TVywtayEeoRJ2yWUW4iZj
This commit is contained in:
Patrick Schurig 2026-08-27 10:09:08 +02:00
parent a8a51d6b32
commit 1906d2116a

View File

@ -577,17 +577,31 @@ void SmartChargingManager::prepareInformation(const QDateTime &currentDateTime)
continue;
}
// [ETM] Le repli ne concerne QUE les modes qui EXIGENT une échéance. La condition
// portait sur « mode != Normal », donc elle emportait aussi les deux modes qui n'ont
// jamais eu d'échéance :
// - ChargingModeEcoWithMinCurrent était réécrit en ChargingModeEco au cycle suivant,
// PERSISTÉ et notifié — le mode « éco + courant minimum garanti » ne survivait
// donc jamais à un cycle, et la branche 4 d'adjustEvChargers() qui l'applique
// était morte. Réglage détruit en silence, du point de vue de l'app.
// - ChargingModeEco était « replié » sur lui-même à CHAQUE cycle : setChargingMode,
// storeChargingInfo (écriture disque) et chargingInfoChanged (notification) sans
// qu'aucune valeur ne change. Un *Changed qui ne change rien (invariant 11).
// Les deux autres sites du même repli (planSpotMarketCharging, planSurplusCharging)
// portent déjà cette garde ; c'est ce site-ci qui l'avait perdue en 7588473.
const ChargingInfo::ChargingMode currentMode = m_chargingInfos.value(evCharger->id()).chargingMode();
const bool exigeUneEcheance = currentMode == ChargingInfo::ChargingModeEcoWithTargetTime
|| currentMode == ChargingInfo::ChargingModeEcoMinWithTargetTime;
QDateTime endDateTime = m_chargingInfos.value(evCharger->id()).nextEndTime(currentDateTime);
if (!endDateTime.isValid() && m_chargingInfos.value(evCharger->id()).chargingMode() != ChargingInfo::ChargingModeNormal) {
if (!endDateTime.isValid() && exigeUneEcheance) {
qCDebug(dcNymeaEnergy()).nospace() << "No valid target time set for " << evCharger->name();
const ChargingInfo::ChargingMode currentMode = m_chargingInfos.value(evCharger->id()).chargingMode();
ChargingInfo::ChargingMode fallbackMode;
if (currentMode == ChargingInfo::ChargingModeEcoMinWithTargetTime) {
qCDebug(dcNymeaEnergy()) << "Resetting to ECO with min current mode.";
fallbackMode = ChargingInfo::ChargingModeEcoWithMinCurrent;
} else {
if (currentMode == ChargingInfo::ChargingModeEcoWithTargetTime)
qCDebug(dcNymeaEnergy()) << "Resetting to ECO mode without time.";
qCDebug(dcNymeaEnergy()) << "Resetting to ECO mode without time.";
fallbackMode = ChargingInfo::ChargingModeEco;
}
m_chargingInfos[evCharger->id()].setChargingMode(fallbackMode);