Sessions: fix odometer not persisted
This commit is contained in:
parent
5ddf3c841f
commit
42ca83d3c0
4 changed files with 46 additions and 36 deletions
|
|
@ -1,8 +1,6 @@
|
|||
package db
|
||||
|
||||
import (
|
||||
"time"
|
||||
|
||||
serverdb "github.com/evcc-io/evcc/server/db"
|
||||
"github.com/evcc-io/evcc/util"
|
||||
"gorm.io/gorm"
|
||||
|
|
@ -35,7 +33,6 @@ func New(name string) (*DB, error) {
|
|||
func (s *DB) Session(meter float64) *Session {
|
||||
t := Session{
|
||||
Loadpoint: s.name,
|
||||
Created: time.Now(),
|
||||
MeterStart: meter,
|
||||
}
|
||||
|
||||
|
|
|
|||
|
|
@ -31,15 +31,6 @@ type Session struct {
|
|||
ChargedEnergy float64 `json:"chargedEnergy" csv:"Charged Energy (kWh)" gorm:"column:charged_kwh"`
|
||||
}
|
||||
|
||||
// Stop stops charging session with end meter reading and due total amount
|
||||
func (t *Session) Stop(chargedWh, total float64) {
|
||||
if chargedEnergy := chargedWh / 1e3; chargedEnergy > t.ChargedEnergy {
|
||||
t.ChargedEnergy = chargedEnergy
|
||||
}
|
||||
t.MeterStop = total
|
||||
t.Finished = time.Now()
|
||||
}
|
||||
|
||||
// Sessions is a list of sessions
|
||||
type Sessions []Session
|
||||
|
||||
|
|
|
|||
|
|
@ -387,7 +387,12 @@ func (lp *LoadPoint) evChargeStartHandler() {
|
|||
// soc update reset
|
||||
lp.socUpdated = time.Time{}
|
||||
|
||||
lp.startSession()
|
||||
// set created when first charging session segment starts
|
||||
lp.updateSession(func(session *db.Session) {
|
||||
if session.Created.IsZero() {
|
||||
session.Created = lp.clock.Now()
|
||||
}
|
||||
})
|
||||
}
|
||||
|
||||
// evChargeStopHandler sends external stop event
|
||||
|
|
@ -432,15 +437,17 @@ func (lp *LoadPoint) evVehicleConnectHandler() {
|
|||
|
||||
// immediately allow pv mode activity
|
||||
lp.elapsePVTimer()
|
||||
|
||||
// create charging session
|
||||
lp.createSession()
|
||||
}
|
||||
|
||||
// evVehicleDisconnectHandler sends external start event
|
||||
func (lp *LoadPoint) evVehicleDisconnectHandler() {
|
||||
lp.log.INFO.Println("car disconnected")
|
||||
|
||||
// ensure session is persisted and closed before vehicle is changed
|
||||
lp.stopSession()
|
||||
lp.finalizeSession()
|
||||
// session is persisted during evChargeStopHandler which runs before
|
||||
lp.clearSession()
|
||||
|
||||
// phases are unknown when vehicle disconnects
|
||||
lp.resetMeasuredPhases()
|
||||
|
|
|
|||
|
|
@ -1,6 +1,8 @@
|
|||
package core
|
||||
|
||||
import (
|
||||
"time"
|
||||
|
||||
"github.com/evcc-io/evcc/api"
|
||||
"github.com/evcc-io/evcc/core/db"
|
||||
)
|
||||
|
|
@ -20,39 +22,50 @@ func (lp *LoadPoint) chargeMeterTotal() float64 {
|
|||
return f
|
||||
}
|
||||
|
||||
func (lp *LoadPoint) startSession() {
|
||||
// createSession creates a charging session. The created timestamp is empty until set by evChargeStartHandler.
|
||||
// The session is not persisted yet. That will only happen when stopSession is called.
|
||||
func (lp *LoadPoint) createSession() {
|
||||
// test guard
|
||||
if lp.db == nil {
|
||||
if lp.db == nil || lp.session != nil {
|
||||
return
|
||||
}
|
||||
|
||||
if lp.session == nil {
|
||||
lp.session = lp.db.Session(lp.chargeMeterTotal())
|
||||
lp.session = lp.db.Session(lp.chargeMeterTotal())
|
||||
|
||||
if lp.vehicle != nil {
|
||||
lp.session.Vehicle = lp.vehicle.Title()
|
||||
}
|
||||
|
||||
if c, ok := lp.charger.(api.Identifier); ok {
|
||||
if id, err := c.Identify(); err == nil {
|
||||
lp.session.Identifier = id
|
||||
}
|
||||
}
|
||||
|
||||
// TODO remove
|
||||
lp.log.DEBUG.Println("session started")
|
||||
|
||||
lp.db.Persist(lp.session)
|
||||
if lp.vehicle != nil {
|
||||
lp.session.Vehicle = lp.vehicle.Title()
|
||||
}
|
||||
|
||||
if c, ok := lp.charger.(api.Identifier); ok {
|
||||
if id, err := c.Identify(); err == nil {
|
||||
lp.session.Identifier = id
|
||||
}
|
||||
}
|
||||
|
||||
// TODO remove
|
||||
lp.log.DEBUG.Println("session started")
|
||||
}
|
||||
|
||||
// stopSession ends a charging session segment and persists the session.
|
||||
func (lp *LoadPoint) stopSession() {
|
||||
// test guard
|
||||
if lp.db == nil || lp.session == nil {
|
||||
return
|
||||
}
|
||||
|
||||
lp.session.Stop(lp.getChargedEnergy(), lp.chargeMeterTotal())
|
||||
// abort the session if charging has never started
|
||||
if lp.session.Created.IsZero() {
|
||||
// TODO remove
|
||||
lp.log.DEBUG.Println("session aborted")
|
||||
return
|
||||
}
|
||||
|
||||
lp.session.Finished = time.Now()
|
||||
lp.session.MeterStop = lp.chargeMeterTotal()
|
||||
|
||||
if chargedEnergy := lp.getChargedEnergy() / 1e3; chargedEnergy > lp.session.ChargedEnergy {
|
||||
lp.session.ChargedEnergy = chargedEnergy
|
||||
}
|
||||
|
||||
// TODO remove
|
||||
lp.log.DEBUG.Println("session stopped")
|
||||
|
|
@ -62,6 +75,7 @@ func (lp *LoadPoint) stopSession() {
|
|||
|
||||
type sessionOption func(*db.Session)
|
||||
|
||||
// updateSession updates any parameter of a charging session and persists the session.
|
||||
func (lp *LoadPoint) updateSession(opts ...sessionOption) {
|
||||
// test guard
|
||||
if lp.db == nil || lp.session == nil {
|
||||
|
|
@ -78,7 +92,8 @@ func (lp *LoadPoint) updateSession(opts ...sessionOption) {
|
|||
lp.db.Persist(lp.session)
|
||||
}
|
||||
|
||||
func (lp *LoadPoint) finalizeSession() {
|
||||
// clearSession clears the charging session without persisting it.
|
||||
func (lp *LoadPoint) clearSession() {
|
||||
// test guard
|
||||
if lp.db == nil {
|
||||
return
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue