Sei sulla pagina 1di 6

Implementación de SSO en sistemas con java y servidores glassfish

EN EL PROYECTO

Dependencias

pom.xml
<dependency>
<groupId>com.onelogin</groupId>
<artifactId>java-saml</artifactId>
<version>2.2.0</version>
</dependency>

Archivo de configuración

Adjuntado en la carpeta

Cambiar las direcciones url en la parte de

Service Provider Data (SP) por las direcciones

del sistema actual.

web.xml
<error-page>
<error-code>500</error-code>
<location>/login.xhtml</location>
</error-page>

Clases/Paginas a agregar o reemplazar


(están en el zip)

Clases modificadas desde la librería one login.


Utilizadas por LoginBacking.java, agregar en
un paquete nuevo .auth

Clases
Auth.java
ServletUtils.java

Paginas web
logout.xhtml
errorpage.xhtml
metadata.jsp
Clases a modificar

AuthorizationListener.java
LoginBacking.java
AuthorizationListener

agregar el metodo
public void getLoginPage() {
try {
HttpServletRequest request = (HttpServletRequest)
FacesContext.getCurrentInstance().getExternalContext().getRequest();
HttpServletResponse response = (HttpServletResponse)
FacesContext.getCurrentInstance().getExternalContext().getResponse();

Auth auth = new Auth(request, response);


if (request.getParameter("attrs") == null) {
String redirect = auth.login();

FacesContext.getCurrentInstance().getApplication().getNavigationHandler().handleNavigation(FacesCont
ext.getCurrentInstance(), null, redirect);
}
} catch (Error | SettingsException | IOException ex) {
Logger.getLogger(LoginBacking.class.getName()).log(Level.SEVERE, null, ex);
}
}

y modificar afterPhase donde redirecciona a /login


NavigationHandler nh = facesContext.getApplication().getNavigationHandler();
nh.handleNavigation(facesContext, null, "/login.xhtml?faces-redirect=true");

reemplazar las dos lineas por

getLoginPage();

Agregar imports

import ar.edu.unnoba.declaracionjurada.jsf.backing.Auth;
import ar.edu.unnoba.programas.jsf.backing.LoginBacking;
import com.onelogin.saml2.exception.SettingsException;
import java.io.IOException;
import java.util.logging.Level;
import java.util.logging.Logger;
import javax.faces.application.NavigationHandler;
import javax.faces.context.FacesContext;
import javax.faces.event.PhaseEvent;
import javax.faces.event.PhaseId;
import javax.faces.event.PhaseListener;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import javax.servlet.http.HttpSession;
LoginBacking.java

Importante esta clase debe implementar @SessionScoped

El metodo performLogin() tiene que realizar el login según el sistema y poner el usuario en sesión o
no, pero ya no devuelve nada.
public boolean performLogin() {
EntityWebResource ewr = new EntityWebResource();
String url_path = null;
String mensaje = "";
HttpServletRequest request = (HttpServletRequest)
FacesContext.getCurrentInstance().getExternalContext().getRequest();
try {
mensaje = authenticate(this.getUsuario().getUserName(),
this.getUsuario().getPassword());
if (!mensaje.equals("servicio_error") && !mensaje.equals("credentials_error")) {
Usuario user = this.load(this.getUsuario().getUserName(),
this.getUsuario().getPassword(), mensaje);
if (user == null) {
this.setCurrentUser(null);
return false;
} else {
this.setUsuario(user);
this.setCurrentUser(this.getUsuario());
url_path = getFullURL(request);
ewr.guardarRegistro(url_path, user.getUserName());
return true;
}
}
} catch (Exception e) {
System.out.println(e.getMessage());
return false;
}
}

Sobrescribir los siguientes metodos:

