Skip to content

Instantly share code, notes, and snippets.

@kakawait
Created March 27, 2017 12:03
Show Gist options
  • Save kakawait/18c16393ba626b46ec9ebd300d49b1ce to your computer and use it in GitHub Desktop.
Save kakawait/18c16393ba626b46ec9ebd300d49b1ce to your computer and use it in GitHub Desktop.
import com.fasterxml.jackson.databind.ObjectMapper;
import lombok.extern.slf4j.Slf4j;
import org.springframework.boot.autoconfigure.security.oauth2.resource.FixedPrincipalExtractor;
import org.springframework.boot.autoconfigure.security.oauth2.resource.PrincipalExtractor;
import org.springframework.core.ParameterizedTypeReference;
import org.springframework.http.HttpMethod;
import org.springframework.http.ResponseEntity;
import org.springframework.social.ApiException;
import org.springframework.social.connect.ApiAdapter;
import org.springframework.social.connect.ConnectionValues;
import org.springframework.social.connect.UserProfile;
import org.springframework.social.connect.UserProfileBuilder;
import org.springframework.web.client.RestClientException;
import org.springframework.web.client.RestOperations;
import java.net.URI;
import java.util.Map;
/**
* @author Thibaud Leprêtre
*/
@Slf4j
public class Oauth2ApiAdapter implements ApiAdapter<RestOperations> {
private static final PrincipalExtractor USER_ID_FIELD_EXTRACTOR = new FixedPrincipalExtractor();
private static final FieldExtractor NAME_FIELD_EXTRACTOR = new NameFieldExtractor();
private static final FieldExtractor PROFILE_URL_FIELD_EXTRACTOR = new ProfileUrlFieldExtractor();
private final String providerId;
private final URI userInfoUri;
private final ImageUrlFieldExtractor imageUrlFieldExtractor;
private final EmailFieldExtractor emailFieldExtractor;
public Oauth2ApiAdapter(String providerId, URI userInfoUri, ObjectMapper objectMapper) {
this.providerId = providerId;
this.userInfoUri = userInfoUri;
this.imageUrlFieldExtractor = new ImageUrlFieldExtractor(objectMapper);
this.emailFieldExtractor = new EmailFieldExtractor(objectMapper);
}
@Override
public boolean test(RestOperations api) {
try {
api.getForObject(userInfoUri, String.class);
return true;
} catch (Exception e) {
logger.debug("Unable to fetch profile for provider {} using following url: {}", providerId, userInfoUri, e);
return false;
}
}
@Override
public void setConnectionValues(RestOperations api, ConnectionValues values) {
Map<String, Object> profile = getUserProfile(api);
values.setProviderUserId((String) USER_ID_FIELD_EXTRACTOR.extractPrincipal(profile));
values.setDisplayName((String) NAME_FIELD_EXTRACTOR.extract(profile));
values.setProfileUrl((String) PROFILE_URL_FIELD_EXTRACTOR.extract(profile));
values.setImageUrl((String) imageUrlFieldExtractor.extract(profile));
}
@Override
public UserProfile fetchUserProfile(RestOperations api) {
Map<String, Object> profile = getUserProfile(api);
return new UserProfileBuilder()
.setUsername((String) USER_ID_FIELD_EXTRACTOR.extractPrincipal(profile))
.setEmail((String) emailFieldExtractor.extract(profile))
.setName((String) NAME_FIELD_EXTRACTOR.extract(profile))
.build();
}
@Override
public void updateStatus(RestOperations api, String message) {
throw new UnsupportedOperationException("Update status is not supported using generic adapter");
}
private Map<String, Object> getUserProfile(RestOperations api) {
ParameterizedTypeReference<Map<String, Object>> responseType =
new ParameterizedTypeReference<Map<String, Object>>() {};
try {
ResponseEntity<Map<String, Object>> response = api.exchange(userInfoUri, HttpMethod.GET, null, responseType);
if (!response.getStatusCode().is2xxSuccessful()) {
throw new ApiException(providerId, "Unable to fetch user profile using following url: \"" + userInfoUri
+ "\" - " + response.getStatusCode());
}
return response.getBody();
} catch (RestClientException e) {
throw new ApiException(providerId, "Unable to fetch user profile using following url: \"" + userInfoUri, e);
}
}
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment