Skip to content

Commit

Permalink
fix: fix mfa code handling
Browse files Browse the repository at this point in the history
  • Loading branch information
alandtse committed Mar 2, 2021
1 parent 31b56cc commit e005fcf
Show file tree
Hide file tree
Showing 2 changed files with 15 additions and 5 deletions.
9 changes: 6 additions & 3 deletions teslajsonpy/connection.py
Original file line number Diff line number Diff line change
Expand Up @@ -75,6 +75,7 @@ def __init__(
self.__sethead(access_token=self.access_token, expiration=self.expiration)
_LOGGER.debug("Connecting with existing access token")
self.websocket = None
self.mfa_code: Text = ""

async def get(self, command):
"""Get data from API."""
Expand All @@ -101,7 +102,7 @@ async def post(self, command, method="post", data=None):
if self.email and self.password:
_LOGGER.debug("Getting sso auth code using credentials")
self.code = await self.get_authorization_code(
self.email, self.password
self.email, self.password, mfa_code=self.mfa_code
)
else:
_LOGGER.debug("Using existing authorization code")
Expand Down Expand Up @@ -396,6 +397,7 @@ async def get_authorization_code(
if not resp.history:
html = await resp.text()
if "/mfa/verify" in html:
_LOGGER.debug("Detected MFA request")
mfa_resp = await self.websession.get(
"https://auth.tesla.com/oauth2/v3/authorize/mfa/factors",
params={"transaction_id": transaction_id},
Expand All @@ -416,7 +418,7 @@ async def get_authorization_code(
# ]
# }
mfa_json = await mfa_resp.json()
if len(mfa_json.get("data", [])) > 1:
if len(mfa_json.get("data", [])) >= 1:
factor_id = mfa_json["data"][mfa_device]["id"]
if not mfa_code:
_LOGGER.debug("No MFA provided")
Expand Down Expand Up @@ -445,10 +447,11 @@ async def get_authorization_code(
resp = await self.websession.post(url, data=data)
_process_resp(resp)
await asyncio.sleep(3)
if not (resp.history):
if not resp.history or not URL(resp.history[-1].url).query.get("code"):
_LOGGER.debug("Failed to authenticate")
raise IncompleteCredentials("Unable to login with credentials")
code_url = URL(resp.history[-1].url)
_LOGGER.debug("Found code %s", code_url.query.get("code"))
return code_url.query.get("code")

def get_authorization_code_link(self, new=False) -> yarl.URL:
Expand Down
11 changes: 9 additions & 2 deletions teslajsonpy/controller.py
Original file line number Diff line number Diff line change
Expand Up @@ -10,7 +10,7 @@
import asyncio
import logging
import time
from typing import Callable, Dict, Optional, Text
from typing import Callable, Dict, List, Optional, Text

from aiohttp import ClientConnectorError
import backoff
Expand Down Expand Up @@ -260,20 +260,27 @@ def __init__(
self.enable_websocket = enable_websocket

async def connect(
self, test_login=False, wake_if_asleep=False, filtered_vins=None
self,
test_login: bool = False,
wake_if_asleep: bool = False,
filtered_vins: Optional[List[Text]] = None,
mfa_code: Text = "",
) -> Dict[Text, Text]:
"""Connect controller to Tesla.
Args
test_login (bool, optional): Whether to test credentials only. Defaults to False.
wake_if_asleep (bool, optional): Whether to wake up any sleeping cars to update state. Defaults to False.
filtered_vins (list, optional): If not empty, filters the cars by the provided VINs.
mfa_code (Text, optional): MFA code to use for connection
Returns
Dict[Text, Text]: Returns the refresh_token, access_token, and expires_in time
"""

if mfa_code:
self.__connection.mfa_code = mfa_code
cars = await self.get_vehicles()
self._last_attempted_update_time = time.time()
self.__update_lock = asyncio.Lock()
Expand Down

0 comments on commit e005fcf

Please sign in to comment.