package com.constellio.app.servlet; import java.io.IOException; import javax.servlet.ServletException; import javax.servlet.http.HttpServlet; import javax.servlet.http.HttpServletRequest; import javax.servlet.http.HttpServletResponse; import org.apache.commons.lang3.StringUtils; import org.joda.time.Duration; import com.constellio.app.services.factories.ConstellioFactories; import com.constellio.model.entities.security.global.UserCredential; import com.constellio.model.services.security.authentification.AuthenticationService; import com.constellio.model.services.users.UserServices; import com.constellio.model.services.users.UserServicesRuntimeException.UserServicesRuntimeException_NoSuchUser; public class ConstellioGenerateTokenWebServlet extends HttpServlet { private static final String USERNAME = "username"; private static final String PASSWORD = "password"; private static final String DURATION = "duration"; private static final String AS_USER = "asUser"; public static final String BAD_DURATION = "Bad Duration. Example : 14d or 24h"; public static final String PARAM_USERNAME_REQUIRED = "Parameter 'username' required"; public static final String PARAM_PASSWORD_REQUIRED = "Parameter 'password' required"; public static final String PARAM_DURATION_REQUIRED = "Parameter 'duration' required"; public static final String BAD_USERNAME_PASSWORD = "Bad username/password"; public static final String BAD_ASUSER = "Bad asUser value"; public static final String REQUIRE_ADMIN_RIGHTS = "asUser requires system admin rights"; @Override protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException { String username = req.getParameter(USERNAME); String password = req.getParameter(PASSWORD); String duration = req.getParameter(DURATION); String asUser = req.getParameter(AS_USER); if (StringUtils.isBlank(username)) { username = req.getHeader(USERNAME); } if (StringUtils.isBlank(password)) { password = req.getHeader(PASSWORD); } if (StringUtils.isBlank(duration)) { duration = req.getHeader(DURATION); } if (StringUtils.isBlank(asUser)) { asUser = req.getHeader(AS_USER); } if (StringUtils.isBlank(username)) { resp.getWriter().write(PARAM_USERNAME_REQUIRED); return; } if (StringUtils.isBlank(duration)) { resp.getWriter().write(PARAM_DURATION_REQUIRED); return; } if (StringUtils.isBlank(password)) { resp.getWriter().write(PARAM_PASSWORD_REQUIRED); return; } if (StringUtils.isBlank(asUser) || "null".equalsIgnoreCase(asUser)) { asUser = null; } int tokenDurationInHours = getTokenDurationInHours(duration); if (tokenDurationInHours <= 0) { resp.getWriter().write(BAD_DURATION); return; } UserServices userServices = ConstellioFactories.getInstance().getModelLayerFactory().newUserServices(); AuthenticationService authService = ConstellioFactories.getInstance().getModelLayerFactory().newAuthenticationService(); if (!authService.authenticate(username, password)) { resp.getWriter().write(BAD_USERNAME_PASSWORD); return; } UserCredential authentifiedUser = userServices.getUserCredential(username); UserCredential tokenForUser = authentifiedUser; if (asUser != null) { if (authentifiedUser.isSystemAdmin()) { try { tokenForUser = userServices.getUserCredential(asUser); if (tokenForUser == null) { throw new UserServicesRuntimeException_NoSuchUser(asUser); } } catch (UserServicesRuntimeException_NoSuchUser e) { resp.getWriter().write(BAD_ASUSER); return; } } else { resp.getWriter().write(REQUIRE_ADMIN_RIGHTS); return; } } if (tokenForUser.getServiceKey() == null) { tokenForUser = tokenForUser.withServiceKey("agent_" + tokenForUser.getUsername()); userServices.addUpdateUserCredential(tokenForUser); } String token = userServices.generateToken(tokenForUser.getUsername(), Duration.standardHours(tokenDurationInHours)); StringBuilder sb = new StringBuilder("<?xml version=\"1.0\" encoding=\"UTF-8\"?>"); sb.append("<response><serviceKey>"); sb.append(tokenForUser.getServiceKey()); sb.append("</serviceKey>"); sb.append("<token>"); sb.append(token); sb.append("</token></response>"); resp.setContentType("text/xml;charset=UTF-8"); resp.getWriter().write(sb.toString()); } private int getTokenDurationInHours(String duration) { try { int durationInHours; if (duration.endsWith("d") || duration.endsWith("j")) { int durationInDays = Integer.valueOf(duration.substring(0, duration.length() - 1)); durationInHours = durationInDays * 24; } else if (duration.endsWith("h")) { durationInHours = Integer.valueOf(duration.substring(0, duration.length() - 1)); } else { durationInHours = Integer.valueOf(duration); } return durationInHours; } catch (Exception e) { e.printStackTrace(); return 0; } } }