Skip to content

Commit 22b1863

Browse files
committed
Add logging
1 parent 6576cd0 commit 22b1863

File tree

12 files changed

+377
-132
lines changed

12 files changed

+377
-132
lines changed

requirements-build.txt

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -486,6 +486,7 @@ django==5.2.8 \
486486
# django-crum
487487
# django-filter
488488
# django-generate-series
489+
# django-guid
489490
# django-solo
490491
# django-weasyprint
491492
# djangorestframework
@@ -509,6 +510,10 @@ django-generate-series==0.5.0 \
509510
--hash=sha256:54e33e5aba69be75f591bda970421dee9f1c5feeb84c20d8cee634bcc0e249bc \
510511
--hash=sha256:8cced6473ba75aed5e1e2ecd6f5426d11d33926e86d2630dabe9c424b7a6da8a
511512
# via -r requirements-pinned.txt
513+
django-guid==3.5.2 \
514+
--hash=sha256:0f812a837579031c7db8524b07e498f65b5fcf191857c1f7fb5414a0ceb584fa \
515+
--hash=sha256:cadbc929bfa2b19c6f9e847da3e095ebebe1124adef92f0af317f963ee51a6cb
516+
# via -r requirements-pinned.txt
512517
django-solo==2.4.0 \
513518
--hash=sha256:62e9c7d929620a61848515839833750ca142840051595cf5c8e617dcefc9e5cf \
514519
--hash=sha256:ec92dc00aec75034a3f93b3a85152e57c4b03d7987f8cfd0ea8a47cc6e3c2084
@@ -676,6 +681,7 @@ packaging==25.0 \
676681
--hash=sha256:d443872c98d677bf60f6a1f2f8c1cb748e8fe762d2bf9d3148b5599295b0fc4f
677682
# via
678683
# ansible-runner
684+
# django-guid
679685
# pytest
680686
pexpect==4.9.0 \
681687
--hash=sha256:7236d1e080e4936be2dc3e326cec0af72acf9212a7e1d060210e70a47e253523 \

requirements-pinned.txt

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -8,6 +8,7 @@ django-ansible-base==2025.10.20
88
django-cors-headers==4.9.0
99
django-filter==25.2
1010
django-generate-series==0.5.0
11+
django-guid==3.5.2
1112
django-solo==2.4.0
1213
django-weasyprint==2.4.0
1314
djangorestframework==3.16.1

requirements.txt

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -8,6 +8,7 @@ django-ansible-base==2025.10.20
88
django-cors-headers==4.9.0
99
django-filter==25.2
1010
django-generate-series==0.5.0
11+
django-guid==3.5.2
1112
django-solo==2.4.0
1213
django-weasyprint==2.4.0
1314
djangorestframework==3.16.1

src/backend/apps/aap_auth/aap_auth.py

Lines changed: 42 additions & 19 deletions
Original file line numberDiff line numberDiff line change
@@ -13,7 +13,7 @@
1313
from backend.apps.users.models import User
1414
from backend.apps.users.schemas import UserResponseSchema
1515

16-
logger = logging.getLogger("automation-dashboard")
16+
logger = logging.getLogger("automation-dashboard.aap_auth")
1717

1818

1919
def memoize(func):
@@ -35,8 +35,9 @@ class AAPAuth:
3535
# Handles AAP authentication and user management
3636

3737
def __init__(self):
38-
# Initialize authentication settings from config
38+
logger.info("Initializing AAPAuth")
3939
auth_settings = AAPAuthSettings(**settings.AAP_AUTH_PROVIDER)
40+
logger.debug(f"Auth settings: {auth_settings}")
4041
setting_url = auth_settings.url[:-1] if auth_settings.url.endswith('/') else auth_settings.url
4142

4243
self.name = auth_settings.name
@@ -50,59 +51,65 @@ def __init__(self):
5051
self.user_data_uri = user_data_uri
5152
self.check_ssl = auth_settings.check_ssl
5253

54+
logger.info("Fetching OAuth endpoints")
5355
o_endpoints = self.get_o_endpoints()
56+
logger.debug(f"OAuth endpoints: {o_endpoints}")
5457

5558
self.authorize_uri = o_endpoints["authorize_uri"]
5659
self.token_uri = o_endpoints["token_uri"]
5760
self.revoke_token_uri = o_endpoints["revoke_token_uri"]
5861

59-
# Optionally suppress urllib3 SSL warnings
6062
if not settings.SHOW_URLLIB3_INSECURE_REQUEST_WARNING:
6163
urllib3.disable_warnings(urllib3.exceptions.InsecureRequestWarning)
62-
64+
logger.info("AAPAuth initialized successfully")
6365

