Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Porsche: remove deprecated mobile api #8349

Merged
merged 5 commits into from
Jun 7, 2023
Merged
Show file tree
Hide file tree
Changes from 1 commit
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Prev Previous commit
Next Next commit
Remove mobile api
  • Loading branch information
andig committed Jun 7, 2023
commit 1a9655093d60f672b5294f3a9afef0697cedb883
10 changes: 1 addition & 9 deletions vehicle/porsche.go
Original file line number Diff line number Diff line change
Expand Up @@ -48,16 +48,8 @@ func NewPorscheFromConfig(other map[string]interface{}) (api.Vehicle, error) {
}

api := porsche.NewAPI(log, identity.DefaultSource)
mobile := porsche.NewMobileAPI(log, identity.MobileSource)

cc.VIN, err = ensureVehicle(cc.VIN, func() ([]string, error) {
mobileVehicles, err := mobile.Vehicles()
if err == nil {
return lo.Map(mobileVehicles, func(v porsche.StatusResponseMobile, _ int) string {
return v.VIN
}), err
}

vehicles, err := api.Vehicles()
return lo.Map(vehicles, func(v porsche.Vehicle, _ int) string {
return v.VIN
Expand All @@ -80,7 +72,7 @@ func NewPorscheFromConfig(other map[string]interface{}) (api.Vehicle, error) {
return nil, err
}

provider := porsche.NewProvider(log, api, emobility, mobile, cc.VIN, capabilities.CarModel, cc.Cache)
provider := porsche.NewProvider(log, api, emobility, cc.VIN, capabilities.CarModel, cc.Cache)

v := &Porsche{
embed: &cc.embed,
Expand Down
4 changes: 2 additions & 2 deletions vehicle/porsche/api.go
Original file line number Diff line number Diff line change
Expand Up @@ -48,15 +48,15 @@ func NewAPI(log *util.Logger, identity oauth2.TokenSource) *API {
// Vehicles implements the vehicle list response
func (v *API) Vehicles() ([]Vehicle, error) {
var res []Vehicle
uri := fmt.Sprintf("%s/core/api/v4/de/de_DE/vehicles", ApiURI)
uri := fmt.Sprintf("%s/core/api/v3/de/de_DE/vehicles", ApiURI)
err := v.GetJSON(uri, &res)
return res, err
}

// PairingStatus implements the vehicle pairing status response
func (v *API) PairingStatus(vin string) (VehiclePairingResponse, error) {
var res VehiclePairingResponse
uri := fmt.Sprintf("%s/core/api/v4/de/de_DE/vehicles/%s/pairing", ApiURI, vin)
uri := fmt.Sprintf("%s/core/api/v3/de/de_DE/vehicles/%s/pairing", ApiURI, vin)
err := v.GetJSON(uri, &res)
return res, err
}
Expand Down
38 changes: 5 additions & 33 deletions vehicle/porsche/identity.go
Original file line number Diff line number Diff line change
Expand Up @@ -7,7 +7,6 @@ import (
"net/http"
"net/http/cookiejar"
"net/url"
"strings"

"github.com/evcc-io/evcc/util"
"github.com/evcc-io/evcc/util/oauth"
Expand Down Expand Up @@ -39,21 +38,14 @@ var (
Endpoint: OAuth2Config.Endpoint,
Scopes: []string{"openid"},
}

MobileOAuth2Config = &oauth2.Config{
ClientID: "L20OiZ0kBgWt958NWbuCB8gb970y6V6U",
RedirectURL: "One-Product-App://porsche-id/oauth2redirect",
Endpoint: OAuth2Config.Endpoint,
Scopes: []string{"openid", "magiclink", "mbb"},
}
)

// Identity is the Porsche Identity client
type Identity struct {
*request.Helper
user, password string
defaultToken, emobilityToken, mobileToken *oauth2.Token
DefaultSource, EmobilitySource, MobileSource oauth2.TokenSource
user, password string
defaultToken, emobilityToken *oauth2.Token
DefaultSource, EmobilitySource oauth2.TokenSource
}

// NewIdentity creates Porsche identity
Expand All @@ -73,7 +65,7 @@ func (v *Identity) Login() error {
if err == nil {
v.DefaultSource = oauth.RefreshTokenSource(v.defaultToken, v)
v.EmobilitySource = oauth.RefreshTokenSource(v.emobilityToken, &emobilityAdapter{v})
v.MobileSource = oauth.RefreshTokenSource(v.mobileToken, &mobileAdapter{v})
// v.MobileSource = oauth.RefreshTokenSource(v.mobileToken, &mobileAdapter{v})
}

return err
Expand Down Expand Up @@ -146,10 +138,6 @@ func (v *Identity) RefreshToken(_ *oauth2.Token) (*oauth2.Token, error) {
if token, err = v.fetchToken(EmobilityOAuth2Config); err == nil {
v.emobilityToken = token
}

if token, err = v.fetchToken(MobileOAuth2Config); err == nil {
v.mobileToken = token
}
}

return v.defaultToken, err
Expand Down Expand Up @@ -181,11 +169,7 @@ func (v *Identity) fetchToken(oc *oauth2.Config) (*oauth2.Token, error) {
}
resp.Body.Close()

rawQuery := resp.Request.URL.RawQuery
if location, ok := strings.CutPrefix(resp.Header.Get("Location"), "One-Product-App://porsche-id/oauth2redirect?"); ok {
rawQuery = location
}
query, err := url.ParseQuery(rawQuery)
query, err := url.ParseQuery(resp.Request.URL.RawQuery)
if err != nil {
return nil, err
}
Expand Down Expand Up @@ -219,15 +203,3 @@ func (v *emobilityAdapter) RefreshToken(_ *oauth2.Token) (*oauth2.Token, error)
}
return token, err
}

type mobileAdapter struct {
tr *Identity
}

func (v *mobileAdapter) RefreshToken(_ *oauth2.Token) (*oauth2.Token, error) {
token, err := v.tr.RefreshToken(nil)
if err == nil {
token = v.tr.mobileToken
}
return token, err
}
94 changes: 1 addition & 93 deletions vehicle/porsche/provider.go
Original file line number Diff line number Diff line change
Expand Up @@ -13,12 +13,11 @@ import (
type Provider struct {
statusG func() (StatusResponse, error)
emobilityG func() (EmobilityResponse, error)
mobileG func() (StatusResponseMobile, error)
wakeup func() error
}

// NewProvider creates a vehicle api provider
func NewProvider(log *util.Logger, api *API, emobility *EmobilityAPI, mobile *MobileAPI, vin, carModel string, cache time.Duration) *Provider {
func NewProvider(log *util.Logger, api *API, emobility *EmobilityAPI, vin, carModel string, cache time.Duration) *Provider {
impl := &Provider{
statusG: provider.Cached(func() (StatusResponse, error) {
return api.Status(vin)
Expand All @@ -31,16 +30,11 @@ func NewProvider(log *util.Logger, api *API, emobility *EmobilityAPI, mobile *Mo
return EmobilityResponse{}, errors.New("no car model")
}, cache),

mobileG: provider.Cached(func() (StatusResponseMobile, error) {
return mobile.Status(vin, []string{BATTERY_LEVEL, BATTERY_CHARGING_STATE, CLIMATIZER_STATE, E_RANGE, HEATING_STATE, MILEAGE})
}, cache),

wakeup: func() error {
_, _ = api.Status(vin)
if carModel != "" {
_, _ = emobility.Status(vin, carModel)
}
_, _ = mobile.Status(vin, []string{BATTERY_LEVEL})
return nil
},
}
Expand All @@ -52,17 +46,6 @@ var _ api.Battery = (*Provider)(nil)

// Soc implements the api.Vehicle interface
func (v *Provider) Soc() (float64, error) {
res, err := v.mobileG()
if err == nil {
m, err := res.MeasurementByKey("BATTERY_LEVEL")
if err != nil && err != api.ErrNotAvailable {
return 0, err
}
if err != api.ErrNotAvailable {
return float64(m.Value.Percent), nil
}
}

res3, err := v.emobilityG()
if err == nil && res3.BatteryChargeStatus != nil {
return float64(res3.BatteryChargeStatus.StateOfChargeInPercentage), nil
Expand All @@ -80,17 +63,6 @@ var _ api.VehicleRange = (*Provider)(nil)

// Range implements the api.VehicleRange interface
func (v *Provider) Range() (int64, error) {
res, err := v.mobileG()
if err == nil {
m, err := res.MeasurementByKey("E_RANGE")
if err != nil && err != api.ErrNotAvailable {
return 0, err
}
if err != api.ErrNotAvailable {
return int64(m.Value.Kilometers), nil
}
}

res3, err := v.emobilityG()
if err == nil && res3.BatteryChargeStatus != nil {
return res3.BatteryChargeStatus.RemainingERange.ValueInKilometers, nil
Expand All @@ -108,24 +80,6 @@ var _ api.VehicleFinishTimer = (*Provider)(nil)

// FinishTime implements the api.VehicleFinishTimer interface
func (v *Provider) FinishTime() (time.Time, error) {
res, err := v.mobileG()
if err == nil {
m, err := res.MeasurementByKey("BATTERY_CHARGING_STATE")
if err != nil && err != api.ErrNotAvailable {
return time.Time{}, err
}

if err != api.ErrNotAvailable {
if m.Value.EndsAt == "" {
if m.Value.LastModified != "" {
return time.Parse(time.RFC3339, m.Value.LastModified)
}
return time.Time{}, nil
}
return time.Parse(time.RFC3339, m.Value.EndsAt)
}
}

res2, err := v.emobilityG()
if err == nil {
if res2.BatteryChargeStatus == nil {
Expand All @@ -142,30 +96,6 @@ var _ api.ChargeState = (*Provider)(nil)

// Status implements the api.ChargeState interface
func (v *Provider) Status() (api.ChargeStatus, error) {
res, err := v.mobileG()
if err == nil {
m, err := res.MeasurementByKey("BATTERY_CHARGING_STATE")
if err != nil && err != api.ErrNotAvailable {
return api.StatusNone, err
}

if err != api.ErrNotAvailable {
switch m.Value.Status {
case "FAST_CHARGING", "NOT_PLUGGED", "UNKNOWN":
return api.StatusA, nil
case "CHARGING_COMPLETED", "CHARGING_PAUSED", "READY_TO_CHARGE", "SOC_REACHED",
"INITIALISING", "STANDBY", "SUSPENDED", "PLUGGED_LOCKED", "PLUGGED_NOT_LOCKED":
return api.StatusB, nil
case "CHARGING":
return api.StatusC, nil
case "CHARGING_ERROR":
return api.StatusF, nil
default:
return api.StatusNone, errors.New("mobile - unknown charging status: " + m.Value.Status)
}
}
}

res2, err := v.emobilityG()
if err == nil {
if res2.BatteryChargeStatus == nil {
Expand Down Expand Up @@ -200,17 +130,6 @@ var _ api.VehicleClimater = (*Provider)(nil)

// Climater implements the api.VehicleClimater interface
func (v *Provider) Climater() (bool, error) {
res, err := v.mobileG()
if err == nil {
m, err := res.MeasurementByKey("CLIMATIZER_STATE")
if err != nil && err != api.ErrNotAvailable {
return false, err
}
if err != api.ErrNotAvailable {
return m.Value.IsOn, err
}
}

res2, err := v.emobilityG()
if err == nil {
if res2.BatteryChargeStatus == nil {
Expand All @@ -234,17 +153,6 @@ var _ api.VehicleOdometer = (*Provider)(nil)

// Odometer implements the api.VehicleOdometer interface
func (v *Provider) Odometer() (float64, error) {
res, err := v.mobileG()
if err == nil {
m, err := res.MeasurementByKey("MILEAGE")
if err != nil && err != api.ErrNotAvailable {
return 0, err
}
if err != api.ErrNotAvailable {
return float64(m.Value.Kilometers), nil
}
}

res2, err := v.statusG()
if err == nil {
return res2.Mileage.Value, nil
Expand Down