From eb15f37d660a42fd35af42dfe9dbc9a4051ccce4 Mon Sep 17 00:00:00 2001 From: Andreas Linde <42185+DerAndereAndi@users.noreply.github.com> Date: Sun, 7 Jul 2024 21:20:21 +0200 Subject: [PATCH] Improve EEBUS support for Elli Gen 1 (part 2) (#14760) - Tested with Elli Charger Pro Gen 1 - Handle missing power and use current data in evcc instead of eebus library - Check for use case scenario availability for power and current data --- charger/eebus.go | 43 ++++++++++++++++++++++++++++++++++++++++-- charger/eebus/eebus.go | 4 +--- go.mod | 2 +- go.sum | 4 ++-- 4 files changed, 45 insertions(+), 8 deletions(-) diff --git a/charger/eebus.go b/charger/eebus.go index 3e32ac468..5a941d58d 100644 --- a/charger/eebus.go +++ b/charger/eebus.go @@ -407,6 +407,11 @@ func (c *EEBus) writeCurrentLimitData(currents []float64) error { return errors.New("no ev connected") } + // check if the EVSE supports overload protection limits + if !c.uc.OpEV.IsScenarioAvailableAtEntity(evEntity, 1) { + return api.ErrNotAvailable + } + _, maxLimits, _, err := c.uc.OpEV.CurrentLimits(evEntity) if err != nil { return errors.New("no limits available") @@ -533,6 +538,11 @@ func (c *EEBus) writeLoadControlLimitsVASVW(limits []ucapi.LoadLimitsPhase) bool return false } + // check if the EVSE supports optimization of self consumption limits + if !c.uc.OscEV.IsScenarioAvailableAtEntity(evEntity, 1) { + return false + } + // on OSCEV all limits have to be active except they are set to the default value minLimit, _, _, err := c.uc.OscEV.CurrentLimits(evEntity) if err != nil { @@ -613,8 +623,28 @@ func (c *EEBus) currentPower() (float64, error) { return 0, api.ErrNotAvailable } - powers, err := c.uc.EvCem.PowerPerPhase(evEntity) - if err != nil { + var powers []float64 + + // does the EVSE provide power data? + if c.uc.EvCem.IsScenarioAvailableAtEntity(evEntity, 2) { + // is power data available for real? Elli Gen1 says it supports it, but doesn't provide any data + if powerData, err := c.uc.EvCem.PowerPerPhase(evEntity); err == nil { + powers = powerData + } + } + + // if no power data is available, and currents are reported to be supported, use currents + if len(powers) == 0 && c.uc.EvCem.IsScenarioAvailableAtEntity(evEntity, 1) { + // no power provided, calculate from current + if currents, err := c.uc.EvCem.CurrentPerPhase(evEntity); err == nil { + for _, current := range currents { + powers = append(powers, current*voltage) + } + } + } + + // if still no power data is available, return an error + if len(powers) == 0 { return 0, api.ErrNotAvailable } @@ -636,6 +666,10 @@ func (c *EEBus) chargedEnergy() (float64, error) { return 0, nil } + if !c.uc.EvCem.IsScenarioAvailableAtEntity(evEntity, 3) { + return 0, api.ErrNotAvailable + } + energy, err := c.uc.EvCem.EnergyCharged(evEntity) if err != nil { return 0, api.ErrNotAvailable @@ -651,6 +685,11 @@ func (c *EEBus) currents() (float64, float64, float64, error) { return 0, 0, 0, nil } + // check if the EVSE supports currents + if !c.uc.EvCem.IsScenarioAvailableAtEntity(evEntity, 1) { + return 0, 0, 0, api.ErrNotAvailable + } + res, err := c.uc.EvCem.CurrentPerPhase(evEntity) if err != nil { if err == eebusapi.ErrDataNotAvailable { diff --git a/charger/eebus/eebus.go b/charger/eebus/eebus.go index bb80814d2..d7fc7ad80 100644 --- a/charger/eebus/eebus.go +++ b/charger/eebus/eebus.go @@ -118,7 +118,7 @@ func NewServer(other Config) (*EEBus, error) { EEBUSBrandName, EEBUSBrandName, EEBUSModel, serial, model.DeviceTypeTypeEnergyManagementSystem, []model.EntityTypeType{model.EntityTypeTypeCEM}, - port, certificate, 230, time.Second*4, + port, certificate, time.Second*4, ) if err != nil { return nil, err @@ -206,7 +206,6 @@ func (c *EEBus) evseUsecaseCB(ski string, device spineapi.DeviceRemoteInterface, // EEBUSServiceHandler -// no implementation needed, handled in CEM events func (c *EEBus) RemoteSKIConnected(service eebusapi.ServiceInterface, ski string) { c.mux.Lock() defer c.mux.Unlock() @@ -216,7 +215,6 @@ func (c *EEBus) RemoteSKIConnected(service eebusapi.ServiceInterface, ski string } } -// no implementation needed, handled in CEM events func (c *EEBus) RemoteSKIDisconnected(service eebusapi.ServiceInterface, ski string) { c.mux.Lock() defer c.mux.Unlock() diff --git a/go.mod b/go.mod index 455a6e033..209db26e7 100644 --- a/go.mod +++ b/go.mod @@ -197,6 +197,6 @@ require ( replace gopkg.in/yaml.v3 => github.com/andig/yaml v0.0.0-20240531135838-1ff5761ab467 -replace github.com/enbility/eebus-go => github.com/enbility/eebus-go v0.0.0-20240705085643-aef0f7bf9e5d +replace github.com/enbility/eebus-go => github.com/enbility/eebus-go v0.0.0-20240705140947-e13aec8af1ba replace github.com/enbility/spine-go => github.com/enbility/spine-go v0.0.0-20240705075417-fb2969d753c1 diff --git a/go.sum b/go.sum index 85b41ef72..644bc7a4b 100644 --- a/go.sum +++ b/go.sum @@ -121,8 +121,8 @@ github.com/eapache/queue v1.1.0/go.mod h1:6eCeP0CKFpHLu8blIFXhExK/dRa7WDZfr6jVFP github.com/eclipse/paho.mqtt.golang v1.4.3 h1:2kwcUGn8seMUfWndX0hGbvH8r7crgcJguQNCyp70xik= github.com/eclipse/paho.mqtt.golang v1.4.3/go.mod h1:CSYvoAlsMkhYOXh/oKyxa8EcBci6dVkLCbo5tTC1RIE= github.com/edsrzf/mmap-go v1.0.0/go.mod h1:YO35OhQPt3KJa3ryjFM5Bs14WD66h8eGKpfaBNrHW5M= -github.com/enbility/eebus-go v0.0.0-20240705085643-aef0f7bf9e5d h1:PweAytR6T0Cd+RCTx/94VZbdkq70bsu2C3/AnrSCBGg= -github.com/enbility/eebus-go v0.0.0-20240705085643-aef0f7bf9e5d/go.mod h1:6ka3OsfqJDiXAWMMYO1LkKQa7xSIgqrhwOeP5kO/yao= +github.com/enbility/eebus-go v0.0.0-20240705140947-e13aec8af1ba h1:wlfFa9joFrll4u3nqPc25q3QyNUxiYSa0l8sPiYMOCA= +github.com/enbility/eebus-go v0.0.0-20240705140947-e13aec8af1ba/go.mod h1:6ka3OsfqJDiXAWMMYO1LkKQa7xSIgqrhwOeP5kO/yao= github.com/enbility/ship-go v0.5.1 h1:8Vax1MpyI/C+kQlMFAzQ7/h/xJ7fuumSLJy9FYgEkcE= github.com/enbility/ship-go v0.5.1/go.mod h1:jewJWYQ10jNhsnhS1C4jESx3CNmDa5HNWZjBhkTug5Y= github.com/enbility/spine-go v0.0.0-20240705075417-fb2969d753c1 h1:H7Jvd7QOmA3IJtfswnoXY37WFSxYeMCIQemtmrN1pS8=