NIHVIVO-1207 Rename Shibboleth servlets to more general ExternalAuth servlets. Add functionality to deal with self-editors as well as Users.
This commit is contained in:
parent
dae66852f9
commit
37c9eaf4a1
7 changed files with 246 additions and 153 deletions
|
@ -1087,8 +1087,13 @@
|
||||||
</servlet>
|
</servlet>
|
||||||
|
|
||||||
<servlet>
|
<servlet>
|
||||||
<servlet-name>loginShibboleth</servlet-name>
|
<servlet-name>loginExternalAuthSetup</servlet-name>
|
||||||
<servlet-class>edu.cornell.mannlib.vitro.webapp.controller.authenticate.LoginShibboleth</servlet-class>
|
<servlet-class>edu.cornell.mannlib.vitro.webapp.controller.authenticate.LoginExternalAuthSetup</servlet-class>
|
||||||
|
</servlet>
|
||||||
|
|
||||||
|
<servlet>
|
||||||
|
<servlet-name>loginExternalAuthReturn</servlet-name>
|
||||||
|
<servlet-class>edu.cornell.mannlib.vitro.webapp.controller.authenticate.LoginExternalAuthReturn</servlet-class>
|
||||||
</servlet>
|
</servlet>
|
||||||
|
|
||||||
<servlet>
|
<servlet>
|
||||||
|
@ -1096,6 +1101,15 @@
|
||||||
<servlet-class>edu.cornell.mannlib.vitro.webapp.controller.edit.Logout</servlet-class>
|
<servlet-class>edu.cornell.mannlib.vitro.webapp.controller.edit.Logout</servlet-class>
|
||||||
</servlet>
|
</servlet>
|
||||||
|
|
||||||
|
<servlet>
|
||||||
|
<servlet-name>unrecognizedUser</servlet-name>
|
||||||
|
<servlet-class>edu.cornell.mannlib.vitro.webapp.controller.authenticate.UnrecognizedUserController</servlet-class>
|
||||||
|
</servlet>
|
||||||
|
<servlet-mapping>
|
||||||
|
<servlet-name>unrecognizedUser</servlet-name>
|
||||||
|
<url-pattern>/unrecognizedUser</url-pattern>
|
||||||
|
</servlet-mapping>
|
||||||
|
|
||||||
<servlet>
|
<servlet>
|
||||||
<servlet-name>browsecontroller</servlet-name>
|
<servlet-name>browsecontroller</servlet-name>
|
||||||
<servlet-class>edu.cornell.mannlib.vitro.webapp.controller.freemarker.BrowseController</servlet-class>
|
<servlet-class>edu.cornell.mannlib.vitro.webapp.controller.freemarker.BrowseController</servlet-class>
|
||||||
|
@ -1258,6 +1272,14 @@
|
||||||
<servlet-name>loginShibboleth</servlet-name>
|
<servlet-name>loginShibboleth</servlet-name>
|
||||||
<url-pattern>/loginShibboleth</url-pattern>
|
<url-pattern>/loginShibboleth</url-pattern>
|
||||||
</servlet-mapping>
|
</servlet-mapping>
|
||||||
|
<servlet-mapping>
|
||||||
|
<servlet-name>loginExternalAuthSetup</servlet-name>
|
||||||
|
<url-pattern>/loginExternalAuth</url-pattern>
|
||||||
|
</servlet-mapping>
|
||||||
|
<servlet-mapping>
|
||||||
|
<servlet-name>loginExternalAuthReturn</servlet-name>
|
||||||
|
<url-pattern>/loginExternalAuthReturn</url-pattern>
|
||||||
|
</servlet-mapping>
|
||||||
<servlet-mapping>
|
<servlet-mapping>
|
||||||
<!-- for backward-compatibility -->
|
<!-- for backward-compatibility -->
|
||||||
<servlet-name>login</servlet-name>
|
<servlet-name>login</servlet-name>
|
||||||
|
|
|
@ -0,0 +1,117 @@
|
||||||
|
/* $This file is distributed under the terms of the license in /doc/license.txt$ */
|
||||||
|
|
||||||
|
package edu.cornell.mannlib.vitro.webapp.controller.authenticate;
|
||||||
|
|
||||||
|
import static edu.cornell.mannlib.vitro.webapp.controller.authenticate.LoginExternalAuthSetup.ATTRIBUTE_REFERRER;
|
||||||
|
|
||||||
|
import java.io.IOException;
|
||||||
|
|
||||||
|
import javax.servlet.ServletException;
|
||||||
|
import javax.servlet.http.HttpServletRequest;
|
||||||
|
import javax.servlet.http.HttpServletResponse;
|
||||||
|
|
||||||
|
import org.apache.commons.logging.Log;
|
||||||
|
import org.apache.commons.logging.LogFactory;
|
||||||
|
|
||||||
|
import edu.cornell.mannlib.vitro.webapp.ConfigurationProperties;
|
||||||
|
import edu.cornell.mannlib.vitro.webapp.controller.VitroRequest;
|
||||||
|
import edu.cornell.mannlib.vitro.webapp.controller.login.LoginProcessBean;
|
||||||
|
import edu.cornell.mannlib.vitro.webapp.controller.login.LoginProcessBean.Message;
|
||||||
|
import edu.cornell.mannlib.vitro.webapp.dao.WebappDaoFactory;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Handle the return from the external authorization login server. If we are
|
||||||
|
* successful, record the login. Otherwise, display the failure.
|
||||||
|
*/
|
||||||
|
public class LoginExternalAuthReturn extends BaseLoginServlet {
|
||||||
|
private static final Log log = LogFactory
|
||||||
|
.getLog(LoginExternalAuthReturn.class);
|
||||||
|
|
||||||
|
/* This configuration property tells us what header contains the username. */
|
||||||
|
public static final String PROPERTY_EXTERNAL_AUTH_USERNAME_HEADER = "externalAuth.headerName";
|
||||||
|
|
||||||
|
/** The complaint we make if there is no such property. */
|
||||||
|
private static final Message MESSAGE_NO_EXTERNAL_AUTH_USERNAME = new LoginProcessBean.Message(
|
||||||
|
"deploy.properties doesn't contain a value for '"
|
||||||
|
+ PROPERTY_EXTERNAL_AUTH_USERNAME_HEADER + "'",
|
||||||
|
LoginProcessBean.MLevel.ERROR);
|
||||||
|
|
||||||
|
private static final Message MESSAGE_LOGIN_FAILED = new LoginProcessBean.Message(
|
||||||
|
"External login failed.", LoginProcessBean.MLevel.ERROR);
|
||||||
|
|
||||||
|
private final LoginRedirector loginRedirector = new LoginRedirector();
|
||||||
|
private String externalAuthUsernameHeader;
|
||||||
|
|
||||||
|
/** Get the configuration properties. */
|
||||||
|
@Override
|
||||||
|
public void init() throws ServletException {
|
||||||
|
externalAuthUsernameHeader = ConfigurationProperties
|
||||||
|
.getProperty(PROPERTY_EXTERNAL_AUTH_USERNAME_HEADER);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* <pre>
|
||||||
|
* Returning from the external authorization server. If we were successful,
|
||||||
|
* the header will contain the name of the user who just logged in.
|
||||||
|
*
|
||||||
|
* Deal with these possibilities:
|
||||||
|
* - The header name was not configured in deploy.properties. Complain.
|
||||||
|
* - No username: the login failed. Complain
|
||||||
|
* - User corresponds to a User acocunt. Record the login.
|
||||||
|
* - User corresponds to an Individual (self-editor).
|
||||||
|
* - User is not recognized.
|
||||||
|
* </pre>
|
||||||
|
*/
|
||||||
|
@Override
|
||||||
|
protected void doPost(HttpServletRequest req, HttpServletResponse resp)
|
||||||
|
throws ServletException, IOException {
|
||||||
|
if (externalAuthUsernameHeader == null) {
|
||||||
|
complainAndReturnToReferrer(req, resp, ATTRIBUTE_REFERRER,
|
||||||
|
MESSAGE_NO_EXTERNAL_AUTH_USERNAME);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
String username = req.getHeader(externalAuthUsernameHeader);
|
||||||
|
String uri = getAssociatedIndividualUri(username, req);
|
||||||
|
|
||||||
|
if (username == null) {
|
||||||
|
log.debug("No username.");
|
||||||
|
complainAndReturnToReferrer(req, resp, ATTRIBUTE_REFERRER,
|
||||||
|
MESSAGE_LOGIN_FAILED);
|
||||||
|
} else if (getAuthenticator(req).isExistingUser(username)) {
|
||||||
|
log.debug("Logging in as " + username);
|
||||||
|
getAuthenticator(req).recordUserIsLoggedIn(username);
|
||||||
|
removeLoginProcessArtifacts(req);
|
||||||
|
loginRedirector.redirectLoggedInUser(req, resp);
|
||||||
|
} else if (uri != null) {
|
||||||
|
log.debug("Recognize '' as self-editor for " + uri);
|
||||||
|
removeLoginProcessArtifacts(req);
|
||||||
|
loginRedirector.redirectSelfEditingUser(req, resp, uri);
|
||||||
|
} else {
|
||||||
|
log.debug("User is not recognized: " + username);
|
||||||
|
removeLoginProcessArtifacts(req);
|
||||||
|
loginRedirector.redirectUnrecognizedUser(req, resp, username);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
private String getAssociatedIndividualUri(String username,
|
||||||
|
HttpServletRequest req) {
|
||||||
|
if (username == null) {
|
||||||
|
return null;
|
||||||
|
}
|
||||||
|
VitroRequest vreq = new VitroRequest(req);
|
||||||
|
WebappDaoFactory wdf = vreq.getWebappDaoFactory();
|
||||||
|
return wdf.getIndividualDao().getIndividualURIFromNetId(username);
|
||||||
|
}
|
||||||
|
|
||||||
|
private void removeLoginProcessArtifacts(HttpServletRequest req) {
|
||||||
|
LoginProcessBean.removeBean(req);
|
||||||
|
req.getSession().removeAttribute(ATTRIBUTE_REFERRER);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
protected void doGet(HttpServletRequest request,
|
||||||
|
HttpServletResponse response) throws ServletException, IOException {
|
||||||
|
doPost(request, response);
|
||||||
|
}
|
||||||
|
}
|
|
@ -19,69 +19,71 @@ import edu.cornell.mannlib.vitro.webapp.controller.login.LoginProcessBean;
|
||||||
import edu.cornell.mannlib.vitro.webapp.controller.login.LoginProcessBean.Message;
|
import edu.cornell.mannlib.vitro.webapp.controller.login.LoginProcessBean.Message;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Set up the Shibboleth login process.
|
* Set up the external authorization process.
|
||||||
*
|
*
|
||||||
* Write down the page that triggered the request, so we can get back to it.
|
* Write down the page that triggered the request, so we can get back to it.
|
||||||
*
|
*
|
||||||
* Send a request to the Shibboleth server that will return us to the
|
* Send a request to the external authorization server that will return us to
|
||||||
* LoginShibbolethReturn servlet for further processing.
|
* the LoginExternalAuthReturn servlet for further processing.
|
||||||
*/
|
*/
|
||||||
public class LoginShibbolethSetup extends BaseLoginServlet {
|
public class LoginExternalAuthSetup extends BaseLoginServlet {
|
||||||
private static final Log log = LogFactory
|
private static final Log log = LogFactory
|
||||||
.getLog(LoginShibbolethSetup.class);
|
.getLog(LoginExternalAuthSetup.class);
|
||||||
|
|
||||||
/** This session attribute tells where we came from. */
|
/** This session attribute tells where we came from. */
|
||||||
static final String ATTRIBUTE_REFERRER = LoginShibbolethSetup.class
|
static final String ATTRIBUTE_REFERRER = LoginExternalAuthSetup.class
|
||||||
.getName() + ".referrer";
|
.getName() + ".referrer";
|
||||||
|
|
||||||
private static final String RETURN_SERVLET_URL = "/loginShibbolethReturn";
|
private static final String RETURN_SERVLET_URL = "/loginExternalAuthReturn";
|
||||||
|
|
||||||
/** This http header holds the referring page. */
|
/** This http header holds the referring page. */
|
||||||
private static final String HEADING_REFERRER = "referer";
|
private static final String HEADING_REFERRER = "referer";
|
||||||
|
|
||||||
/** The configuration property that points to the Shibboleth server. */
|
/**
|
||||||
private static final String PROPERTY_SHIBBOLETH_SERVER_URL = "shibboleth.server.url";
|
* The configuration property that points to the external authorization
|
||||||
|
* server.
|
||||||
|
*/
|
||||||
|
private static final String PROPERTY_EXTERNAL_AUTH_SERVER_URL = "externalAuth.serverUrl";
|
||||||
|
|
||||||
/** The complaint we make if there is no Shibbolet server property. */
|
/**
|
||||||
private static final Message MESSAGE_NO_SHIBBOLETH_SERVER = new LoginProcessBean.Message(
|
* The complaint we make if there is no external authorization server
|
||||||
|
* property.
|
||||||
|
*/
|
||||||
|
private static final Message MESSAGE_NO_EXTERNAL_AUTH_SERVER = new LoginProcessBean.Message(
|
||||||
"deploy.properties doesn't contain a value for '"
|
"deploy.properties doesn't contain a value for '"
|
||||||
+ PROPERTY_SHIBBOLETH_SERVER_URL + "'",
|
+ PROPERTY_EXTERNAL_AUTH_SERVER_URL + "'",
|
||||||
LoginProcessBean.MLevel.ERROR);
|
LoginProcessBean.MLevel.ERROR);
|
||||||
|
|
||||||
private String shibbolethServerUrl;
|
private String extrnalAuthServerUrl;
|
||||||
|
|
||||||
/** Get the configuration property. */
|
/** Get the configuration property. */
|
||||||
@Override
|
@Override
|
||||||
public void init() throws ServletException {
|
public void init() throws ServletException {
|
||||||
shibbolethServerUrl = ConfigurationProperties
|
extrnalAuthServerUrl = ConfigurationProperties
|
||||||
.getProperty(PROPERTY_SHIBBOLETH_SERVER_URL);
|
.getProperty(PROPERTY_EXTERNAL_AUTH_SERVER_URL);
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Write down the referring page, record that we are logging in, and
|
* Write down the referring page, record that we are logging in, and
|
||||||
* redirect to the shib server URL.
|
* redirect to the external authorization server URL.
|
||||||
*/
|
*/
|
||||||
@Override
|
@Override
|
||||||
protected void doPost(HttpServletRequest req, HttpServletResponse resp)
|
protected void doPost(HttpServletRequest req, HttpServletResponse resp)
|
||||||
throws ServletException, IOException {
|
throws ServletException, IOException {
|
||||||
// Record where we came from, so we can get back there.
|
|
||||||
storeTheReferringPage(req);
|
storeTheReferringPage(req);
|
||||||
|
|
||||||
// If we have no URL for the Shibboleth server, give up.
|
if (extrnalAuthServerUrl == null) {
|
||||||
if (shibbolethServerUrl == null) {
|
log.debug("No external authorization server in deploy.properties");
|
||||||
log.debug("No shibboleth server in deploy.properties");
|
|
||||||
complainAndReturnToReferrer(req, resp, ATTRIBUTE_REFERRER,
|
complainAndReturnToReferrer(req, resp, ATTRIBUTE_REFERRER,
|
||||||
MESSAGE_NO_SHIBBOLETH_SERVER);
|
MESSAGE_NO_EXTERNAL_AUTH_SERVER);
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
// Record that we are in the process of logging in.
|
|
||||||
LoginProcessBean.getBean(req).setState(
|
LoginProcessBean.getBean(req).setState(
|
||||||
LoginProcessBean.State.LOGGING_IN);
|
LoginProcessBean.State.LOGGING_IN);
|
||||||
|
|
||||||
// Hand over to Shibboleth.
|
log.debug("Sending to external authorization server.");
|
||||||
log.debug("Sending to shibboleth server.");
|
resp.sendRedirect(buildExternalAuthRedirectUrl(req));
|
||||||
resp.sendRedirect(buildShibbolethRedirectUrl(req));
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/** Remember where we came from - we'll need to go back there. */
|
/** Remember where we came from - we'll need to go back there. */
|
||||||
|
@ -95,15 +97,15 @@ public class LoginShibbolethSetup extends BaseLoginServlet {
|
||||||
req.getSession().setAttribute(ATTRIBUTE_REFERRER, referrer);
|
req.getSession().setAttribute(ATTRIBUTE_REFERRER, referrer);
|
||||||
}
|
}
|
||||||
|
|
||||||
/** How do we get to the Shibboleth server and back? */
|
/** How do we get to the external authorization server and back? */
|
||||||
private String buildShibbolethRedirectUrl(HttpServletRequest req) {
|
private String buildExternalAuthRedirectUrl(HttpServletRequest req) {
|
||||||
try {
|
try {
|
||||||
String returnUrl = figureHomePageUrl(req) + RETURN_SERVLET_URL;
|
String returnUrl = figureHomePageUrl(req) + RETURN_SERVLET_URL;
|
||||||
String encodedReturnUrl = URLEncoder.encode(returnUrl, "UTF-8");
|
String encodedReturnUrl = URLEncoder.encode(returnUrl, "UTF-8");
|
||||||
String shibbolethUrl = shibbolethServerUrl + "?target="
|
String externalAuthUrl = extrnalAuthServerUrl + "?target="
|
||||||
+ encodedReturnUrl;
|
+ encodedReturnUrl;
|
||||||
log.debug("shibbolethURL is '" + shibbolethUrl + "'");
|
log.debug("externalAuthUrl is '" + externalAuthUrl + "'");
|
||||||
return shibbolethUrl;
|
return externalAuthUrl;
|
||||||
} catch (UnsupportedEncodingException e) {
|
} catch (UnsupportedEncodingException e) {
|
||||||
throw new RuntimeException(e); // No UTF-8? Really?
|
throw new RuntimeException(e); // No UTF-8? Really?
|
||||||
}
|
}
|
|
@ -3,6 +3,7 @@
|
||||||
package edu.cornell.mannlib.vitro.webapp.controller.authenticate;
|
package edu.cornell.mannlib.vitro.webapp.controller.authenticate;
|
||||||
|
|
||||||
import java.io.IOException;
|
import java.io.IOException;
|
||||||
|
import java.io.UnsupportedEncodingException;
|
||||||
import java.net.URLEncoder;
|
import java.net.URLEncoder;
|
||||||
import java.util.List;
|
import java.util.List;
|
||||||
|
|
||||||
|
@ -23,9 +24,23 @@ import edu.cornell.mannlib.vitro.webapp.controller.Controllers;
|
||||||
public class LoginRedirector {
|
public class LoginRedirector {
|
||||||
private static final Log log = LogFactory.getLog(LoginRedirector.class);
|
private static final Log log = LogFactory.getLog(LoginRedirector.class);
|
||||||
|
|
||||||
|
public void redirectSelfEditingUser(HttpServletRequest request,
|
||||||
|
HttpServletResponse response, String uri) throws IOException {
|
||||||
|
String userHomePage = assembleUserHomePageUrl(request, uri);
|
||||||
|
log.debug("Redirecting self-editor to " + userHomePage);
|
||||||
|
response.sendRedirect(userHomePage);
|
||||||
|
}
|
||||||
|
|
||||||
|
public void redirectUnrecognizedUser(HttpServletRequest request,
|
||||||
|
HttpServletResponse response, String username) throws IOException {
|
||||||
|
log.debug("Redirecting unrecognized user: " + username);
|
||||||
|
response.sendRedirect(request.getContextPath()
|
||||||
|
+ "/unrecognizedUser?username=" + username);
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* <pre>
|
* <pre>
|
||||||
* Exit: the user is logged in. They might go to:
|
* The user is logged in. They might go to:
|
||||||
* - A one-time redirect, stored in the session, if they had tried to
|
* - A one-time redirect, stored in the session, if they had tried to
|
||||||
* bookmark to a page that requires login.
|
* bookmark to a page that requires login.
|
||||||
* - An application-wide redirect, stored in the servlet context.
|
* - An application-wide redirect, stored in the servlet context.
|
||||||
|
@ -68,9 +83,8 @@ public class LoginRedirector {
|
||||||
List<String> uris = getAuthenticator(request)
|
List<String> uris = getAuthenticator(request)
|
||||||
.asWhomMayThisUserEdit(user);
|
.asWhomMayThisUserEdit(user);
|
||||||
if (uris != null && uris.size() > 0) {
|
if (uris != null && uris.size() > 0) {
|
||||||
String userHomePage = request.getContextPath()
|
String userHomePage = assembleUserHomePageUrl(request,
|
||||||
+ "/individual?uri="
|
uris.get(0));
|
||||||
+ URLEncoder.encode(uris.get(0), "UTF-8");
|
|
||||||
log.debug("User is logged in. Redirect as self-editor to "
|
log.debug("User is logged in. Redirect as self-editor to "
|
||||||
+ userHomePage);
|
+ userHomePage);
|
||||||
response.sendRedirect(userHomePage);
|
response.sendRedirect(userHomePage);
|
||||||
|
@ -106,7 +120,6 @@ public class LoginRedirector {
|
||||||
|
|
||||||
/** What's the URL for the site admin screen? */
|
/** What's the URL for the site admin screen? */
|
||||||
private String getSiteAdminUrl(HttpServletRequest request) {
|
private String getSiteAdminUrl(HttpServletRequest request) {
|
||||||
// return Route.SITE_ADMIN.url();
|
|
||||||
String contextPath = request.getContextPath();
|
String contextPath = request.getContextPath();
|
||||||
return contextPath + Controllers.SITE_ADMIN;
|
return contextPath + Controllers.SITE_ADMIN;
|
||||||
}
|
}
|
||||||
|
@ -116,4 +129,9 @@ public class LoginRedirector {
|
||||||
return Authenticator.getInstance(request);
|
return Authenticator.getInstance(request);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
private String assembleUserHomePageUrl(HttpServletRequest request,
|
||||||
|
String uri) throws UnsupportedEncodingException {
|
||||||
|
return request.getContextPath() + "/individual?uri="
|
||||||
|
+ URLEncoder.encode(uri, "UTF-8");
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -1,116 +0,0 @@
|
||||||
/* $This file is distributed under the terms of the license in /doc/license.txt$ */
|
|
||||||
|
|
||||||
package edu.cornell.mannlib.vitro.webapp.controller.authenticate;
|
|
||||||
|
|
||||||
import static edu.cornell.mannlib.vitro.webapp.controller.authenticate.LoginShibbolethSetup.ATTRIBUTE_REFERRER;
|
|
||||||
|
|
||||||
import java.io.IOException;
|
|
||||||
import java.io.UnsupportedEncodingException;
|
|
||||||
|
|
||||||
import javax.servlet.ServletException;
|
|
||||||
import javax.servlet.http.HttpServletRequest;
|
|
||||||
import javax.servlet.http.HttpServletResponse;
|
|
||||||
|
|
||||||
import org.apache.commons.logging.Log;
|
|
||||||
import org.apache.commons.logging.LogFactory;
|
|
||||||
|
|
||||||
import edu.cornell.mannlib.vitro.webapp.ConfigurationProperties;
|
|
||||||
import edu.cornell.mannlib.vitro.webapp.controller.login.LoginProcessBean;
|
|
||||||
import edu.cornell.mannlib.vitro.webapp.controller.login.LoginProcessBean.Message;
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Handle the return from the Shibboleth login server. If we are successful,
|
|
||||||
* record the login. Otherwise, display the failure.
|
|
||||||
*/
|
|
||||||
public class LoginShibbolethReturn extends BaseLoginServlet {
|
|
||||||
private static final Log log = LogFactory
|
|
||||||
.getLog(LoginShibbolethReturn.class);
|
|
||||||
|
|
||||||
/** The configuration property that tells what provider name we expect. */
|
|
||||||
private static final String PROPERTY_SHIBBOLETH_PROVIDER = "shibboleth.provider";
|
|
||||||
|
|
||||||
/** On return froma Shibboleth login, this header holds the provider name. */
|
|
||||||
private static final String HEADING_SHIBBOLETH_PROVIDER = "shib-identity-provider";
|
|
||||||
|
|
||||||
/** On return froma Shibboleth login, this header holds the user name. */
|
|
||||||
private static final String HEADING_SHIBBOLETH_USERNAME = "glid";
|
|
||||||
|
|
||||||
private static final Message MESSAGE_LOGIN_FAILED = new LoginProcessBean.Message(
|
|
||||||
"Shibboleth login failed.", LoginProcessBean.MLevel.ERROR);
|
|
||||||
|
|
||||||
private static final Message MESSAGE_NO_SUCH_USER = new LoginProcessBean.Message(
|
|
||||||
"Shibboleth login succeeded, but user {0} is unknown to VIVO.",
|
|
||||||
LoginProcessBean.MLevel.ERROR);
|
|
||||||
|
|
||||||
private static final Message MESSAGE_NO_SHIBBOLETH_PROVIDER = new LoginProcessBean.Message(
|
|
||||||
"deploy.properties doesn't contain a value for '"
|
|
||||||
+ PROPERTY_SHIBBOLETH_PROVIDER + "'",
|
|
||||||
LoginProcessBean.MLevel.ERROR);
|
|
||||||
|
|
||||||
private final LoginRedirector loginRedirector = new LoginRedirector();
|
|
||||||
private String shibbolethProvider;
|
|
||||||
|
|
||||||
/** Get the configuration properties. */
|
|
||||||
@Override
|
|
||||||
public void init() throws ServletException {
|
|
||||||
shibbolethProvider = ConfigurationProperties
|
|
||||||
.getProperty(PROPERTY_SHIBBOLETH_PROVIDER);
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Returning from the Shibboleth server. If we were successful, the headers
|
|
||||||
* will contain the Shibboleth provider name and the name of the user who
|
|
||||||
* just logged in.
|
|
||||||
*
|
|
||||||
* We report problems if the provider name is missing or we don't know the
|
|
||||||
* correct value for it. We also report problems if the username is missing
|
|
||||||
* or if we don't recognize that user.
|
|
||||||
*
|
|
||||||
* If there are no problems, record the login and redirect like we would on
|
|
||||||
* a normal login.
|
|
||||||
*/
|
|
||||||
@Override
|
|
||||||
protected void doPost(HttpServletRequest req, HttpServletResponse resp)
|
|
||||||
throws ServletException, IOException {
|
|
||||||
String provider = req.getHeader(HEADING_SHIBBOLETH_PROVIDER);
|
|
||||||
String user = req.getHeader(HEADING_SHIBBOLETH_USERNAME);
|
|
||||||
log.debug("Info from Shibboleth: user=" + user + ", provider="
|
|
||||||
+ provider);
|
|
||||||
|
|
||||||
if ((provider == null) || (user == null)) {
|
|
||||||
complainAndReturnToReferrer(req, resp, ATTRIBUTE_REFERRER,
|
|
||||||
MESSAGE_LOGIN_FAILED);
|
|
||||||
} else if (shibbolethProvider == null) {
|
|
||||||
log.debug("No shibboleth provider in deploy.properties");
|
|
||||||
complainAndReturnToReferrer(req, resp, ATTRIBUTE_REFERRER,
|
|
||||||
MESSAGE_NO_SHIBBOLETH_PROVIDER);
|
|
||||||
} else if (!this.shibbolethProvider.equals(provider)) {
|
|
||||||
log.error("Wrong shibboleth provider: " + provider);
|
|
||||||
complainAndReturnToReferrer(req, resp, ATTRIBUTE_REFERRER,
|
|
||||||
MESSAGE_LOGIN_FAILED);
|
|
||||||
} else if (!getAuthenticator(req).isExistingUser(user)) {
|
|
||||||
log.debug("No such user: " + user);
|
|
||||||
complainAndReturnToReferrer(req, resp, ATTRIBUTE_REFERRER,
|
|
||||||
MESSAGE_NO_SUCH_USER, user);
|
|
||||||
} else {
|
|
||||||
log.debug("Logging in as " + user);
|
|
||||||
recordLoginAndRedirect(req, resp, user);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
/** Success. Record the login and send them to the appropriate page. */
|
|
||||||
private void recordLoginAndRedirect(HttpServletRequest req,
|
|
||||||
HttpServletResponse resp, String username)
|
|
||||||
throws UnsupportedEncodingException, IOException {
|
|
||||||
getAuthenticator(req).recordUserIsLoggedIn(username);
|
|
||||||
LoginProcessBean.removeBean(req);
|
|
||||||
req.getSession().removeAttribute(ATTRIBUTE_REFERRER);
|
|
||||||
loginRedirector.redirectLoggedInUser(req, resp);
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
protected void doGet(HttpServletRequest request,
|
|
||||||
HttpServletResponse response) throws ServletException, IOException {
|
|
||||||
doPost(request, response);
|
|
||||||
}
|
|
||||||
}
|
|
|
@ -0,0 +1,35 @@
|
||||||
|
/* $This file is distributed under the terms of the license in /doc/license.txt$ */
|
||||||
|
|
||||||
|
package edu.cornell.mannlib.vitro.webapp.controller.authenticate;
|
||||||
|
|
||||||
|
import java.util.HashMap;
|
||||||
|
import java.util.Map;
|
||||||
|
|
||||||
|
import edu.cornell.mannlib.vitro.webapp.controller.VitroRequest;
|
||||||
|
import edu.cornell.mannlib.vitro.webapp.controller.freemarker.FreemarkerHttpServlet;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* TODO
|
||||||
|
*/
|
||||||
|
public class UnrecognizedUserController extends FreemarkerHttpServlet {
|
||||||
|
private static final String TEMPLATE_DEFAULT = "unrecognizedUser.ftl";
|
||||||
|
private static final String PARAMETER_USERNAME = "username";
|
||||||
|
|
||||||
|
@Override
|
||||||
|
protected ResponseValues processRequest(VitroRequest vreq) {
|
||||||
|
Map<String, Object> body = new HashMap<String, Object>();
|
||||||
|
|
||||||
|
String username = vreq.getParameter(PARAMETER_USERNAME);
|
||||||
|
if (username != null) {
|
||||||
|
body.put("username", username);
|
||||||
|
}
|
||||||
|
|
||||||
|
return new TemplateResponseValues(TEMPLATE_DEFAULT, body);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
protected String getTitle(String siteName) {
|
||||||
|
return "Unrecognized user " + siteName;
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
15
webapp/web/templates/freemarker/body/unrecognizedUser.ftl
Normal file
15
webapp/web/templates/freemarker/body/unrecognizedUser.ftl
Normal file
|
@ -0,0 +1,15 @@
|
||||||
|
<#-- $This file is distributed under the terms of the license in /doc/license.txt$ -->
|
||||||
|
|
||||||
|
<#-- Template for the Unrecognized User page. -->
|
||||||
|
|
||||||
|
<section role="region">
|
||||||
|
<h2>Unrecognized user</h2>
|
||||||
|
|
||||||
|
<p>
|
||||||
|
For some reason, there is no individual in VIVO that is associated with your Net ID.
|
||||||
|
Perhaps you should contact your VIVO administrator.
|
||||||
|
</p>
|
||||||
|
|
||||||
|
<br/>
|
||||||
|
<a href="${urls.home}">Continue</a>
|
||||||
|
</section>
|
Loading…
Add table
Add a link
Reference in a new issue