// SPDX-License-Identifier: GPL-3.0-or-later /* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * Copyright (C) 2013 - 2024, nymea GmbH * Copyright (C) 2024 - 2025, chargebyte austria GmbH * * This file is part of nymea-energy-plugin-nymea. * * nymea-energy-plugin-nymea.s free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * nymea-energy-plugin-nymea.s distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with nymea-energy-plugin-nymea. If not, see . * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */ #ifndef SMARTCHARGINGMANAGER_H #define SMARTCHARGINGMANAGER_H #include #include #include "energymanagerconfiguration.h" #include "types/charginginfo.h" #include "types/chargingaction.h" #include "types/chargingschedule.h" #include "types/chargingprocessinfo.h" #include "spotmarket/spotmarketmanager.h" // from libnymea #include #include // from libnymea-energy #include class EvCharger; class RootMeter; // Minimum charging current (A) applied when EcoWithMinCurrent is active and no surplus is available static constexpr uint EcoMinChargingCurrent = 6; class SmartChargingManager : public QObject { Q_OBJECT public: explicit SmartChargingManager(EnergyManager *energyManager, ThingManager *thingManager, SpotMarketManager *spotMarketManager, EnergyManagerConfiguration *configuration, QObject *parent = nullptr); uint phasePowerLimit() const; void setPhasePowerLimit(uint phasePowerLimit); double acquisitionTolerance() const; void setAcquisitionTolerance(double acquisitionTolerance); double batteryLevelConsideration() const; void setBatteryLevelConsideration(double batteryLevelConsideration); bool lockOnUnplug() const; void setLockOnUnplug(bool lockOnUnplug); ChargingInfos chargingInfos() const; ChargingInfo chargingInfo(const ThingId &evChargerId) const; EnergyManager::EnergyError setChargingInfo(const ChargingInfo &chargingInfo); ChargingSchedules chargingSchedules() const; // [ETM] Mode dégradé L2 (watchdog fraîcheur compteur). Base = false ; // overridé dans EnergyArbitrator. Exposé pour la notification JSON-RPC. virtual bool degradedMode() const { return false; } SpotMarketManager *spotMarketManager() const; #ifdef ENERGY_SIMULATION void simulationCallUpdate(const QDateTime &dateTime); void simulationCallUpdateManualSoCsWithMeter(EnergyLogs::SampleRate sampleRate, const ThingPowerLogEntry &entry); #endif signals: void phasePowerLimitChanged(int phasePowerLimit); void acquisitionToleranceChanged(double acquisitionTolerance); void batteryLevelConsiderationChanged(double batteryLevelConsideration); void lockOnUnplugChanged(bool lockOnUnplug); void chargingInfoAdded(const ChargingInfo &chargingInfo); void chargingInfoRemoved(const ThingId &evChargerThingId); void chargingInfoChanged(const ChargingInfo &chargingInfo); void chargingSchedulesChanged(); #ifdef ENERGY_SIMULATION void chargingUpdated(); #endif // [ETM] BEGIN — SmartChargingManager protected API for EnergyArbitrator (etm/). // All changes below are visibility-only (private → protected / virtual added). // Zero logic change. Revert by deleting this block and restoring private slots. protected slots: virtual void update(const QDateTime ¤tDateTime); // [ETM] virtual added void prepareInformation(const QDateTime ¤tDateTime); // [ETM] private → protected void planSpotMarketCharging(const QDateTime ¤tDateTime); // [ETM] private → protected void planSurplusCharging(const QDateTime ¤tDateTime); // [ETM] private → protected void adjustEvChargers(const QDateTime ¤tDateTime); // [ETM] private → protected void updateManualSoCsWithoutMeter(const QDateTime ¤tDateTime); // [ETM] private → protected void verifyOverloadProtection(const QDateTime ¤tDateTime); // [ETM] private → protected void verifyOverloadProtectionRecovery(const QDateTime ¤tDateTime); // [ETM] private → protected protected: void executeChargingAction(EvCharger *evCharger, const ChargingAction &chargingAction, const QDateTime ¤tDateTime); // [ETM] private → protected // [ETM] Read-only state accessors — inline, no copies, no logic. const QHash &internalEvChargers() const { return m_evChargers; } // [ETM] new const QHash &internalChargingActions() const { return m_chargingActions; } // [ETM] new RootMeter *internalRootMeter() const { return m_rootMeter; } // [ETM] new // [ETM] END private slots: void updateManualSoCsWithMeter(EnergyLogs::SampleRate sampleRate, const ThingPowerLogEntry &entry); void onThingAdded(Thing *thing); void onThingRemoved(const ThingId &thingId); void onActionExecuted(const Action &action, Thing::ThingError status); void onChargingModeChanged(const ThingId &evChargerId, const ChargingInfo &chargingInfo); private: void setupRootMeter(Thing *thing); void setupEvCharger(Thing *thing); void setupPluggedInHandlers(const Thing *thing); void storeChargingInfo(const ChargingInfo &chargingInfo); void storeManualChargingParameters(const ThingId &evChargerId, bool enabled, int maxChargingCurrent, uint desiredPhaseCount); bool manualChargingEnabled(const ThingId &evChargerId) const; uint manualMaxChargingCurrent(const ThingId &evChargerId) const; uint manualDesiredPhaseCount(const ThingId &evChargerId) const; Electricity::Phases getAscendingPhasesForCount(uint phaseCount); uint getBestPhaseCount(EvCharger *evCharger, double surplusAmpere); QString chargerPhaseKey(EvCharger *evCharger) const; EnergyManager *m_energyManager = nullptr; ThingManager *m_thingManager = nullptr; SpotMarketManager *m_spotMarketManager = nullptr; EnergyManagerConfiguration *m_configuration = nullptr; QHash m_chargingSchedules; QHash m_processInfos; QHash m_chargingActions; QDateTime m_lastSpotMarketPlanning; // Overload protection QHash m_overloadProtectionActive; uint m_phasePowerConsumptionLimit = 25; double m_acquisitionTolerance = 0.5; double m_batteryLevelConsideration = 0.9; QHash m_chargingInfos; RootMeter *m_rootMeter = nullptr; QHash m_evChargers; }; #endif // SMARTCHARGINGMANAGER_H