84 lines
1.9 KiB
Go
84 lines
1.9 KiB
Go
package polestar
|
|
|
|
import (
|
|
"context"
|
|
|
|
"github.com/evcc-io/evcc/util"
|
|
"github.com/evcc-io/evcc/util/request"
|
|
"github.com/hasura/go-graphql-client"
|
|
"golang.org/x/oauth2"
|
|
)
|
|
|
|
// https://github.com/leeyuentuen/polestar_api
|
|
// https://github.com/TA2k/ioBroker.polestar
|
|
|
|
const (
|
|
ApiURI = "https://pc-api.polestar.com/eu-north-1"
|
|
ApiURIv2 = ApiURI + "/mystar-v2"
|
|
)
|
|
|
|
type API struct {
|
|
client *graphql.Client
|
|
}
|
|
|
|
func NewAPI(log *util.Logger, identity oauth2.TokenSource) *API {
|
|
httpClient := request.NewClient(log)
|
|
|
|
// replace client transport with authenticated transport
|
|
httpClient.Transport = &oauth2.Transport{
|
|
Base: httpClient.Transport,
|
|
Source: identity,
|
|
}
|
|
|
|
v := &API{
|
|
client: graphql.NewClient(ApiURIv2, httpClient),
|
|
}
|
|
|
|
return v
|
|
}
|
|
|
|
func (v *API) Vehicles(ctx context.Context) ([]ConsumerCar, error) {
|
|
var res struct {
|
|
GetConsumerCarsV2 []ConsumerCar `graphql:"getConsumerCarsV2"`
|
|
}
|
|
|
|
err := v.client.Query(ctx, &res, nil, graphql.OperationName("getCars"))
|
|
|
|
return res.GetConsumerCarsV2, err
|
|
}
|
|
|
|
func (v *API) CarTelemetry(ctx context.Context, vin string) (CarTelemetryData, error) {
|
|
var res struct {
|
|
CarTelemetryData `graphql:"carTelematicsV2(vins: $vins)"`
|
|
}
|
|
|
|
err := v.client.Query(ctx, &res, map[string]any{
|
|
"vins": []string{vin},
|
|
}, graphql.OperationName("CarTelematicsV2"))
|
|
|
|
// Filter data for the requested VIN
|
|
var filteredData CarTelemetryData
|
|
|
|
// Filter health data
|
|
for _, health := range res.CarTelemetryData.Health {
|
|
if health.VIN == vin {
|
|
filteredData.Health = append(filteredData.Health, health)
|
|
}
|
|
}
|
|
|
|
// Filter battery data
|
|
for _, battery := range res.CarTelemetryData.Battery {
|
|
if battery.VIN == vin {
|
|
filteredData.Battery = append(filteredData.Battery, battery)
|
|
}
|
|
}
|
|
|
|
// Filter odometer data
|
|
for _, odometer := range res.CarTelemetryData.Odometer {
|
|
if odometer.VIN == vin {
|
|
filteredData.Odometer = append(filteredData.Odometer, odometer)
|
|
}
|
|
}
|
|
|
|
return filteredData, err
|
|
}
|