Skip to content

Commit aed9857

Browse files
authored
ENH: Add get_access_token method to clients (#36)
1 parent c3a2c79 commit aed9857

File tree

4 files changed

+87
-6
lines changed

4 files changed

+87
-6
lines changed

msal_requests_auth/auth/base_auth_client.py

Lines changed: 16 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -45,22 +45,33 @@ def __call__(
4545
"""
4646
Adds the token to the authorization header.
4747
"""
48+
token = self.get_access_token()
49+
input_request.headers[
50+
"Authorization"
51+
] = f"{token['token_type']} {token['access_token']}"
52+
return input_request
53+
54+
def get_access_token(self) -> Dict[str, str]:
55+
"""
56+
Retrieves the token dictionary from Azure AD.
57+
58+
Returns
59+
-------
60+
dict
61+
"""
4862
token = self._get_access_token()
4963
if "access_token" not in token:
5064
error = token.get("error")
5165
description = token.get("error_description")
5266
raise AuthenticationError(
5367
f"Unable to get token. Error: {error} (Details: {description})."
5468
)
55-
input_request.headers[
56-
"Authorization"
57-
] = f"{token['token_type']} {token['access_token']}"
58-
return input_request
69+
return token
5970

6071
@abstractmethod
6172
def _get_access_token(self) -> Dict[str, str]:
6273
"""
63-
Retrieves the token dictionary from Azure AD.
74+
Abstract method to return the token dictionary from Azure AD.
6475
6576
Returns
6677
-------

test/test_base_client.py

Whitespace-only changes.

test/test_client_credential.py

Lines changed: 36 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -6,6 +6,42 @@
66
from msal_requests_auth.exceptions import AuthenticationError
77

88

9+
@patch("msal.ConfidentialClientApplication", autospec=True)
10+
@patch(
11+
"msal_requests_auth.auth.client_credential.ClientCredentialAuth._get_access_token"
12+
)
13+
def test_client_credential_auth__get_access_token__error(access_token_mock, cca_mock):
14+
access_token_mock.return_value = {
15+
"error": "BAD REQUEST",
16+
"error_description": "Request to get token was bad.",
17+
}
18+
with pytest.raises(
19+
AuthenticationError,
20+
match=(
21+
r"Unable to get token\. Error: BAD REQUEST "
22+
r"\(Details: Request to get token was bad\.\)\."
23+
),
24+
):
25+
ClientCredentialAuth(client=cca_mock, scopes=["TEST SCOPE"]).get_access_token()
26+
27+
28+
@patch("msal.ConfidentialClientApplication", autospec=True)
29+
@patch(
30+
"msal_requests_auth.auth.client_credential.ClientCredentialAuth._get_access_token"
31+
)
32+
def test_client_credential_auth__get_access_token__valid(access_token_mock, cca_mock):
33+
access_token_mock.return_value = {
34+
"token_type": "Bearer",
35+
"access_token": "TEST TOKEN",
36+
}
37+
assert ClientCredentialAuth(
38+
client=cca_mock, scopes=["TEST SCOPE"]
39+
).get_access_token() == {
40+
"token_type": "Bearer",
41+
"access_token": "TEST TOKEN",
42+
}
43+
44+
945
@patch("msal.ConfidentialClientApplication", autospec=True)
1046
def test_client_credential_auth__no_cache(cca_mock):
1147
cca_mock.acquire_token_silent.return_value = None
Lines changed: 35 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -66,7 +66,7 @@ def test_device_code_auth__headless(pca_mock, headless):
6666
@patch("msal.PublicClientApplication", autospec=True)
6767
@patch("msal_requests_auth.auth.device_code.webbrowser")
6868
@patch("msal_requests_auth.auth.device_code.pyperclip")
69-
def test_device_code_auth__no_accounts__unable_to_get_token(
69+
def test_device_code_auth__no_accounts__unable_to_get_token__call(
7070
pyperclip_patch, webbrowser_patch, pca_mock
7171
):
7272
pca_mock.get_accounts.return_value = None
@@ -102,6 +102,40 @@ def test_device_code_auth__no_accounts__unable_to_get_token(
102102
pyperclip_patch.copy.assert_called_with("TEST CODE")
103103

104104

105+
@patch.dict(os.environ, {}, clear=True)
106+
@patch("msal.PublicClientApplication", autospec=True)
107+
@patch("msal_requests_auth.auth.device_code.DeviceCodeAuth._get_access_token")
108+
def test_device_code_auth__get_access_token__error(access_token_mock, pca_mock):
109+
access_token_mock.return_value = {
110+
"error": "BAD REQUEST",
111+
"error_description": "Request to get token was bad.",
112+
}
113+
with pytest.raises(
114+
AuthenticationError,
115+
match=(
116+
r"Unable to get token\. Error: BAD REQUEST "
117+
r"\(Details: Request to get token was bad\.\)\."
118+
),
119+
):
120+
DeviceCodeAuth(client=pca_mock, scopes=["TEST SCOPE"]).get_access_token()
121+
122+
123+
@patch.dict(os.environ, {}, clear=True)
124+
@patch("msal.PublicClientApplication", autospec=True)
125+
@patch("msal_requests_auth.auth.device_code.DeviceCodeAuth._get_access_token")
126+
def test_device_code_auth__get_access_token__valid(access_token_mock, pca_mock):
127+
access_token_mock.return_value = {
128+
"token_type": "Bearer",
129+
"access_token": "TEST TOKEN",
130+
}
131+
assert DeviceCodeAuth(
132+
client=pca_mock, scopes=["TEST SCOPE"]
133+
).get_access_token() == {
134+
"token_type": "Bearer",
135+
"access_token": "TEST TOKEN",
136+
}
137+
138+
105139
@patch.dict(os.environ, {}, clear=True)
106140
@patch("msal.PublicClientApplication", autospec=True)
107141
@patch("msal_requests_auth.auth.device_code.webbrowser")

0 commit comments

Comments
 (0)