Skip to content
This repository has been archived by the owner on Oct 3, 2023. It is now read-only.

feat: SPORT-200 better user to partner auth management #150

Open
wants to merge 2 commits into
base: hub-decathlon
Choose a base branch
from
Open
Show file tree
Hide file tree
Changes from all commits
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
34 changes: 19 additions & 15 deletions tapiriik/services/Fitbit/fitbit.py
Original file line number Diff line number Diff line change
Expand Up @@ -306,25 +306,29 @@ def _requestWithAuth(self, reqLambda, serviceRecord):
})

if response.status_code != 200:
raise APIException("No authorization to refresh token", block=True,
user_exception=UserException(UserExceptionType.Authorization,
intervention_required=True))
if response.status_code == 401 or response.status_code == 403:
raise APIException("%i - No authorization to refresh token for the user with FITBIT ID : %s" %(response.status_code, serviceRecord.ExternalID), block=True,
user_exception=UserException(UserExceptionType.Authorization,
intervention_required=True))
else:
raise APIException("%i - Can't refresh token (for an undefined reason) for the user with FITBIT ID : %s" %(response.status_code, serviceRecord.ExternalID))
else:

data = response.json()
data = response.json()

now = datetime.now(timezone.utc)
endDate = now + timedelta(seconds=data['expires_in'])
now = datetime.now(timezone.utc)
endDate = now + timedelta(seconds=data['expires_in'])

authorizationData = {
"AccessToken": data["access_token"],
"AccessTokenRequestedAt": now,
"AccessTokenExpiresAt": endDate,
"RefreshToken": data["refresh_token"],
'TokenType': data['token_type']
}
authorizationData = {
"AccessToken": data["access_token"],
"AccessTokenRequestedAt": now,
"AccessTokenExpiresAt": endDate,
"RefreshToken": data["refresh_token"],
'TokenType': data['token_type']
}

serviceRecord.Authorization.update(authorizationData)
db.connections.update({"_id": serviceRecord._id}, {"$set": {"Authorization": authorizationData}})
serviceRecord.Authorization.update(authorizationData)
db.connections.update({"_id": serviceRecord._id}, {"$set": {"Authorization": authorizationData}})

#session.headers.update({"Authorization": "access_token %s" % serviceRecord.Authorization["AccessToken"]})
return reqLambda(session)
Expand Down
6 changes: 6 additions & 0 deletions tapiriik/services/service_record.py
Original file line number Diff line number Diff line change
Expand Up @@ -40,6 +40,12 @@ def HasExtendedAuthorizationDetails(self, persisted_only=False):
return False
return cachedb.extendedAuthDetails.find({"ID": self._id}).limit(1).count()

def HasAuthSyncError(self):
if hasattr(self, "SyncErrors"):
return next((se for se in self.SyncErrors if se["UserException"]["InterventionRequired"] and se["Block"] and se["UserException"]["Type"] == "auth"), False) is not False
else:
return False

def SetPartialSyncTriggerSubscriptionState(self, subscribed):
db.connections.update_one({"_id": self._id}, {"$set": {"PartialSyncTriggerSubscribed": subscribed}})

Expand Down
22 changes: 20 additions & 2 deletions tapiriik/web/views/api/providers.py
Original file line number Diff line number Diff line change
Expand Up @@ -7,8 +7,26 @@
@ensure_csrf_cookie
def providers(req):
if req.user != None:
user_connections = [conns.get("Service") for conns in req.user.get("ConnectedServices")]
active_providers = [{"id": x.ID, "displayName": x.DisplayName, "isReceiver": x.ReceivesActivities, "isSupplier": x.ProvidesActivities, "isConnected": True if x.ID in user_connections else False, "authURI": x.UserAuthorizationURL} for x in Service.List() if x.ID not in WITHDRAWN_SERVICES and x.ID != "decathlon"]
user_connections = req.user.get("ConnectedServices")
user_connections_name = [connection["Service"] for connection in user_connections]
user_connections_with_auth_error = [
connection["Service"]
for connection in user_connections
if Service.GetServiceRecordByID(connection["ID"]).HasAuthSyncError()
]

active_providers = [
{
"id": x.ID,
"displayName": x.DisplayName,
"mustReconnect": x.ID in user_connections_with_auth_error,
"isReceiver": x.ReceivesActivities,
"isSupplier": x.ProvidesActivities,
"isConnected": True if x.ID in user_connections_name else False,
"authURI": x.UserAuthorizationURL
} for x in Service.List() if x.ID not in WITHDRAWN_SERVICES and x.ID != "decathlon"
]

return JsonResponse({"providers": active_providers})
else:
return HttpResponse(content="<h1>Unauthorized</h1>" ,status=403)