Go-E: re-add session energy for v2 (#18138)
This commit is contained in:
parent
879378dc4f
commit
25902b5fdd
4 changed files with 80 additions and 25 deletions
|
|
@ -38,13 +38,18 @@ type GoE struct {
|
|||
}
|
||||
|
||||
func init() {
|
||||
registry.Add("go-e", NewGoEFromConfig)
|
||||
registry.Add("go-e", func(other map[string]interface{}) (api.Charger, error) {
|
||||
return newGoEFromConfig(true, other)
|
||||
})
|
||||
registry.Add("go-e-v3", func(other map[string]interface{}) (api.Charger, error) {
|
||||
return newGoEFromConfig(false, other)
|
||||
})
|
||||
}
|
||||
|
||||
//go:generate decorate -f decorateGoE -b *GoE -r api.Charger -t "api.PhaseSwitcher,Phases1p3p,func(int) error"
|
||||
//go:generate decorate -f decorateGoE -b *GoE -r api.Charger -t "api.ChargeRater,ChargedEnergy,func() (float64, error)" -t "api.PhaseSwitcher,Phases1p3p,func(int) error"
|
||||
|
||||
// NewGoEFromConfig creates a go-e charger from generic config
|
||||
func NewGoEFromConfig(other map[string]interface{}) (api.Charger, error) {
|
||||
// newGoEFromConfig creates a go-e charger from generic config
|
||||
func newGoEFromConfig(v2 bool, other map[string]interface{}) (api.Charger, error) {
|
||||
cc := struct {
|
||||
Token string
|
||||
URI string
|
||||
|
|
@ -61,11 +66,26 @@ func NewGoEFromConfig(other map[string]interface{}) (api.Charger, error) {
|
|||
return nil, errors.New("must have either uri or token")
|
||||
}
|
||||
|
||||
return NewGoE(cc.URI, cc.Token, cc.Cache)
|
||||
c, err := NewGoE(cc.URI, cc.Token, cc.Cache)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
var chargedEnergy func() (float64, error)
|
||||
if v2 {
|
||||
chargedEnergy = c.chargedEnergy
|
||||
}
|
||||
|
||||
var phases1p3p func(int) error
|
||||
if c.api.IsV2() {
|
||||
phases1p3p = c.phases1p3p
|
||||
}
|
||||
|
||||
return decorateGoE(c, chargedEnergy, phases1p3p), nil
|
||||
}
|
||||
|
||||
// NewGoE creates GoE charger
|
||||
func NewGoE(uri, token string, cache time.Duration) (api.Charger, error) {
|
||||
func NewGoE(uri, token string, cache time.Duration) (*GoE, error) {
|
||||
c := &GoE{}
|
||||
|
||||
log := util.NewLogger("go-e").Redact(token)
|
||||
|
|
@ -80,10 +100,6 @@ func NewGoE(uri, token string, cache time.Duration) (api.Charger, error) {
|
|||
return nil, api.ErrSponsorRequired
|
||||
}
|
||||
|
||||
if c.api.IsV2() {
|
||||
return decorateGoE(c, c.phases1p3p), nil
|
||||
}
|
||||
|
||||
return c, nil
|
||||
}
|
||||
|
||||
|
|
@ -203,6 +219,17 @@ func (c *GoE) TotalEnergy() (float64, error) {
|
|||
return resp.TotalEnergy(), err
|
||||
}
|
||||
|
||||
// chargedEnergy implements the api.ChargeRater interface - v2 only
|
||||
// https://github.com/evcc-io/evcc/issues/13726
|
||||
func (c *GoE) chargedEnergy() (float64, error) {
|
||||
resp, err := c.api.Status()
|
||||
if err != nil {
|
||||
return 0, err
|
||||
}
|
||||
|
||||
return resp.ChargedEnergy(), err
|
||||
}
|
||||
|
||||
// phases1p3p implements the api.PhaseSwitcher interface - v2 only
|
||||
func (c *GoE) phases1p3p(phases int) error {
|
||||
if phases == 3 {
|
||||
|
|
|
|||
|
|
@ -6,12 +6,23 @@ import (
|
|||
"github.com/evcc-io/evcc/api"
|
||||
)
|
||||
|
||||
func decorateGoE(base *GoE, phaseSwitcher func(int) error) api.Charger {
|
||||
func decorateGoE(base *GoE, chargeRater func() (float64, error), phaseSwitcher func(int) error) api.Charger {
|
||||
switch {
|
||||
case phaseSwitcher == nil:
|
||||
case chargeRater == nil && phaseSwitcher == nil:
|
||||
return base
|
||||
|
||||
case phaseSwitcher != nil:
|
||||
case chargeRater != nil && phaseSwitcher == nil:
|
||||
return &struct {
|
||||
*GoE
|
||||
api.ChargeRater
|
||||
}{
|
||||
GoE: base,
|
||||
ChargeRater: &decorateGoEChargeRaterImpl{
|
||||
chargeRater: chargeRater,
|
||||
},
|
||||
}
|
||||
|
||||
case chargeRater == nil && phaseSwitcher != nil:
|
||||
return &struct {
|
||||
*GoE
|
||||
api.PhaseSwitcher
|
||||
|
|
@ -21,11 +32,34 @@ func decorateGoE(base *GoE, phaseSwitcher func(int) error) api.Charger {
|
|||
phaseSwitcher: phaseSwitcher,
|
||||
},
|
||||
}
|
||||
|
||||
case chargeRater != nil && phaseSwitcher != nil:
|
||||
return &struct {
|
||||
*GoE
|
||||
api.ChargeRater
|
||||
api.PhaseSwitcher
|
||||
}{
|
||||
GoE: base,
|
||||
ChargeRater: &decorateGoEChargeRaterImpl{
|
||||
chargeRater: chargeRater,
|
||||
},
|
||||
PhaseSwitcher: &decorateGoEPhaseSwitcherImpl{
|
||||
phaseSwitcher: phaseSwitcher,
|
||||
},
|
||||
}
|
||||
}
|
||||
|
||||
return nil
|
||||
}
|
||||
|
||||
type decorateGoEChargeRaterImpl struct {
|
||||
chargeRater func() (float64, error)
|
||||
}
|
||||
|
||||
func (impl *decorateGoEChargeRaterImpl) ChargedEnergy() (float64, error) {
|
||||
return impl.chargeRater()
|
||||
}
|
||||
|
||||
type decorateGoEPhaseSwitcherImpl struct {
|
||||
phaseSwitcher func(int) error
|
||||
}
|
||||
|
|
|
|||
|
|
@ -33,12 +33,11 @@ func (h *handler) ServeHTTP(w http.ResponseWriter, r *http.Request) {
|
|||
}
|
||||
|
||||
func TestGoEV1(t *testing.T) {
|
||||
h := &handler{}
|
||||
srv := httptest.NewServer(h)
|
||||
srv := httptest.NewServer(new(handler))
|
||||
|
||||
sponsor.Subject = "foo"
|
||||
|
||||
wb, err := NewGoE(srv.URL, "", 0)
|
||||
wb, err := newGoEFromConfig(false, map[string]any{"uri": srv.URL})
|
||||
if err != nil {
|
||||
t.Error(err)
|
||||
}
|
||||
|
|
@ -57,13 +56,12 @@ func TestGoEV1(t *testing.T) {
|
|||
}
|
||||
|
||||
func TestGoEV2(t *testing.T) {
|
||||
h := &handler{}
|
||||
srv := httptest.NewServer(h)
|
||||
srv := httptest.NewServer(new(handler))
|
||||
srv.Config.Handler.(*handler).expect("/api/status?filter=alw")
|
||||
|
||||
sponsor.Subject = "foo"
|
||||
|
||||
h.expect("/api/status?filter=alw")
|
||||
wb, err := NewGoE(srv.URL, "", 0)
|
||||
wb, err := newGoEFromConfig(false, map[string]any{"uri": srv.URL})
|
||||
if err != nil {
|
||||
t.Error(err)
|
||||
}
|
||||
|
|
|
|||
|
|
@ -9,19 +9,15 @@ requirements:
|
|||
description:
|
||||
de: |
|
||||
Benötigt mindestens Firmware 052.1 oder neuer.
|
||||
|
||||
Für 1P/3P-Phasenumschaltung muss die HTTP API v2 im Charger aktiviert sein.
|
||||
|
||||
In der Go-E App (Menüpunkt "Auto") sollte die Option "Ausstecken simulieren" aktiviert sein.
|
||||
en: |
|
||||
Requires firmware 052.1 or later.
|
||||
|
||||
For 1P/3P-Phase switching the HTTP API v2 in the charger setup needs to be activated.
|
||||
|
||||
The “simulate unplugging” option should be activated in the Go-E app ("Car" menu item).
|
||||
evcc: ["sponsorship"]
|
||||
params:
|
||||
- name: host
|
||||
render: |
|
||||
type: go-e
|
||||
type: go-e-v3
|
||||
uri: http://{{ .host }}
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue