evcc-io / evcc

Sonne tanken ☀️🚘
https://evcc.io
MIT License
3.6k stars 667 forks source link

OAuth2 Login Fails Due to Missing code Parameter in Polestar API - Requires Additional Consent Handling #17186

Open rostbeule opened 2 days ago

rostbeule commented 2 days ago

Describe the bug

The OAuth2 login process with the Polestar API is failing because the code parameter is not returned after the initial authentication request. This issue occurs due to a required user interaction step, specifically the rejection of cookies, which prevents the automatic retrieval of the code parameter. It should be safe to automate this step, as it simply involves rejecting cookies.

Steps to Reproduce

  1. Start the OAuth2 login process with the Polestar API.
  2. After entering credentials, note that the code parameter is not returned, as user consent for terms and conditions is still pending.
  3. Only a uid parameter is available at this stage.

Expected Behavior

The OAuth2 login process should automatically handle any additional consent requirements from the Polestar API, enabling the retrieval of the code parameter without extra user interaction.

Proposed Solution

  1. Implement a check to detect when the code parameter is missing but a uid parameter is present.
  2. In such cases, send a POST request to submit the user's consent for rejecting cookies.
  3. After successful rejection, the process should retrieve the code parameter as expected.

Additional Context

This adjustment will allow the OAuth2 login to handle user consent programmatically within the Polestar API, streamlining the process by removing any manual acceptance step.

Acceptance Criteria

Configuration details

vehicles:
  - name: my_car
    type: template
    template: polestar
    title: "Polestar 2"
    user: me@something.com
    password: ********
    vin: LPSVS************
    capacity: 78

Log details

[main] ERROR 2024/11/11 08:20:58 - Vehicle creation failed for 'my_car':
  - Cannot create vehicle type 'template':
      - Cannot create vehicle type 'polestar':
          - Login failed: code not found

What type of operating system are you running?

Docker container

Nightly build

Version

No response

rostbeule commented 2 days ago

see also: https://github.com/evcc-io/evcc/issues/17118

andig commented 2 days ago

Giving consent is up to the user, not up to evcc.

kptkip commented 2 days ago

Consent in the WEB-UI of Polestar already given. How to do this via evcc?! Really necessary?

BTW: works in my Home-Assistant implementation like a charm, but not in evcc

loebse commented 2 days ago

This is exactly the problem @kptkip: it is not possible, the website consent has no impact on the API access. If the EVCC Polestar implementation stays as is, it cannot work. But you also never know what Polestar is changing tomorrow 😉

The HA Integration team implemented the consent via API already, this is why it is working again.

andig commented 2 days ago

the website consent has no impact on the API access

Since the API is reverse-engineered: who's the regular consumer? The Polestar app? Does that allow giving consent?

loebse commented 2 days ago

No, the app does not allow to give consent. I am assuming it is using another API.

The API we are using here is used by the https://www.polestar.com/ website. Here you can see the SOC etc. as well and you are forced to give consent before you can see the data:

image

The HA integration is making the consent via an API call to make the integration work again.

This is all valid for today. Polestar is known for making sudden changes without any communication. Which is understandable as this is not a public / documented API.

kptkip commented 2 days ago

The HA integration is making the consent via an API call to make the integration work again.

Why not using the same approach like the HA integration?

rostbeule commented 2 days ago

Okay, long story short: I took a look at what actually needs to be accepted. It's just cookies, and nothing is stopping us from rejecting them.

So you can also send:

var confirmData = new Dictionary<string, string>
{
    { "pf.submit", "false" },
    { "subject", uid }
};
var content = new FormUrlEncodedContent(confirmData);
var response = await client.PostAsync($"{OAuthURI}/as/{resumePath}/resume/as/authorization.ping", content);

this should do the trick for now.

[Edit] Pardon me, as said, I'm more into c#

data := url.Values{
    "pf.submit": []string{"false"},
    "subject":   []string{uid},
}
rostbeule commented 2 days ago

@andig, I understand your concern. I hope my proposed solution is acceptable. I've adjusted the issue text accordingly. Unfortunately, I am unable to provide further assistance at this time and would appreciate it if either you or someone else could implement it. Personally, I lack the necessary Go skills, and it would take me quite a while to implement it myself.

jahoooo commented 2 days ago

evcc v0.131.5 as home assistant add-on doesn't solve the issue for me neither. Guess the suggested approach from rostbeule is needed. I get the same error [main ] ERROR 2024/11/12 01:31:34 creating vehicle Polestar_2 failed: cannot create vehicle type 'template': cannot create vehicle type 'polestar': login failed: code not found

Pypolestar in home assistant does display the SOC for me, though. I hoped if it the consent was already given by pypolestar inside home assistant, it would work without consent then for evcc. But looks like this is handled independently and evcc has to do this credentials hack itself. Oh my god Polestar... What have you done...

andig commented 1 day ago

The API we are using here is used by the https://www.polestar.com/ website

Apparently there is a difference regarding consent. Anyway, happy to take a PR.

noottzz commented 1 day ago

Not sure the failure message i get when I try to configure my polestar interface results from this problem but at least in the last days I have login problems too: cannot create vehicle type 'template': cannot create vehicle type 'polestar': login failed: code not found

rostbeule commented 5 hours ago

@andig here you go https://github.com/evcc-io/evcc/pull/17252