Skip to content

Commit daf6860

Browse files
committed
Fix token refreshes against the Alfresco API
- send client-secret value when requesting new tokens, which seems to do no harm with Chatter and is also required by Google - If the refresh gives a new refresh token, then make sure this gets saved too
1 parent b0e37d8 commit daf6860

File tree

1 file changed

+41
-20
lines changed

1 file changed

+41
-20
lines changed

share-oauth/src/main/java/org/sharextras/webscripts/connector/HttpOAuth2Connector.java

Lines changed: 41 additions & 20 deletions
Original file line numberDiff line numberDiff line change
@@ -111,7 +111,7 @@ public Response call(String uri, ConnectorContext context, HttpServletRequest re
111111
FakeHttpServletResponse wrappedRes = new FakeHttpServletResponse(res);
112112

113113
Response resp = null;
114-
boolean newlyLoaded = false;
114+
boolean newlyLoaded = false, tokensChanged = false;
115115

116116
context.setCommitResponseOnAuthenticationError(false);
117117

@@ -193,21 +193,37 @@ public Response call(String uri, ConnectorContext context, HttpServletRequest re
193193
logger.debug("Trying to refresh access token - using refresh token " + getRefreshToken());
194194
try
195195
{
196-
String oldToken = getAccessToken();
197-
String newToken = doRefresh(endpointId);
196+
String oldToken = getAccessToken(), oldRefreshToken = getRefreshToken();
197+
JSONObject json = doRefresh(endpointId);
198+
String newToken = json.getString("access_token");
199+
if (logger.isDebugEnabled())
200+
logger.debug("Parsed access token: " + newToken);
198201
if (newToken != null && !newToken.equals(oldToken))
199202
{
200203
if (logger.isDebugEnabled())
201204
logger.debug("Got new access token " + newToken + " - retrying request for " + uri);
202205
connectorSession.setParameter(OAuth2Authenticator.CS_PARAM_ACCESS_TOKEN, newToken);
203-
saveTokens(endpointId, req);
206+
tokensChanged = true;
207+
// Retry the call
204208
wrappedRes.reset();
205209
resp = callInternal(uri, context, req, wrappedRes);
206210
}
207211
else
208212
{
209213
logger.debug("No token returned or token not updated");
210214
}
215+
// In some providers the refresh token may also change when a refresh occurs
216+
if (json.has("refresh_token"))
217+
{
218+
String refreshToken = json.getString("refresh_token");
219+
if (refreshToken != null && !refreshToken.equals(oldRefreshToken))
220+
{
221+
if (logger.isDebugEnabled())
222+
logger.debug("Got new refresh token " + refreshToken);
223+
connectorSession.setParameter(OAuth2Authenticator.CS_PARAM_REFRESH_TOKEN, refreshToken);
224+
tokensChanged = true;
225+
}
226+
}
211227
}
212228
catch (TokenRefreshException e)
213229
{
@@ -216,6 +232,18 @@ public Response call(String uri, ConnectorContext context, HttpServletRequest re
216232
"Unable to refresh token",
217233
e);
218234
}
235+
catch (JSONException e)
236+
{
237+
writeError(wrappedRes, ResponseStatus.STATUS_INTERNAL_SERVER_ERROR,
238+
"ERR_MISSING_ACCESS_TOKEN",
239+
"Unable to retrieve access token from provider response",
240+
e);
241+
}
242+
243+
if (tokensChanged)
244+
{
245+
saveTokens(endpointId, req);
246+
}
219247
}
220248

221249
copyResponseContent(resp, wrappedRes, res, true);
@@ -441,15 +469,15 @@ protected void applyRequestAuthentication(RemoteClient remoteClient, ConnectorCo
441469
}
442470
}
443471

444-
// TODO replace AuthenticationException with something else
445-
protected String doRefresh(String endpointId) throws TokenRefreshException
472+
protected JSONObject doRefresh(String endpointId) throws TokenRefreshException
446473
{
447474
String refreshToken = getRefreshToken();
448475
EndpointDescriptor epd = getEndpointDescriptor(endpointId);
449476

450477
// First try to get the client-id and access-token-url from the endpoint, then from the connector
451478
// TODO Make these strings constants in a Descriptor sub-class or interface
452479
String clientId = getDescriptorProperty("client-id", epd);
480+
String clientSecret = getDescriptorProperty("client-secret", epd);
453481
String tokenUrl = getDescriptorProperty("access-token-url", epd);
454482
/*
455483
RemoteClient remoteClient = buildRemoteClient(tokenUrl);
@@ -476,6 +504,7 @@ protected String doRefresh(String endpointId) throws TokenRefreshException
476504
method.addParameter("grant_type", "refresh_token");
477505
method.addParameter("refresh_token", refreshToken);
478506
method.addParameter("client_id", clientId);
507+
method.addParameter("client_secret", clientSecret);
479508
method.addRequestHeader("Accept", Format.JSON.mimetype());
480509

481510
int statusCode;
@@ -488,11 +517,10 @@ protected String doRefresh(String endpointId) throws TokenRefreshException
488517

489518
if (statusCode == Status.STATUS_OK)
490519
{
491-
String accessToken;
520+
JSONObject json;
492521
try
493522
{
494-
JSONObject json = new JSONObject(tokenResp);
495-
accessToken = json.getString("access_token");
523+
json = new JSONObject(tokenResp);
496524
}
497525
catch (JSONException jErr)
498526
{
@@ -502,30 +530,23 @@ protected String doRefresh(String endpointId) throws TokenRefreshException
502530
"Unable to retrieve access token from provider response", jErr);
503531
}
504532

505-
if (logger.isDebugEnabled())
506-
logger.debug("Parsed access token: " + accessToken);
507-
508-
return accessToken;
533+
return json;
509534
}
510535
else
511536
{
512537
if (logger.isDebugEnabled())
513538
logger.debug("Token refresh failed, received response code: " + statusCode);
514539
logger.debug("Received response " + tokenResp);
515-
return null;
540+
throw new TokenRefreshException("Token refresh failed, received response code: " + statusCode);
516541
}
517542
}
518543
catch (HttpException e)
519544
{
520-
// TODO Auto-generated catch block
521-
e.printStackTrace();
522-
return null;
545+
throw new TokenRefreshException("Error when refreshing tokens", e);
523546
}
524547
catch (IOException e)
525548
{
526-
// TODO Auto-generated catch block
527-
e.printStackTrace();
528-
return null;
549+
throw new TokenRefreshException("Error when refreshing tokens", e);
529550
}
530551
}
531552

0 commit comments

Comments
 (0)