6466
def ping(self, url: str) -> Response:
65-
logger.info(f"Try to obtain OAuth endpoint {url}")
67+
logger.info(f"Trying to obtain OAuth endpoint: {url}")
6668
try:
6769
response = requests.get(
6870
url=url,
6971
verify=self.check_ssl,
7072
allow_redirects=False,
7173
timeout=3)
74+
logger.debug(f"Ping response status: {response.status_code}")
7275
except requests.exceptions.HTTPError as e:
73-
logger.error(f'GET request {url} failed with exception {e}')
76+
logger.error(f'GET request {url} failed: {e}')
7477
raise AuthenticationFailed(f"Failed request to {url}")
7578
if response.ok:
76-
logger.info(f"Successfully obtained OAuth endpoint {url}")
79+
logger.info(f"Successfully obtained OAuth endpoint: {url}")
7780
return response
7881

79-
# Cache the OAuth endpoints to avoid pinging the server on every call
8082
@memoize
8183
def get_o_endpoints(self):
84+
logger.info("Getting OAuth endpoints")
8285
url = f"{self.url}/o/"
8386
response = self.ping(url)
87+
logger.debug(f"First endpoint response: {response.ok}")
8488
if response.ok:
8589
result = {
8690
'authorize_uri': '/o/authorize/',
8791
'token_uri': '/o/token/',
8892
'revoke_token_uri': '/o/revoke_token/'
8993
}
94+
logger.info("OAuth endpoints found at /o/")
9095
return result
9196

9297
url = f"{self.url}/api/o/"
9398
response = self.ping(url)
99+
logger.debug(f"Second endpoint response: {response.ok}")
94100
if response.ok:
95101
result = {
96102
'authorize_uri': '/api/o/authorize/',
97103
'token_uri': '/api/o/token/',
98104
'revoke_token_uri': '/api/o/revoke_token/'
99105
}
106+
logger.info("OAuth endpoints found at /api/o/")
100107
return result
101108
logger.error("Failed to obtain OAuth endpoints after multiple attempts.")
102109
raise AuthenticationFailed("Authorization failed: Unable to find a valid OAuth endpoint.")
103110

104111
def ui_data(self) -> dict[str, str]:
105-
# Returns data needed for UI authorization flow
112+
logger.debug("Preparing UI data for authorization flow")
106113
return {
107114
'name': self.name,
108115
'url': f'{self.url}{self.authorize_uri}',
@@ -113,28 +120,33 @@ def ui_data(self) -> dict[str, str]:
113120
}
114121

115122
def _aap_authorize(self, params: dict[str, str]) -> AAPToken:
116-
# Requests an AAP token using provided parameters
123+
logger.info("Requesting AAP token")
124+
logger.debug(f"Token request params: {params}")
117125
response = requests.post(
118126
url=f"{self.url}{self.token_uri}",
119127
data=params,
120128
verify=self.check_ssl,
121129
allow_redirects=False,
122130
timeout=30,
123131
)
132+
logger.debug(f"AAP token response status: {response.status_code}")
124133
if not response.ok:
125-
logger.error("An error occurred obtaining AAP token. %s", response.content)
134+
logger.error("Error obtaining AAP token: %s", response.content)
126135
raise AuthenticationFailed("Obtaining of AAP token failed. An error occurred connecting to AAP authorization server.")
127136

128137
token_result = response.json()
138+
logger.debug(f"Token result: {token_result}")
129139
access_token = token_result.get("access_token", None)
130140
refresh_token = token_result.get("refresh_token", None)
131141

132142
if access_token is None or refresh_token is None:
143+
logger.error("Invalid token response from AAP")
133144
raise AuthenticationFailed("Obtaining of AAP token failed. Invalid response from AAP.")
134145
return AAPToken(**token_result)
135146

