updated to manage authorised redirect URLs

git-svn-id: http://svn.research-infrastructures.eu/public/d4science/gcube/trunk/portlets/user/my-vres@141580 82a268e6-3cf1-43bd-a215-b396298e98cf
This commit is contained in:
Massimiliano Assante 2017-01-15 18:35:31 +00:00
parent 5fec8824b6
commit 38fde43f0e
6 changed files with 36 additions and 47 deletions

View File

@ -5,17 +5,14 @@ public class GetParameters {
String state; String state;
String context; String context;
String clientId; String clientId;
String clientSecret;
public GetParameters(String redirectURI, String state, String context, String clientId) {
public GetParameters(String redirectURI, String state, String context, String clientId, String clientSecret) {
super(); super();
this.redirectURI = redirectURI; this.redirectURI = redirectURI;
this.state = state; this.state = state;
this.context = context; this.context = context;
this.clientId = clientId; this.clientId = clientId;
this.clientSecret = clientSecret;
} }
public String getRedirectURI() { public String getRedirectURI() {
@ -34,14 +31,10 @@ public class GetParameters {
return clientId; return clientId;
} }
public String getClientSecret() {
return clientSecret;
}
@Override @Override
public String toString() { public String toString() {
return "GetParameters [redirectURI=" + redirectURI + ", state=" + state + ", context=" + context + ", clientId=" return "GetParameters [redirectURI=" + redirectURI + ", state=" + state + ", context=" + context + ", clientId="
+ clientId + ", clientSecret=" + clientSecret + "]"; + clientId + "]";
} }

View File

@ -49,7 +49,7 @@ public class MyVREs implements EntryPoint {
RootPanel.get("myVREsDIV").add(new VresPanel(params)); RootPanel.get("myVREsDIV").add(new VresPanel(params));
} }
else { else {
myVREsService.getUserToken(params.context, params.state, params.clientId, params.clientSecret, new AsyncCallback<AuthorizationBean>() { myVREsService.getUserToken(params.context, params.state, params.clientId, params.redirectURI, new AsyncCallback<AuthorizationBean>() {
@Override @Override
public void onSuccess(AuthorizationBean result) { public void onSuccess(AuthorizationBean result) {
if (result.isSuccess()) { if (result.isSuccess()) {
@ -80,8 +80,7 @@ public class MyVREs implements EntryPoint {
String state = Window.Location.getParameter(GET_STATE_PARAMETER); String state = Window.Location.getParameter(GET_STATE_PARAMETER);
String context = Window.Location.getParameter(GET_CONTEXT_PARAMETER); String context = Window.Location.getParameter(GET_CONTEXT_PARAMETER);
String clientId = Window.Location.getParameter(GET_CLIENT_ID_PARAMETER); String clientId = Window.Location.getParameter(GET_CLIENT_ID_PARAMETER);
String clientSecret = Window.Location.getParameter(GET_CLIENT_SECRET_PARAMETER);
return new GetParameters(redirectURI, state, context, clientId, clientSecret); return new GetParameters(redirectURI, state, context, clientId);
} }
} }

View File

@ -18,5 +18,5 @@ public interface MyVREsService extends RemoteService {
String getSiteLandingPagePath(); String getSiteLandingPagePath();
AuthorizationBean getUserToken(String context, String state, String clientId, String clientSecret); AuthorizationBean getUserToken(String context, String state, String clientId, String authorisedRedirectURL);
} }

View File

@ -15,7 +15,7 @@ public interface MyVREsServiceAsync {
void getSiteLandingPagePath(AsyncCallback<String> callback); void getSiteLandingPagePath(AsyncCallback<String> callback);
void getUserToken(String context, String state, String clientId, String clientSecret, void getUserToken(String context, String state, String clientId, String authorisedRedirectURI,
AsyncCallback<AuthorizationBean> callback); AsyncCallback<AuthorizationBean> callback);
} }

View File

@ -62,7 +62,7 @@ public class ClickableVRE extends HTML {
if (params != null) { if (params != null) {
addClickHandler(new ClickHandler() { addClickHandler(new ClickHandler() {
public void onClick(ClickEvent event) { public void onClick(ClickEvent event) {
myVREsService.getUserToken(vre.getContext(), params.getState(), params.getClientId(), params.getClientSecret(), new AsyncCallback<AuthorizationBean>() { myVREsService.getUserToken(vre.getContext(), params.getState(), params.getClientId(), params.getRedirectURI(), new AsyncCallback<AuthorizationBean>() {
@Override @Override
public void onSuccess(AuthorizationBean result) { public void onSuccess(AuthorizationBean result) {
if (result.isSuccess()) { if (result.isSuccess()) {

View File

@ -10,7 +10,6 @@ import java.util.List;
import javax.servlet.http.HttpServletRequest; import javax.servlet.http.HttpServletRequest;
import org.gcube.common.encryption.StringEncrypter;
import org.gcube.common.portal.GCubePortalConstants; import org.gcube.common.portal.GCubePortalConstants;
import org.gcube.common.portal.PortalContext; import org.gcube.common.portal.PortalContext;
import org.gcube.common.resources.gcore.ServiceEndpoint; import org.gcube.common.resources.gcore.ServiceEndpoint;
@ -51,10 +50,14 @@ public class MyVREsServiceImpl extends RemoteServiceServlet implements MyVREsSer
* *
*/ */
public static final String CACHED_VOS = "CACHED_VRES"; public static final String CACHED_VOS = "CACHED_VRES";
/**
* needed when querying for authorised services in authentication
*/
public static final String REDIRECT_URL = "RedirectURL";
private static final String SERVICE_ENDPOINT_CATEGORY = "OnlineService";
public static final String ADD_MORE_CATEGORY = "Add More"; public static final String ADD_MORE_CATEGORY = "Add More";
public static final String ADD_MORE_IMAGE_PATH= "images/More.png"; public static final String ADD_MORE_IMAGE_PATH= "images/More.png";
private static final String SERVICE_ENDPOINT_CATEGORY = "Portal";
@Override @Override
public String getSiteLandingPagePath() { public String getSiteLandingPagePath() {
@ -257,20 +260,25 @@ public class MyVREsServiceImpl extends RemoteServiceServlet implements MyVREsSer
} }
@Override @Override
public AuthorizationBean getUserToken(String context, String state, String clientId, String clientSecret) { public AuthorizationBean getUserToken(String context, String state, String clientId, String redirectURL) {
if (clientId == null || clientId.compareTo("")== 0) { if (clientId == null || clientId.compareTo("")== 0) {
return new AuthorizationBean(null, null, false, "client_id is null, you MUST register your application to allow users connect with their D4Science Credentials"); return new AuthorizationBean(null, null, false, "client_id is null, you MUST register your application to allow users connect with their D4Science Credentials");
} }
if (clientSecret == null || clientSecret.compareTo("")== 0) { if (redirectURL == null || redirectURL.compareTo("")== 0) {
return new AuthorizationBean(null, null, false, "client_secret is null, you MUST pass the clientSecret related to your client_id registered application to allow users connect with their D4Science Credentials"); return new AuthorizationBean(null, null, false, "authorised redirect URL is null, you MUST pass the authorisedRedirectURI related to your client_id registered application to allow users connect with their D4Science Credentials");
} }
String registeredClientSecret = getClientSecretFromIs(clientId); List<String> authorisedRedirectURLs = getAuthorisedRedirectURLsFromIs(clientId);
if (registeredClientSecret == null) { if (authorisedRedirectURLs == null || authorisedRedirectURLs.isEmpty()) {
return new AuthorizationBean(null, null, false, "Your client_id ("+ clientId +") is not registered in the infrastructure, you MUST register your client_id to allow users connect with their D4Science Credentials"); return new AuthorizationBean(null, null, false, "Your application ("+ clientId + ") is not registered or there are no authorised redirect URLs registered for your application");
}
if (registeredClientSecret.compareTo(clientSecret)!=0) {
return new AuthorizationBean(null, null, false, "The client_secret for clientId ("+ clientId +"), does not match");
} }
boolean urlAuthorised = false;
for (String authorisedURL : authorisedRedirectURLs)
if (authorisedURL.compareTo(redirectURL)==0) {
urlAuthorised = true;
break;
}
if (! urlAuthorised)
return new AuthorizationBean(null, null, false, "Invalid redirect URL. This value must match a URL registered with the clientId: " + clientId);
if (state == null || state.compareTo("")== 0) { if (state == null || state.compareTo("")== 0) {
return new AuthorizationBean(null, null, false, "State is null, please use a unique string value of your choice that is hard to guess (e.g. state=7d12bf13-111c-4f46-ab06-9e9e08ad377b). Used to prevent CSRF attacks"); return new AuthorizationBean(null, null, false, "State is null, please use a unique string value of your choice that is hard to guess (e.g. state=7d12bf13-111c-4f46-ab06-9e9e08ad377b). Used to prevent CSRF attacks");
} }
@ -312,13 +320,13 @@ public class MyVREsServiceImpl extends RemoteServiceServlet implements MyVREsSer
} }
//TODO: check the query, it doesn work //TODO: check the query, it doesn work
private List<ServiceEndpoint> getPortalConfigurationFromIS(String infrastructureName, String gatewayName) throws Exception { private List<ServiceEndpoint> getPortalConfigurationFromIS(String infrastructureName, String clientId) throws Exception {
String scope = "/" + infrastructureName; String scope = "/" + infrastructureName;
String currScope = ScopeProvider.instance.get(); String currScope = ScopeProvider.instance.get();
ScopeProvider.instance.set(scope); ScopeProvider.instance.set(scope);
SimpleQuery query = queryFor(ServiceEndpoint.class); SimpleQuery query = queryFor(ServiceEndpoint.class);
query.addCondition("$resource/Profile/Category/text() eq '"+ SERVICE_ENDPOINT_CATEGORY +"'"); query.addCondition("$resource/Profile/Category/text() eq '"+ SERVICE_ENDPOINT_CATEGORY +"'");
query.addCondition("$resource/Profile/Name/text() eq '"+ gatewayName +"'"); query.addCondition("$resource/Profile/Name/text() eq '"+ clientId +"'");
DiscoveryClient<ServiceEndpoint> client = clientFor(ServiceEndpoint.class); DiscoveryClient<ServiceEndpoint> client = clientFor(ServiceEndpoint.class);
List<ServiceEndpoint> toReturn = client.submit(query); List<ServiceEndpoint> toReturn = client.submit(query);
ScopeProvider.instance.set(currScope); ScopeProvider.instance.set(currScope);
@ -330,37 +338,26 @@ public class MyVREsServiceImpl extends RemoteServiceServlet implements MyVREsSer
* @param clientId * @param clientId
* @return the client secret related to the id, or null if non existent * @return the client secret related to the id, or null if non existent
*/ */
private String getClientSecretFromIs(String clientId) { private List<String> getAuthorisedRedirectURLsFromIs(String clientId) {
PortalContext pContext = PortalContext.getConfiguration(); PortalContext pContext = PortalContext.getConfiguration();
String gatewayName = pContext.getGatewayName(getThreadLocalRequest());
String scope = "/"+pContext.getInfrastructureName(); String scope = "/"+pContext.getInfrastructureName();
List<String> autRedirectURLs = new ArrayList<>();
try { try {
List<ServiceEndpoint> list = getPortalConfigurationFromIS(pContext.getInfrastructureName(), gatewayName); List<ServiceEndpoint> list = getPortalConfigurationFromIS(pContext.getInfrastructureName(), clientId);
if (list.size() > 1) { if (list.size() > 1) {
_log.error("Too many Service Endpoints having name " + gatewayName +" in this scope having Category " + SERVICE_ENDPOINT_CATEGORY); _log.error("Too many Service Endpoints having name " + clientId +" in this scope having Category " + SERVICE_ENDPOINT_CATEGORY);
} }
else if (list.size() == 0){ else if (list.size() == 0){
_log.warn("There is no Service Endpoint having name " + gatewayName +" and Category " + SERVICE_ENDPOINT_CATEGORY + " in this scope: " + scope); _log.warn("There is no Service Endpoint having name " + clientId +" and Category " + SERVICE_ENDPOINT_CATEGORY + " in this scope: " + scope);
} }
else { else {
for (ServiceEndpoint res : list) { for (ServiceEndpoint res : list) {
Group<AccessPoint> apGroup = res.profile().accessPoints(); Group<AccessPoint> apGroup = res.profile().accessPoints();
AccessPoint[] accessPoints = (AccessPoint[]) apGroup.toArray(new AccessPoint[apGroup.size()]); AccessPoint[] accessPoints = (AccessPoint[]) apGroup.toArray(new AccessPoint[apGroup.size()]);
for (int i = 0; i < accessPoints.length; i++) { for (int i = 0; i < accessPoints.length; i++) {
if (accessPoints[i].name().compareTo(clientId) == 0) { if (accessPoints[i].name().compareTo(REDIRECT_URL) == 0) {
_log.info("Found credentials for " + clientId);
AccessPoint found = accessPoints[i]; AccessPoint found = accessPoints[i];
//String thumbnailURL = found.address(); autRedirectURLs.add(found.address());
String encrPassword = found.password();
String clientSecret = "";
try {
clientSecret = StringEncrypter.getEncrypter().decrypt( encrPassword);
_log.debug("clientSecret for " + clientId + " found");
return clientSecret;
} catch (Exception e) {
_log.error("Something went wrong while decrypting password for " + clientId);
e.printStackTrace();
}
} }
} }
} }
@ -369,7 +366,7 @@ public class MyVREsServiceImpl extends RemoteServiceServlet implements MyVREsSer
e.printStackTrace(); e.printStackTrace();
return null; return null;
} }
return null; return autRedirectURLs;
} }
} }