public void getIndexPage() {


FacesContext facesContext = FacesContext.getCurrentInstance();
String outcome = "/index?faces-redirect=true";
facesContext.getApplication().getNavigationHandler().handleNavigation(facesContext, null,
outcome);

public void getLoginPage() {


try {
HttpServletRequest request = (HttpServletRequest)
FacesContext.getCurrentInstance().getExternalContext().getRequest();
HttpServletResponse response = (HttpServletResponse)
FacesContext.getCurrentInstance().getExternalContext().getResponse();
Auth auth = new Auth(request, response);
if (request.getParameter("attrs") == null) {
String redirect = auth.login();

FacesContext.getCurrentInstance().getApplication().getNavigationHandler().handleNavigation(FacesCont
ext.getCurrentInstance(), null, redirect);
}
} catch (IOException ex) {
Logger.getLogger(LoginBacking.class.getName()).log(Level.SEVERE, null, ex);
} catch (SettingsException ex) {
Logger.getLogger(LoginBacking.class.getName()).log(Level.SEVERE, null, ex);
} catch (Error ex) {
Logger.getLogger(LoginBacking.class.getName()).log(Level.SEVERE, null, ex);
}
}

public void forwardToMainIfLoggedIn() {


String login = this.isUserLoggedIn();
if (login.equals("si")){
getIndexPage();
}
if (login.equals("no")) {
getLoginPage();
}
if (login.equals("error")) {
FacesContext facesContext = FacesContext.getCurrentInstance();
String outcome = "/errorpage?faces-redirect=true";
facesContext.getApplication().getNavigationHandler().handleNavigation(facesContext,
null, outcome);
}
}

/**
*
* @return
*/
public String isUserLoggedIn() {
String result = "no";
if (getSessionMap().containsKey("currentUser")) {
result = "si";
} else {

try {
HttpServletRequest request = (HttpServletRequest)
FacesContext.getCurrentInstance().getExternalContext().getRequest();
HttpServletResponse response = (HttpServletResponse)
FacesContext.getCurrentInstance().getExternalContext().getResponse();

Auth auth = new Auth(request, response);


auth.processResponse();

if (!auth.isAuthenticated()) {
result = "no";
} else {
Map<String, List<String>> attributes = auth.getAttributes();
String nameId = auth.getNameId();

if (tieneServicio((List<String>) auth.getAttribute("memberOf"))) {
this.getUsuario().setUserName(auth.getAttribute("mail").iterator().next());

this.getUsuario().setPassword(auth.getAttribute("user_password").iterator().next());
if (performLogin()) {
result = "si";
} else {
result = "error";
}
} else {
result = "error";
}

}
} catch (Exception ex) {
Logger.getLogger(LoginBacking.class.getName()).log(Level.SEVERE, null, ex);
result = "no";
}
}
return result;
}

public boolean tieneServicio(List<String> servicios) {


boolean result = false;
for (String string : servicios) {
if (string.contains("ProgramasDocentes")) {
result = true;
}
}
return result;
}
public void performLogout() throws IOException {
String logout = "";
try {
setCurrentUser(null);
HttpServletRequest request = (HttpServletRequest)
FacesContext.getCurrentInstance().getExternalContext().getRequest();
HttpServletResponse response = (HttpServletResponse)
FacesContext.getCurrentInstance().getExternalContext().getResponse();

Auth auth = new Auth(request, response);


logout = auth.logout("http://login.unnoba.edu.ar", null, null, true);

List<String> errors = auth.getErrors();


} catch (Exception ex) {
// Logger.getLogger(LoginBacking.class.getName()).log(Level.SEVERE, null, ex);
}
ExternalContext ec = FacesContext.getCurrentInstance().getExternalContext();
ec.redirect(logout);
}

public void performLogout2() throws IOException {


setCurrentUser(null);
ExternalContext ec = FacesContext.getCurrentInstance().getExternalContext();
ec.redirect("https://login.unnoba.edu.ar");
}

public void volverAlogin() throws IOException {


ExternalContext ec = FacesContext.getCurrentInstance().getExternalContext();
ec.redirect("https://login.unnoba.edu.ar");
}

AbstractBacking.java

borrar o comentar los siguientes metodos

isUserLoggedIn()
logMessage(String... messages)

template.xhtml

modificar donde se encuentra el botón de salir


<h:form>
<p:outputLabel style="margin-right: 10px" value="Usuario:
#{sessionScope.currentUser.docenteHumanized}"/>
<div style="display: inline-block; margin-top: 5px">
<p:commandButton style="margin-right: 10px" value="Volver a login"
action="#{loginBacking.volverAlogin}" icon="ui-icon-arrowthick-1-w"/>
<p:commandButton style="margin-right: 10px" value="Salir"
action="#{loginBacking.performLogout}" icon="ui-icon-close"/>
</div>

</h:form>

Cambiar #{loginBacking.userLoggedIn} por #{loginBacking.isUserLoggedIn() == 'si'}"


mirar si utiliza dos veces el render en esta parte, dejar solo el del if
<c:if test="#{loginBacking.isUserLoggedIn() == 'si'}">
<div id="datos_usuario" class="ui-widget"> Si aparece aca sacarlo
<ui:include src="menu.xhtml"></ui:include>
</div>
</c:if>
EN EL SERVIDOR DEL PROYECTO

Instalar open jdk y no open jre, no importa si estan las dos pero si o si tiene que estar la jdk

#sudo apt-get install openjdk-8-jdk

EN EL SERVIDOR OPENID

#cd /var/simplesamlphp/metadata
#nano saml20-sp-remote.php

En el archivo agregar
$metadata['http://192.168.16.31:8080/declaracion_jurada/metadata.jsp'] = array (
'AssertionConsumerService' => 'http://192.168.16.31:8080/declaracion_jurada/login.xhtml',
'SingleLogoutService' => 'http://192.168.16.31:8080/declaracion_jurada/logout.xhtml',
);

$metadata['http://ddjjviaticos.test.unnoba.edu.ar/metadata.jsp'] = array ( Reemplazar las urls


'AssertionConsumerService' => 'http://ddjjviaticos.test.unnoba.edu.ar/login.xhtml',
por las que correspondan
'SingleLogoutService' => 'http://ddjjviaticos.test.unnoba.edu.ar/logout.xhtml',
);

$metadata['https://ddjjviaticos.unnoba.edu.ar/metadata.jsp'] = array (
'AssertionConsumerService' => 'https://ddjjviaticos.unnoba.edu.ar/login.xhtml',
'SingleLogoutService' => 'https://ddjjviaticos.unnoba.edu.ar/logout.xhtml',
);

si existe algun problema de recursividad en los paths poner la direccion completa


'....:8080/declaracion_jurada/login.xhtml' (en producción no)

Potrebbero piacerti anche