136147
def authorize(self, code: str, redirect_uri: str) -> dict[str, JwtUserToken | JwtUserRefreshToken]:
137-
# Exchanges authorization code for tokens and user info
148+
logger.info("Authorizing user")
149+
logger.debug(f"Authorization code: {code}, redirect_uri: {redirect_uri}")
138150
token_params = {
139151
"client_id": self.client_id,
140152
"client_secret": self.client_secret,
@@ -145,10 +157,12 @@ def authorize(self, code: str, redirect_uri: str) -> dict[str, JwtUserToken | Jw
145157
aap_token = self._aap_authorize(token_params)
146158
user = self.get_user_data(aap_token)
147159
jwt_token = JWTToken()
160+
logger.info("User authorized successfully")
148161
return jwt_token.acquire_token_pair(aap_token=aap_token, user=user)
149162

150163
def get_user_data(self, aap_token: AAPToken) -> User:
151-
# Fetches user data from AAP using the access token
164+
logger.info("Fetching user data from AAP")
165+
logger.debug(f"Access token: {aap_token.access_token}")
152166
headers = {
153167
'Authorization': f'{aap_token.token_type} {aap_token.access_token}',
154168
'Content-Type': 'application/json',
@@ -163,26 +177,31 @@ def get_user_data(self, aap_token: AAPToken) -> User:
163177
timeout=30,
164178
headers=headers
165179
)
180+
logger.debug(f"User data response status: {user_response.status_code}")
166181
user_response.raise_for_status()
167182
except requests.exceptions.HTTPError as e:
168-
logger.error("An error occurred obtaining AAP user. %s", e.response.content)
183+
logger.error("Error obtaining AAP user: %s", e.response.content)
169184
raise AuthenticationFailed("An error occurred obtaining AAP user.")
170185
except requests.exceptions.RequestException as e:
171186
logger.error(f"Failed to validate token with AAP: {str(e)}")
172187
raise ValueError("Failed to validate token with AAP")
173188

174189
users = UserResponseSchema(**user_response.json())
190+
logger.debug(f"User response schema: {users}")
175191
if users.count != 1:
176-
logger.error(f"Failed to retrieve AAP user. {str(users)}")
192+
logger.error(f"Failed to retrieve AAP user: {str(users)}")
177193
raise ValueError("Failed to retrieve AAP user.")
194+
logger.info("User data fetched successfully")
178195
return User.create_or_update_aap_user(users.results[0])
179196

180197
def refresh_token(self, refresh_token: str) -> dict[str, JwtUserToken | JwtUserRefreshToken]:
181-
# Refreshes JWT tokens using the AAP refresh token
198+
logger.info("Refreshing JWT token")
199+
logger.debug(f"Refresh token: {refresh_token}")
182200
jwt_token = JWTToken()
183201
refresh_token = jwt_token.decode_refresh_token(token=refresh_token)
184202

185203
if refresh_token is None:
204+
logger.error("Refresh token is invalid")
186205
raise NotAuthenticated("Refresh token is invalid.")
187206

188207
token_params = {
@@ -195,17 +214,19 @@ def refresh_token(self, refresh_token: str) -> dict[str, JwtUserToken | JwtUserR
195214
user = self.get_user_data(aap_token)
196215

197216
refresh_token.revoke_token()
198-
217+
logger.info("JWT token refreshed successfully")
199218
return jwt_token.acquire_token_pair(aap_token=aap_token, user=user)
200219

201220
def logout(self, access_token: str) -> dict[str, any]:
202-
# Revokes the AAP token and logs out the user
221+
logger.info("Logging out user")
222+
logger.debug(f"Access token: {access_token}")
203223
token = JwtUserToken.get_user_token(access_token)
204224
result = {
205225
"success": True,
206226
"message": "",
207227
}
208228
if token is None or token.id is None:
229+
logger.error("Invalid token for logout")
209230
raise AuthenticationFailed("Invalid token.")
210231

211232
token_params = {
@@ -221,14 +242,16 @@ def logout(self, access_token: str) -> dict[str, any]:
221242
allow_redirects=False,
222243
timeout=30,
223244
)
245+
logger.debug(f"Logout response status: {response.status_code}")
224246

225247
if not response.ok:
226-
logger.error("An error occurred revoking AAP token. %s", response.content)
248+
logger.error("Error revoking AAP token: %s", response.content)
227249
result["success"] = False
228250
result["message"] = response.content
229251
result["status_code"] = response.status_code
230252
return result
231253

232254
token.revoke_token()
255+
logger.info("User logged out successfully")
233256
result["success"] = True
234257
return result

src/backend/apps/aap_auth/authentication.py

Lines changed: 13 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -7,42 +7,52 @@
77

88
from backend.apps.aap_auth.jwt_token import JWTToken
99

10-
logger = logging.getLogger("automation-dashboard")
10+
logger = logging.getLogger("automation-dashboard.auth")
1111

1212

1313
def enforce_csrf(request):
1414
"""
1515
Enforce CSRF validation.
1616
"""
17+
logger.info("Starting CSRF validation.")
1718
check = CSRFCheck(request)
1819
check.process_request(request)
1920
reason = check.process_view(request, None, (), {})
2021
if reason:
22+
logger.error('CSRF Failed: %s' % reason)
2123
raise exceptions.PermissionDenied('CSRF Failed: %s' % reason)
2224

2325

2426
class AAPAuthentication(BaseAuthentication):
2527
def authenticate(self, request: Request):
28+
logger.info("Starting authentication process")
2629
token = request.COOKIES.get(settings.AUTH_COOKIE_ACCESS_TOKEN_NAME) or None
30+
logger.debug(f"Token from cookies: {token}")
2731

2832
if token is None:
33+
logger.info("No token found in cookies")
2934
return None
3035

31-
if len(token) < 10: # Basic length check
36+
if len(token) < 10:
37+
logger.warning("Token length is too short")
3238
return None
3339

40+
logger.debug("Attempting to decode token")
3441
jwt_token = JWTToken()
3542
db_token = jwt_token.decode_token(token)
3643

3744
if db_token is None:
45+
logger.warning("Failed to decode token")
3846
return None
3947

4048
if not db_token.user.is_active:
49+
logger.warning("User is not active")
4150
return None
4251

4352
enforce_csrf(request)
44-
53+
logger.info("Authentication successful")
4554
return db_token.user, token
4655

4756
def authenticate_header(self, request: Request) -> str:
57+
logger.debug("Returning authentication header")
4858
return "Bearer"

0 commit comments

Comments
 (0)