Seat: fix retrieving list of vehicles (#9703)
This commit is contained in:
parent
cec3de4770
commit
a42affd827
5 changed files with 130 additions and 16 deletions
|
|
@ -8,7 +8,6 @@ import (
|
|||
"github.com/evcc-io/evcc/api"
|
||||
"github.com/evcc-io/evcc/util"
|
||||
"github.com/evcc-io/evcc/util/request"
|
||||
"github.com/evcc-io/evcc/vehicle/seat"
|
||||
"github.com/evcc-io/evcc/vehicle/seat/cupra"
|
||||
"github.com/evcc-io/evcc/vehicle/vag/service"
|
||||
"github.com/evcc-io/evcc/vehicle/vag/vwidentity"
|
||||
|
|
@ -51,7 +50,7 @@ func NewCupraFromConfig(other map[string]interface{}) (api.Vehicle, error) {
|
|||
|
||||
log := util.NewLogger("cupra").Redact(cc.User, cc.Password, cc.VIN)
|
||||
|
||||
ts, err := service.TokenRefreshServiceTokenSource(log, seat.TRSParams, seat.AuthParams, cc.User, cc.Password)
|
||||
ts, err := service.TokenRefreshServiceTokenSource(log, cupra.TRSParams, cupra.AuthParams, cc.User, cc.Password)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
|
|
|||
|
|
@ -1,14 +1,22 @@
|
|||
package vehicle
|
||||
|
||||
import (
|
||||
"context"
|
||||
"fmt"
|
||||
"net/http"
|
||||
"net/url"
|
||||
"strings"
|
||||
"time"
|
||||
|
||||
"github.com/evcc-io/evcc/api"
|
||||
"github.com/evcc-io/evcc/util"
|
||||
"github.com/evcc-io/evcc/util/request"
|
||||
"github.com/evcc-io/evcc/vehicle/seat"
|
||||
"github.com/evcc-io/evcc/vehicle/seat/cupra"
|
||||
"github.com/evcc-io/evcc/vehicle/vag/service"
|
||||
"github.com/evcc-io/evcc/vehicle/vag/vwidentity"
|
||||
"github.com/evcc-io/evcc/vehicle/vw"
|
||||
"golang.org/x/oauth2"
|
||||
)
|
||||
|
||||
// https://github.com/trocotronic/weconnect
|
||||
|
|
@ -50,18 +58,36 @@ func NewSeatFromConfig(other map[string]interface{}) (api.Vehicle, error) {
|
|||
|
||||
log := util.NewLogger("seat").Redact(cc.User, cc.Password, cc.VIN)
|
||||
|
||||
trs, err := service.TokenRefreshServiceTokenSource(log, seat.TRSParams, seat.AuthParams, cc.User, cc.Password)
|
||||
trs, err := service.TokenRefreshServiceTokenSource(log, cupra.TRSParams, cupra.AuthParams, cc.User, cc.Password)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
ts := service.MbbTokenSource(log, trs, seat.AuthClientID)
|
||||
api := vw.NewAPI(log, ts, seat.Brand, seat.Country)
|
||||
api.Client.Timeout = cc.Timeout
|
||||
// get OIDC user information
|
||||
ctx := context.WithValue(context.Background(), oauth2.HTTPClient, request.NewClient(log))
|
||||
ui, err := vwidentity.Config.NewProvider(ctx).UserInfo(ctx, trs)
|
||||
if err != nil {
|
||||
return nil, fmt.Errorf("failed getting user information: %w", err)
|
||||
}
|
||||
|
||||
cc.VIN, err = ensureVehicle(cc.VIN, api.Vehicles)
|
||||
mbbId, err := mbbUserId(log, trs, ui.Subject)
|
||||
if err != nil {
|
||||
return nil, fmt.Errorf("failed getting mbbUserId: %w", err)
|
||||
}
|
||||
|
||||
ts := service.MbbTokenSource(log, trs, seat.AuthClientID)
|
||||
api := seat.NewAPI(log, ts)
|
||||
|
||||
cc.VIN, err = ensureVehicle(
|
||||
cc.VIN, func() ([]string, error) {
|
||||
return api.Vehicles(mbbId)
|
||||
},
|
||||
)
|
||||
|
||||
if err == nil {
|
||||
api := vw.NewAPI(log, ts, seat.Brand, seat.Country)
|
||||
api.Client.Timeout = cc.Timeout
|
||||
|
||||
if err = api.HomeRegion(cc.VIN); err == nil {
|
||||
v.Provider = vw.NewProvider(api, cc.VIN, cc.Cache)
|
||||
}
|
||||
|
|
@ -69,3 +95,28 @@ func NewSeatFromConfig(other map[string]interface{}) (api.Vehicle, error) {
|
|||
|
||||
return v, err
|
||||
}
|
||||
|
||||
func mbbUserId(log *util.Logger, ts oauth2.TokenSource, uid string) (string, error) {
|
||||
client := request.NewHelper(log)
|
||||
client.Transport = &oauth2.Transport{
|
||||
Source: ts,
|
||||
Base: client.Transport,
|
||||
}
|
||||
|
||||
data := url.Values{
|
||||
"scopeId": []string{"commonMandatoryFields"},
|
||||
}
|
||||
|
||||
var mandatoryConsentInfo struct {
|
||||
MbbUserId string `json:"mbbUserId"`
|
||||
}
|
||||
|
||||
uri := fmt.Sprintf("https://profileintegrityservice.apps.emea.vwapps.io/iaa/pic/v1/users/%s/check-profile", uid)
|
||||
req, err := request.New(http.MethodPost, uri, strings.NewReader(data.Encode()), request.URLEncoding)
|
||||
|
||||
if err == nil {
|
||||
err = client.DoJSON(req, &mandatoryConsentInfo)
|
||||
}
|
||||
|
||||
return mandatoryConsentInfo.MbbUserId, err
|
||||
}
|
||||
|
|
|
|||
53
vehicle/seat/api.go
Normal file
53
vehicle/seat/api.go
Normal file
|
|
@ -0,0 +1,53 @@
|
|||
package seat
|
||||
|
||||
import (
|
||||
"fmt"
|
||||
|
||||
"github.com/evcc-io/evcc/util"
|
||||
"github.com/evcc-io/evcc/util/request"
|
||||
"golang.org/x/oauth2"
|
||||
)
|
||||
|
||||
// BaseURL is the API base url
|
||||
const BaseURL = "https://mal-3a.prd.eu.dp.vwg-connect.com/api"
|
||||
|
||||
// API provides list of vehicles for Seat cars
|
||||
type API struct {
|
||||
*request.Helper
|
||||
}
|
||||
|
||||
// NewAPI creates a new vehicle
|
||||
func NewAPI(log *util.Logger, ts oauth2.TokenSource) *API {
|
||||
v := &API{
|
||||
Helper: request.NewHelper(log),
|
||||
}
|
||||
|
||||
v.Client.Transport = &oauth2.Transport{
|
||||
Source: ts,
|
||||
Base: v.Client.Transport,
|
||||
}
|
||||
|
||||
return v
|
||||
}
|
||||
|
||||
// Vehicles implements the /vehicles response
|
||||
func (v *API) Vehicles(userID string) ([]string, error) {
|
||||
var res struct {
|
||||
UserVehicles struct {
|
||||
UserId string
|
||||
Vehicle []struct {
|
||||
Content string
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
uri := fmt.Sprintf("%s/usermanagement/users/v2/users/%s/vehicles", BaseURL, userID)
|
||||
err := v.GetJSON(uri, &res)
|
||||
|
||||
var vehicles []string
|
||||
for _, v := range res.UserVehicles.Vehicle {
|
||||
vehicles = append(vehicles, v.Content)
|
||||
}
|
||||
|
||||
return vehicles, err
|
||||
}
|
||||
16
vehicle/seat/cupra/params.go
Normal file
16
vehicle/seat/cupra/params.go
Normal file
|
|
@ -0,0 +1,16 @@
|
|||
package cupra
|
||||
|
||||
import "net/url"
|
||||
|
||||
// Authorization parameters
|
||||
var AuthParams = url.Values{
|
||||
"response_type": {"code id_token"}, // token
|
||||
"client_id": {"30e33736-c537-4c72-ab60-74a7b92cfe83@apps_vw-dilab_com"},
|
||||
"redirect_uri": {"cupraconnect://identity-kit/login"},
|
||||
"scope": {"openid profile mbb"}, // cars birthdate nickname address phone
|
||||
}
|
||||
|
||||
// TokenRefreshService parameters
|
||||
var TRSParams = url.Values{
|
||||
"brand": {"cupra"},
|
||||
}
|
||||
|
|
@ -7,18 +7,13 @@ const (
|
|||
Country = "ES"
|
||||
|
||||
// Authorization ClientID
|
||||
AuthClientID = "9d183b70-d129-424f-9a26-c3778edf95e1"
|
||||
AuthClientID = "9dcc70f0-8e79-423a-a3fa-4065d99088b4"
|
||||
)
|
||||
|
||||
// Authorization parameters
|
||||
var AuthParams = url.Values{
|
||||
"response_type": {"code id_token"}, // token
|
||||
"client_id": {"30e33736-c537-4c72-ab60-74a7b92cfe83@apps_vw-dilab_com"},
|
||||
"redirect_uri": {"cupraconnect://identity-kit/login"},
|
||||
"scope": {"openid profile mbb"}, // cars birthdate nickname address phone
|
||||
}
|
||||
|
||||
// TokenRefreshService parameters
|
||||
var TRSParams = url.Values{
|
||||
"brand": {"cupra"},
|
||||
"client_id": {"3c8e98bc-3ae9-4277-a563-d5ee65ddebba@apps_vw-dilab_com"},
|
||||
"redirect_uri": {"seatconnect://identity-kit/login"},
|
||||
"scope": {"openid profile"}, // address phone email birthdate nationalIdentifier cars mbb dealers badge nationality
|
||||
}
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue