Java tutorial
/*************************************************************************** * Copyright (C) 2005 Global Biodiversity Information Facility Secretariat. * All Rights Reserved. * The contents of this file are subject to the Mozilla Public * License Version 1.1 (the "License"); you may not use this file * except in compliance with the License. You may obtain a copy of * the License at http://www.mozilla.org/MPL/ * Software distributed under the License is distributed on an "AS * IS" basis, WITHOUT WARRANTY OF ANY KIND, either express or * implied. See the License for the specific language governing * rights and limitations under the License. ***************************************************************************/ package org.gbif.portal.web.controller.registration; import org.gbif.portal.dto.KeyValueDTO; import org.gbif.portal.dto.resources.DataProviderDTO; import org.gbif.portal.dto.resources.DataResourceDTO; import org.gbif.portal.registration.ErrorMessageKeys; import org.gbif.portal.registration.LDAPUtils; import org.gbif.portal.registration.ResourceExtractionUtils; import org.gbif.portal.registration.UDDIUtils; import org.gbif.portal.registration.model.ProviderDetail; import org.gbif.portal.registration.model.ResourceDetail; import org.gbif.portal.registration.model.UserLogin; import org.gbif.portal.service.DataResourceManager; import org.gbif.portal.service.GeospatialManager; import org.gbif.portal.service.TaxonomyManager; import org.gbif.portal.util.mhf.message.Message; import org.gbif.portal.util.propertystore.PropertyStore; import org.gbif.portal.util.workflow.ProcessContext; import org.gbif.portal.util.workflow.Processor; import org.gbif.portal.web.util.DateUtil; import org.gbif.portal.web.util.PasswordUtils; import java.util.ArrayList; import java.util.Date; import java.util.Enumeration; import java.util.HashMap; import java.util.LinkedList; import java.util.List; import java.util.Locale; import java.util.Map; import java.util.StringTokenizer; import java.util.regex.Matcher; import java.util.regex.Pattern; import javax.naming.NamingException; import javax.servlet.http.HttpServletRequest; import javax.servlet.http.HttpServletResponse; import org.apache.commons.beanutils.PropertyUtils; import org.apache.commons.lang.StringUtils; import org.springframework.context.MessageSource; import org.springframework.mail.MailException; import org.springframework.mail.MailSender; import org.springframework.mail.SimpleMailMessage; import org.springframework.validation.BindingResult; import org.springframework.validation.Errors; import org.springframework.web.bind.ServletRequestDataBinder; import org.springframework.web.bind.ServletRequestUtils; import org.springframework.web.servlet.ModelAndView; import org.springframework.web.servlet.mvc.multiaction.MultiActionController; import org.springframework.web.servlet.mvc.multiaction.NoSuchRequestHandlingMethodException; import org.springframework.web.servlet.support.RequestContextUtils; import org.springframework.web.servlet.view.RedirectView; import org.uddi4j.UDDIException; import org.uddi4j.transport.TransportException; /** * The dispatcher controller for all provider updating activities for the * wizard to create or update a provider. * The user is capable of creating and editing data providers in uddi * Forms are pre-populated from the LDAP configuration, * * @author trobertson * @author dmartin */ public class RegistrationController extends MultiActionController { /** The request constants */ public static final String REQUEST_BUSINESS_UDDI_KEY = "businessKey"; public static final String REQUEST_CONTACT_TYPES = "contactTypes"; public static final String REQUEST_PROVIDER_DETAIL = "providerDetail"; public static final String REQUEST_COUNTRIES = "countries"; public static final String REQUEST_RESOURCE_NETWORKS = "resourceNetworks"; public static final String REQUEST_BASES_OF_RECORD = "basesOfRecord"; public static final String REQUEST_RESOURCE_URL = "resourceUrl"; public static final String REQUEST_RESOURCES = "resources"; public static final String REQUEST_RESOURCE = "resource"; public static final String REQUEST_SELECTED_CONCEPT = "selectedConcept"; public static final String REQUEST_DATA_PROVIDER = "dataProvider"; public static final String REQUEST_DATA_RESOURCE = "dataResource"; public static final String REQUEST_CONCEPTS = "concepts"; public static final String REQUEST_RESOURCE_TYPES = "resourceTypes"; /** The name of the admin role */ protected String adminRole = "Portal Admins"; /** MailSender */ protected MailSender mailSender; protected SimpleMailMessage userTemplateMessage; protected String usernamePostfix = ""; /** The LDAP URL */ protected String ldapUrl; /** Utils */ protected UDDIUtils uddiUtils; protected LDAPUtils ldapUtils; protected ResourceExtractionUtils resourceExtractionUtils; /** The property store */ protected PropertyStore propertyStore; /** Managers */ protected GeospatialManager geospatialManager; protected DataResourceManager dataResourceManager; protected TaxonomyManager taxonomyManager; /** the basis of records */ protected List<String> basisOfRecordTypes; /** the resource types supported */ protected List<String> resourceTypes; /** resource 2 namespace mappings */ protected Map<String, String> resourceType2namespaceList; /** Minimum username length */ protected int minimumUsernameLength = 6; /** Minimum password length */ protected int minimumPasswordLength = 6; public PasswordUtils passwordUtils = new PasswordUtils(); //protected String adminEmail = "portal@gbif.org"; protected String adminEmail = "oduque@humboldt.org.co"; /** Message source for i18n */ protected MessageSource messageSource; /** * Ajax entry point that adds the resource to provider */ @SuppressWarnings("unchecked") public ModelAndView addDataResource(HttpServletRequest request, HttpServletResponse response) throws Exception { logger.info("Adding a resource..."); debugRequestParams(request); ResourceDetail resourceDetail = new ResourceDetail(); ServletRequestDataBinder binder = createBinder(request, resourceDetail); binder.bind(request); BindingResult result = binder.getBindingResult(); validateDataResource(resourceDetail, result); logger.info("Adding the resource: " + resourceDetail.getName()); uddiUtils.updateResource(resourceDetail, request.getParameter("businessKey")); Map<String, Object> data = new HashMap<String, Object>(); data.put(REQUEST_RESOURCE, resourceDetail); data.putAll(referenceDataForResourceList(request)); return null; } /** * Setup page for a new data provider. When registering a new contact, these some details are pre-populated from LDAP * * @param request * @param response * @return * @throws Exception */ public ModelAndView addRegistrationLogins(HttpServletRequest request, HttpServletResponse response) throws Exception { String user = request.getParameter("user"); String email = request.getParameter("email"); // retrieve the user UserLogin userLogin = null; if (StringUtils.isNotEmpty(user)) { userLogin = ldapUtils.getUserLogin(user); } // if not found, try with email if (userLogin == null && StringUtils.isNotEmpty(email)) { List<UserLogin> userLogins = ldapUtils.getUsernamePasswordForEmail(email); if (userLogins.size() > 1 || userLogins.isEmpty()) { ModelAndView mav = new ModelAndView("registrationUserUpdate"); if (userLogins.isEmpty()) { mav.addObject("userNotFound", true); mav.addObject("user", user); mav.addObject("email", email); } else { mav.addObject("userLogins", userLogins); } return mav; } else { userLogin = userLogins.get(0); } } // if not found at all if (userLogin == null) { ModelAndView mav = new ModelAndView("registrationUserUpdate"); mav.addObject("userNotFound", true); mav.addObject("user", user); mav.addObject("email", email); return mav; } String username = getSystemUserName(userLogin.getUsername()); List<KeyValueDTO> providerList = uddiUtils.getProviderListAsKeyValues(); List<String> businessKeys = uddiUtils.getAssociatedBusinessKeys(username); List<KeyValueDTO> providerRegistrationLogins = new ArrayList<KeyValueDTO>(); for (KeyValueDTO providerKV : providerList) { if (businessKeys.contains(providerKV.getKey())) { providerRegistrationLogins.add(providerKV); } } // providerList.removeAll(providerRegistrationLogins); ModelAndView mav = new ModelAndView("registrationProviderList"); mav.addObject("providerList", providerList); mav.addObject("providerRegistrationLogins", providerRegistrationLogins); mav.addObject("userLogin", userLogin); mav.addObject("updateAction", "updateRegistrationLogins"); return mav; } /** * Updates details in UDDI for this dataset. * * @param request * @param response * @return * @throws Exception */ public ModelAndView completeManualRegistration(HttpServletRequest request, HttpServletResponse response) throws Exception { // bind to object ResourceDetail resource = new ResourceDetail(); ServletRequestDataBinder binder = createBinder(request, resource); initBinder(request, binder); binder.bind(request); BindingResult result = binder.getBindingResult(); validateDataResource(resource, result); logger.info("Adding the resource: " + resource.getName()); if (result.hasErrors()) { logger.info("Errors have occurred: " + result); Map<String, Object> data = new HashMap<String, Object>(); data.put(REQUEST_RESOURCE, resource); data.putAll(referenceDataForResourceList(request)); data.put(BindingResult.MODEL_KEY_PREFIX + RegistrationController.REQUEST_RESOURCE, result); data.put("editableEndpoint", true); // put the errors in the request return new ModelAndView("registrationResourceManual", data); } else { String businessKey = request.getParameter("businessKey"); uddiUtils.updateResource(resource, businessKey); return new ModelAndView(new RedirectView( request.getContextPath() + "/register/showDataResources?businessKey=" + businessKey)); } } /** * Issues a metadata request to the provider */ @SuppressWarnings("unchecked") protected List<ResourceDetail> contactProviderForMetadata(String url) { logger.debug("Contacting provider for metadata"); if (resourceType2namespaceList != null) { for (String resourceType : resourceType2namespaceList.keySet()) { // retrieve the namespace String namespace = resourceType2namespaceList.get(resourceType); try { // this is geared to DiGIR only Processor workflow = (Processor) propertyStore.getProperty(namespace, "REGISTRATION.METADATA.WORKFLOW", Processor.class); Map<String, Object> seedData = new HashMap<String, Object>(); seedData.put("url", url); List<String> namespaces = new LinkedList<String>(); namespaces.add(namespace); seedData.put("psNamespaces", namespaces); ProcessContext context = workflow.doActivities(seedData); Message message = (Message) context.get("responseMessage", Message.class, true); List<ResourceDetail> resources = resourceExtractionUtils.getResourcesFromMetadata(namespaces, message); if (resources != null && !resources.isEmpty()) { for (ResourceDetail resourceDetail : resources) resourceDetail.setResourceType(resourceType); return resources; } } catch (Exception e) { logger.error(e.getMessage(), e); } } } return new LinkedList<ResourceDetail>(); } /** * Debug request parameters. * * @param request */ @SuppressWarnings("unchecked") private void debugRequestParams(HttpServletRequest request) { Map<String, Object> params = request.getParameterMap(); for (String key : params.keySet()) { Object param = params.get(key); if (param instanceof String[]) { for (int i = 0; i < ((String[]) param).length; i++) { logger.info(key + "[" + i + "]: " + ((String[]) param)[i]); } } else { logger.info(key + ": " + 1); } } } /** * Enables a user to find a provider and request access to provider details. * * @param request * @param response * @return * @throws Exception */ public ModelAndView findDataProvider(HttpServletRequest request, HttpServletResponse response) throws Exception { List<KeyValueDTO> providerList = uddiUtils.getProviderListAsKeyValues(); List<String> businessKeys = uddiUtils.getAssociatedBusinessKeys(request.getRemoteUser()); List<KeyValueDTO> providerRegistrationLogins = new ArrayList<KeyValueDTO>(); List<KeyValueDTO> toRemove = new ArrayList<KeyValueDTO>(); for (KeyValueDTO providerKV : providerList) { if (businessKeys.contains(providerKV.getKey())) { providerRegistrationLogins.add(providerKV); toRemove.add(providerKV); } } // remove the ones already accessible providerList.removeAll(toRemove); // view this of providers ModelAndView mav = new ModelAndView("registrationProviderList"); mav.addObject("providerList", providerList); mav.addObject("providerRegistrationLogins", providerRegistrationLogins); // if user is admin, not need to send requests if (request.isUserInRole(adminRole)) { mav.addObject("updateAction", "updateRegistrationLogins"); } else { mav.addObject("updateAction", "sendRegistrationLoginsRequest"); } return mav; } // public static void main(String[] args){ // RegistrationController rc = new RegistrationController(); // System.out.println(rc.validateUsername("dmartin")); // System.out.println(rc.validateUsername("dmartin::")); // System.out.println(rc.validateUsername("dmartin123")); // } /** * Forgotten password. * * @param request * @param response * @return * @throws Exception */ public ModelAndView forgottenPassword(HttpServletRequest request, HttpServletResponse response) throws Exception { if (!isFormSubmission(request)) { ModelAndView mav = new ModelAndView("forgottenPassword"); return mav; } String email = request.getParameter("email"); List<UserLogin> uls = ldapUtils.getUsernamePasswordForEmail(email); if (uls.isEmpty()) { ModelAndView mav = new ModelAndView("forgottenPassword"); mav.addObject("email", email); mav.addObject("unrecognised", true); return mav; } for (UserLogin ul : uls) { // reset password String newPassword = generatePassword(ul.getUsername()); ul.setPassword(newPassword); ldapUtils.updateUser(ul); // send verification email SimpleMailMessage verificationMessage = new SimpleMailMessage(userTemplateMessage); verificationMessage.setTo(email); String encryptedPassword = passwordUtils.encryptPassword(ul.getPassword(), true); verificationMessage.setSubject("Details for GBIF Data Portal"); verificationMessage.setText("Please click here to login:\n\n" + "http://" + request.getHeader("host") + request.getContextPath() + "/register/" + "?u=" + ul.getUsername() + "&p=" + encryptedPassword + "\n\nUsername: " + ul.getUsername() + "\nPassword: " + ul.getPassword()); try { mailSender.send(verificationMessage); } catch (MailException e) { // simply log it and go on... logger.error("Couldn't send message", e); ModelAndView mav = new ModelAndView("emailDetailsFailureView"); mav.addObject("email", email); return mav; } } ModelAndView mav = new ModelAndView("emailDetailsSuccessView"); mav.addObject("email", email); return mav; } /** * Generates a password for a reset password. * * @param userName * @return */ public String generatePassword(String userName) { String password = userName + passwordUtils.getEncryptKey() + System.currentTimeMillis(); int hashCode = password.hashCode(); return Integer.toHexString(hashCode); } // public static void main(String[] args){ // try { // String encrypted = encryptPassword("pass%^&word__++1231:!!@$", true); // System.out.println("Enter encryption password: "+encrypted); // String decrypted = encryptPassword(encrypted, false); // System.out.println("Enter decryption password: "+decrypted); // } catch (Exception e) { // // TODO Auto-generated catch block // e.printStackTrace(); // } // } // public static String decryptPassword(String password) throws Exception{ // java.security.MessageDigest d =null; // d = java.security.MessageDigest.getInstance("SHA-1"); // d.reset(); // d.update(password.getBytes()); // return PasswordUtils.byteArrayToHexString(d.digest()); // } /** * Searches through the parameters in the request to find the highest index of the given * property. * * @see http://forum.springframework.org/showthread.php?t=19976 * @param request The request * @param property The given property to search for * @return The maximum index for the given property, or -1 if the property is not indexed */ protected final int getMaxIndex(HttpServletRequest request, String property) { int maxIndex = -1; for (Enumeration parameters = request.getParameterNames(); parameters.hasMoreElements();) { String parameterName = (String) parameters.nextElement(); if (parameterName.startsWith(property)) { int startIndex = parameterName.indexOf("["); int endIndex = parameterName.indexOf("]"); if ((startIndex == -1) || (endIndex == -1)) { logger.error("Non-indexed property - " + property); return (-1); } int index = Integer.parseInt(parameterName.substring((startIndex + 1), endIndex)); if (index > maxIndex) { maxIndex = index; } } } return (maxIndex); } /** * @return Returns the resourceExtractionUtils. */ public ResourceExtractionUtils getResourceExtractionUtils() { return resourceExtractionUtils; } /** * @param username * @return */ private String getSystemUserName(String username) { if (StringUtils.isNotEmpty(usernamePostfix)) { return username + usernamePostfix; } return username; } /** * @see org.springframework.web.servlet.mvc.multiaction.MultiActionController#handleNoSuchRequestHandlingMethod(org.springframework.web.servlet.mvc.multiaction.NoSuchRequestHandlingMethodException, * javax.servlet.http.HttpServletRequest, javax.servlet.http.HttpServletResponse) */ @Override protected ModelAndView handleNoSuchRequestHandlingMethod(NoSuchRequestHandlingMethodException exception, HttpServletRequest request, HttpServletResponse response) throws Exception { if (StringUtils.isEmpty(exception.getMethodName())) { return viewAdminMenu(request, response); } return super.handleNoSuchRequestHandlingMethod(exception, request, response); } /** * Because the page can dynamically add more Secondary contacts, ensure that the contacts list in the command object * is of sufficient size to handle it. * * @see org.springframework.web.servlet.mvc.BaseCommandController#initBinder(javax.servlet.http.HttpServletRequest, * org.springframework.web.bind.ServletRequestDataBinder) */ @Override protected void initBinder(HttpServletRequest request, ServletRequestDataBinder binder) throws Exception { if (binder.getTarget() instanceof ProviderDetail) { initProviderBinder(request, binder); } else if (binder.getTarget() instanceof ResourceDetail) { initResourceDetailBinder(request, binder); } } /** * Initialises the binder for a provider * This handles the resizing of the secondary contacts and resources */ protected void initProviderBinder(HttpServletRequest request, ServletRequestDataBinder binder) throws Exception { ProviderDetail providerDetail = (ProviderDetail) binder.getTarget(); logger.info("Checking to see if the contacts list needs padded"); int maxSecondaryIndex = getMaxIndex(request, "businessSecondaryContacts"); logger.info("maxSecondaryIndex: " + maxSecondaryIndex); int currentSize = providerDetail.getBusinessSecondaryContacts().size(); logger.info("currentSize: " + currentSize); if (maxSecondaryIndex + 1 > currentSize) { for (int i = 0; i < (maxSecondaryIndex + 1 - currentSize); i++) { logger.info("creating a padded contact"); providerDetail.getBusinessSecondaryContacts().add(providerDetail.new Contact()); } } else if (maxSecondaryIndex + 1 < currentSize) { // shrink it if it's a submit - e.g contacts deleted if (isFormSubmission(request)) { logger.info("shrinking"); providerDetail.setBusinessSecondaryContacts( providerDetail.getBusinessSecondaryContacts().subList(0, maxSecondaryIndex + 1)); } } logger.info("Checking to see if the resource list needs padded"); int maxResourceIndex = getMaxIndex(request, "businessResources"); logger.info("maxResourceIndex: " + maxResourceIndex); currentSize = providerDetail.getBusinessResources().size(); logger.info("currentSize: " + currentSize); if (maxResourceIndex + 1 > currentSize) { for (int i = 0; i < (maxResourceIndex + 1 - currentSize); i++) { logger.info("creating a padded resource"); providerDetail.getBusinessResources().add(new ResourceDetail()); } } else if (maxResourceIndex + 1 < currentSize) { // shrink it if it's a submit - e.g contacts deleted if (isFormSubmission(request)) { logger.info("shrinking"); providerDetail.setBusinessResources( providerDetail.getBusinessResources().subList(0, maxResourceIndex + 1)); } } } /** * Initialises the binder for a provider * This handles the resizing of the secondary contacts and resources */ protected void initResourceDetailBinder(HttpServletRequest request, ServletRequestDataBinder binder) throws Exception { ResourceDetail resourceDetail = (ResourceDetail) binder.getTarget(); String relatesToCountries = request.getParameter("relatesToCountries"); if (StringUtils.isNotEmpty(relatesToCountries)) { ArrayList<String> relatesToCountriesList = new ArrayList<String>(); StringTokenizer st = new StringTokenizer(relatesToCountries, ","); while (st.hasMoreTokens()) { String iso = st.nextToken(); if (iso != null && iso.length() > 0) relatesToCountriesList.add(iso); } resourceDetail.setRelatesToCountries(relatesToCountriesList); } // check for N/A values Date startDate = DateUtil.getDateFromRequest(request, "startDate"); Date endDate = DateUtil.getDateFromRequest(request, "endDate"); resourceDetail.setStartDate(startDate); resourceDetail.setEndDate(endDate); // set N/A values to null if ("N/A".equals(resourceDetail.getRecordBasis())) resourceDetail.setRecordBasis(null); if ("N/A".equals(resourceDetail.getOwnerCountry())) resourceDetail.setOwnerCountry(null); if ("N/A".equals(resourceDetail.getIndexingStartTime())) resourceDetail.setIndexingStartTime(null); if ("N/A".equals(resourceDetail.getIndexingFrequency())) resourceDetail.setIndexingFrequency(null); if ("N/A".equals(resourceDetail.getIndexingMaxDuration())) resourceDetail.setIndexingMaxDuration(null); } /** * Determines if the request is a submission or not * * @param request TO test * @return true if it is a POST, otherwise false */ protected boolean isFormSubmission(HttpServletRequest request) { return "POST".equals(request.getMethod()); } /** * AJAX entry point to dynamically call the provider with a metadata request */ public ModelAndView issueMetadataRequest(HttpServletRequest request, HttpServletResponse response) throws Exception { ProviderDetail provider = retrieveProviderFromUDDI(request); Map<String, Object> data = new HashMap<String, Object>(); if (StringUtils.isNotEmpty(request.getParameter(REQUEST_RESOURCE_URL))) { List<ResourceDetail> resources = contactProviderForMetadata(request.getParameter(REQUEST_RESOURCE_URL)); replaceKnownResourcesWithUDDICopy(provider, resources); data.put(REQUEST_RESOURCES, resources); } data.putAll(referenceDataForResourceList(request)); return new ModelAndView("registrationMetadataResourceList", data); } /** * Log the current user out. * * @param request * @param response * @return * @throws Exception */ public ModelAndView logoutUser(HttpServletRequest request, HttpServletResponse response) throws Exception { request.getSession().invalidate(); return new ModelAndView(new RedirectView(request.getContextPath() + "/register/")); } /** * Display a form for fully manual resource registration. */ public ModelAndView manuallyRegisterResource(HttpServletRequest request, HttpServletResponse response) throws Exception { logger.debug("Entering the register data resources page"); Map<String, Object> data = new HashMap<String, Object>(); ProviderDetail provider = retrieveProviderFromUDDI(request); if (provider == null) { return new ModelAndView("registrationBadBusinessKey"); } logger.debug("Provider has resource count: " + provider.getBusinessResources().size()); ResourceDetail resourceDetail = new ResourceDetail(); // set the resource type if passed as param String resourceType = request.getParameter("ResourceType"); resourceDetail.setResourceType(resourceType); data.put(REQUEST_RESOURCE, resourceDetail); data.put("editableEndpoint", true); data.put(RegistrationController.REQUEST_PROVIDER_DETAIL, provider); data.putAll(referenceDataForResourceList(request)); return new ModelAndView("registrationResourceManual", data); } /** * Create a new user in LDAP. * * @param request * @param response * @return * @throws Exception */ public ModelAndView newUser(HttpServletRequest request, HttpServletResponse response) throws Exception { if (!isFormSubmission(request)) { ModelAndView mav = new ModelAndView("newUser"); UserLogin ul = new UserLogin(); mav.addObject("user", ul); return mav; } UserLogin ul = new UserLogin(); ServletRequestDataBinder binder = createBinder(request, ul); binder.bind(request); BindingResult result = binder.getBindingResult(); String systemUserName = getSystemUserName(ul.getUsername()); String suggestedUsername = null; // validate if (StringUtils.isEmpty(ul.getUsername())) { result.rejectValue("username", ErrorMessageKeys.MUST_BE_SPECIFIED); } else if (ul.getUsername().length() < minimumUsernameLength) { result.rejectValue("username", ErrorMessageKeys.MUST_BE_MINIMIUM_LENGTH); } else if (!validateUsername(ul.getUsername())) { result.rejectValue("username", ErrorMessageKeys.CONTAINS_INVALID_CHARS); } else if (ldapUtils.userNameInUse(systemUserName)) { // iterate until a username available for (int i = 0; i < Integer.MAX_VALUE; i++) { suggestedUsername = getSystemUserName(ul.getUsername() + i); if (!ldapUtils.userNameInUse(suggestedUsername)) { break; } } result.rejectValue("username", ErrorMessageKeys.USERNAME_IN_USE); } if (StringUtils.isEmpty(ul.getFirstName())) { result.rejectValue("firstName", ErrorMessageKeys.MUST_BE_SPECIFIED); } if (StringUtils.isEmpty(ul.getSurname())) { result.rejectValue("surname", ErrorMessageKeys.MUST_BE_SPECIFIED); } if (!StringUtils.isEmpty(ul.getEmail())) { Pattern p = Pattern.compile(".+@.+\\.[a-z]+"); Matcher m = p.matcher(ul.getEmail()); boolean validEmail = m.matches(); if (!validEmail) result.rejectValue("email", ErrorMessageKeys.INVALID_VALUE); } else { result.rejectValue("email", ErrorMessageKeys.MUST_BE_SPECIFIED); } if (StringUtils.isEmpty(ul.getPassword())) { result.rejectValue("password", ErrorMessageKeys.MUST_BE_SPECIFIED); } else if (!validatePassword(ul.getPassword())) { result.rejectValue("password", ErrorMessageKeys.MUST_BE_MINIMIUM_LENGTH); } if (result.hasErrors()) { ModelAndView mav = new ModelAndView("newUser"); if (suggestedUsername != null) { mav.addObject("suggestedUsername", suggestedUsername); } mav.addObject(BindingResult.MODEL_KEY_PREFIX + "user", result); return mav; } // send verification email SimpleMailMessage verificationMessage = new SimpleMailMessage(userTemplateMessage); verificationMessage.setTo(ul.getEmail()); String encryptedPassword = passwordUtils.encryptPassword(ul.getPassword(), true); verificationMessage.setSubject("Confirm e-mail address for GBIF Data Portal"); verificationMessage.setText("Please visit the following link to confirm your e-mail address:\n\n" + "http://" + request.getHeader("host") + request.getContextPath() + "/user/verification" + "?fn=" + ul.getFirstName() + "&sn=" + ul.getSurname() + "&e=" + ul.getEmail() + "&u=" + ul.getUsername() + "&p=" + encryptedPassword); try { mailSender.send(verificationMessage); } catch (MailException e) { // simply log it and go on... logger.error("Couldn't send message", e); ModelAndView mav = new ModelAndView("registrationVerificationFailureView"); mav.addObject("user", ul); return mav; } // successful ModelAndView mav = new ModelAndView("registrationVerificationSuccessView"); mav.addObject("user", ul); return mav; } /** * Populates the ReferenceData for the provider page */ protected Map<String, Object> referenceDataForProvider(HttpServletRequest request) throws Exception { Map<String, Object> data = new HashMap<String, Object>(); data.put(RegistrationController.REQUEST_CONTACT_TYPES, ProviderDetail.ContactTypes.values()); data.put(RegistrationController.REQUEST_COUNTRIES, geospatialManager.findAllCountries(request.getLocale()).getResults()); return data; } /** * Populates the ReferenceData for the resource list page */ protected Map<String, Object> referenceDataForResource(HttpServletRequest request, ResourceDetail resourceDetail) throws Exception { Map<String, Object> data = new HashMap<String, Object>(); Locale locale = RequestContextUtils.getLocale(request); DataProviderDTO nubProvider = dataResourceManager.getNubDataProvider(); DataResourceDTO dataResourceDTO = null; List<DataResourceDTO> resourceDTOs = dataResourceManager.getDataResourcesForProvider(nubProvider.getKey()); if (resourceDTOs != null && !resourceDTOs.isEmpty()) dataResourceDTO = resourceDTOs.get(0); data.put(RegistrationController.REQUEST_BASES_OF_RECORD, basisOfRecordTypes); data.put(RegistrationController.REQUEST_RESOURCE_NETWORKS, dataResourceManager.getResourceNetworkList()); data.put(RegistrationController.REQUEST_COUNTRIES, geospatialManager.findAllCountries(locale).getResults()); data.put(RegistrationController.REQUEST_DATA_PROVIDER, nubProvider); data.put(RegistrationController.REQUEST_DATA_RESOURCE, dataResourceDTO); data.put(RegistrationController.REQUEST_RESOURCE_TYPES, resourceTypes); data.put("messageSource", messageSource); if (StringUtils.isNotEmpty(resourceDetail.getHighestTaxaConceptId())) { data.put(RegistrationController.REQUEST_CONCEPTS, taxonomyManager .getClassificationFor(resourceDetail.getHighestTaxaConceptId(), true, null, true)); data.put(RegistrationController.REQUEST_SELECTED_CONCEPT, taxonomyManager.getTaxonConceptFor(resourceDetail.getHighestTaxaConceptId())); } else { data.put(RegistrationController.REQUEST_CONCEPTS, taxonomyManager .getRootTaxonConceptsForTaxonomy(nubProvider.getKey(), dataResourceDTO.getKey())); } return data; } /** * Populates the ReferenceData for the resource list page */ protected Map<String, Object> referenceDataForResourceList(HttpServletRequest request) throws Exception { return referenceDataForResourceList(request, null); } /** * Populates the ReferenceData for the resource list page */ protected Map<String, Object> referenceDataForResourceList(HttpServletRequest request, ProviderDetail providerDetail) throws Exception { Map<String, Object> data = new HashMap<String, Object>(); Locale locale = RequestContextUtils.getLocale(request); DataProviderDTO nubProvider = dataResourceManager.getNubDataProvider(); DataResourceDTO dataResourceDTO = null; List<DataResourceDTO> resourceDTOs = dataResourceManager.getDataResourcesForProvider(nubProvider.getKey()); if (resourceDTOs != null && !resourceDTOs.isEmpty()) dataResourceDTO = resourceDTOs.get(0); data.put(RegistrationController.REQUEST_BASES_OF_RECORD, basisOfRecordTypes); data.put(RegistrationController.REQUEST_RESOURCE_NETWORKS, dataResourceManager.getResourceNetworkList()); data.put(RegistrationController.REQUEST_COUNTRIES, geospatialManager.findAllCountries(locale).getResults()); data.put(RegistrationController.REQUEST_DATA_PROVIDER, nubProvider); data.put(RegistrationController.REQUEST_DATA_RESOURCE, dataResourceDTO); data.put(RegistrationController.REQUEST_RESOURCE_TYPES, resourceTypes); data.put(RegistrationController.REQUEST_CONCEPTS, taxonomyManager.getRootTaxonConceptsForTaxonomy(nubProvider.getKey(), dataResourceDTO.getKey())); data.put("messageSource", messageSource); return data; } /** * Refreshes the details for the supplied dataset using the latest available for its metadata * request. * * @return */ public ModelAndView refreshMetadataDetails(HttpServletRequest request, HttpServletResponse response) throws Exception { // get the provider from UDDI if necessary ProviderDetail provider = retrieveProviderFromUDDI(request); if (provider == null) { return new ModelAndView("registrationBadBusinessKey"); } // retrieve resource details ResourceDetail resource = retrieveDataResource(request, provider); // retrieve resources from access point List<ResourceDetail> resources = null; try { resources = contactProviderForMetadata(resource.getAccessPoint()); } catch (Exception e) { logger.error(e.getMessage(), e); ModelAndView mav = new ModelAndView("refreshMetadataFailure"); mav.addObject("resource", resource); return mav; } ResourceDetail metadataResource = null; if (resources.size() == 1) { logger.debug("Only one resource found at end point. Assuming same resource."); metadataResource = resources.get(0); } else { // use name to retrieve the properties for (ResourceDetail retrievedResource : resources) { if (resource.getName().equals(retrievedResource.getName())) { metadataResource = retrievedResource; break; } } } // store the updated properties List<String> updatedProperties = new ArrayList<String>(); // find the list of metadata supplied properties List<String> readonlyProperties = null; boolean refreshFailure = false; // if not null, update properties available from metadata if (metadataResource != null) { readonlyProperties = retrieveReadonlyPropertiesForResource(metadataResource); for (String readonlyProperty : readonlyProperties) { Object newValue = PropertyUtils.getProperty(metadataResource, readonlyProperty); Object oldValue = PropertyUtils.getProperty(resource, readonlyProperty); if (newValue != null && !newValue.equals(oldValue)) { PropertyUtils.setProperty(resource, readonlyProperty, newValue); updatedProperties.add(readonlyProperty); } } } else { refreshFailure = true; } // uddiUtils.updateResource(resource, provider.getBusinessKey()); ModelAndView mav = new ModelAndView("registrationResourceDetail"); mav.addAllObjects(referenceDataForResource(request, resource)); mav.addObject(RegistrationController.REQUEST_PROVIDER_DETAIL, provider); mav.addObject(RegistrationController.REQUEST_RESOURCE, resource); mav.addObject("readonlyProperties", readonlyProperties); mav.addObject("updatedProperties", updatedProperties); mav.addObject("refreshFailure", refreshFailure); mav.addObject("metadataRefresh", true); return mav; } /** * Setup page for a new data provider. When registering a new contact, some details are prepopulated from LDAP. * * @param request * @param response * @return * @throws Exception */ public ModelAndView registerDataProvider(HttpServletRequest request, HttpServletResponse response) throws Exception { // get the authenticated user from LDAP UserLogin userLogin = ldapUtils.getUserLogin(request.getRemoteUser()); // get the provider from UDDI if necessary ProviderDetail detail = new ProviderDetail(); // these are prepopulated from LDAP detail.getBusinessPrimaryContact().setName(userLogin.getUsername()); detail.getBusinessPrimaryContact().setPhone(userLogin.getTelephone()); detail.getBusinessPrimaryContact().setEmail(userLogin.getEmail()); Map<String, Object> data = new HashMap<String, Object>(); data.putAll(referenceDataForProvider(request)); data.put(RegistrationController.REQUEST_PROVIDER_DETAIL, detail); ModelAndView mav = new ModelAndView("registrationUpdateProviderDetail", data); return mav; } /** * Populates the page model for the resources within the provider given */ public ModelAndView registerDataResources(HttpServletRequest request, HttpServletResponse response) throws Exception { logger.debug("Entering the register data resources page"); Map<String, Object> data = new HashMap<String, Object>(); ProviderDetail provider = retrieveProviderFromUDDI(request); if (provider == null) { return new ModelAndView("registrationBadBusinessKey"); } List<ResourceDetail> resources = null; logger.debug("Provider has resource count: " + provider.getBusinessResources().size()); data.put(RegistrationController.REQUEST_PROVIDER_DETAIL, provider); if (StringUtils.isNotEmpty(request.getParameter(REQUEST_RESOURCE_URL))) { // retrieve resource list from provider resources = contactProviderForMetadata(request.getParameter(REQUEST_RESOURCE_URL)); replaceKnownResourcesWithUDDICopy(provider, resources); data.put(REQUEST_RESOURCES, resources); } ModelAndView mav = new ModelAndView("registrationResourceLookup", data); // add readonly settings if (resources != null && resources.size() > 0) { ResourceDetail rd = resources.get(0); String namespace = resourceType2namespaceList.get(rd.getResourceType()); List<String> namespaces = new ArrayList<String>(); namespaces.add(namespace); mav.addObject("readonlyProperties", resourceExtractionUtils.getMappedBeanPropertiesForNamespace(namespaces)); } data.putAll(referenceDataForResourceList(request)); mav.addObject(REQUEST_RESOURCE_TYPES, resourceTypes); mav.addAllObjects(data); return mav; } /** * Sets the guid on any resource that appears to be already in the provider * this uses the name only... should be enough... hmmm */ protected void replaceKnownResourcesWithUDDICopy(ProviderDetail provider, List<ResourceDetail> resources) { // put all known resources into a map Map<String, ResourceDetail> resourcesByNames = new HashMap<String, ResourceDetail>(); for (ResourceDetail resource : resources) { resourcesByNames.put(resource.getName(), resource); } // replace any retrieved from request with the UDDI copy for (ResourceDetail resource : provider.getBusinessResources()) { if (resourcesByNames.containsKey(resource.getName())) { ResourceDetail rd = resourcesByNames.get(resource.getName()); int position = resources.indexOf(rd); if (position >= 0) { resources.remove(rd); // replace with UUDI version resources.add(position, resource); } } } } /** * Create a new user in LDAP. * * @param request * @param response * @return * @throws Exception */ public ModelAndView resetPassword(HttpServletRequest request, HttpServletResponse response) throws Exception { if (!isFormSubmission(request)) { return new ModelAndView("resetPassword"); } String password = request.getParameter("password"); if (!validatePassword(password)) { ModelAndView mav = new ModelAndView("resetPassword"); mav.addObject("password", password); mav.addObject("invalidPassword", true); return mav; } String remoteUser = request.getRemoteUser(); ldapUtils.updatePassword(remoteUser, password); return new ModelAndView("passwordReset"); } /** * Retrieve the data resource for the provided serviceKey * * @param request * @param provider * @return */ private ResourceDetail retrieveDataResource(HttpServletRequest request, ProviderDetail provider) { String serviceKey = request.getParameter("serviceKey"); List<ResourceDetail> resources = provider.getBusinessResources(); ResourceDetail resource = null; for (ResourceDetail res : resources) { if (res.getServiceKey().equals(serviceKey)) { resource = res; break; } } return resource; } /** * Retrieve the provider for this request from UDDI. Returns null in case of bad key. * * @param request * @return * @throws NamingException * @throws UDDIException * @throws TransportException */ private ProviderDetail retrieveProviderFromUDDI(HttpServletRequest request) { ProviderDetail provider = null; String key = request.getParameter(REQUEST_BUSINESS_UDDI_KEY); // get the authenticated user from LDAP try { // need to cache these LDAP details for speed UserLogin userLogin = ldapUtils.getUserLogin(request.getRemoteUser()); if (StringUtils.isNotEmpty(key)) { provider = uddiUtils.createProviderFromUDDI(key, userLogin.getUsername()); } } catch (Exception e) { logger.error(e.getMessage(), e); } return provider; } /** * Retrieves a list of properties that are readonly (i.e. available from metadata) for this resource. * * @param resource * @return */ private List<String> retrieveReadonlyPropertiesForResource(ResourceDetail resource) { if (resource.getResourceType() != null) { String namespace = resourceType2namespaceList.get(resource.getResourceType()); List<String> namespaces = new ArrayList<String>(); namespaces.add(namespace); return resourceExtractionUtils.getMappedBeanPropertiesForNamespace(namespaces); } return new ArrayList<String>(); } /** * Populates the page model for the resources within the provider given */ public ModelAndView retrieveRegisteredDataResources(HttpServletRequest request, HttpServletResponse response, ProviderDetail provider) throws Exception { logger.debug("Entering the resources page"); Map<String, Object> data = new HashMap<String, Object>(); if (logger.isDebugEnabled()) { logger.debug("Provider: " + provider); logger.debug("Provider has resource count: " + provider.getBusinessResources().size()); } data.put(REQUEST_PROVIDER_DETAIL, provider); if (StringUtils.isNotEmpty(request.getParameter(REQUEST_RESOURCE_URL))) { // retrieve resource list from provider List<ResourceDetail> resources = contactProviderForMetadata(request.getParameter(REQUEST_RESOURCE_URL)); replaceKnownResourcesWithUDDICopy(provider, resources); data.put(REQUEST_RESOURCES, resources); } data.putAll(referenceDataForResourceList(request, provider)); return new ModelAndView("registrationResourceList", data); } /** * Admin task to review a users request to see details. * * @param request * @param response * @return * @throws Exception */ public ModelAndView reviewUserRequest(HttpServletRequest request, HttpServletResponse response) throws Exception { ModelAndView mav = new ModelAndView("approveProviderListView"); String user = request.getParameter("u"); UserLogin ul = ldapUtils.getUserLogin(user); String[] requestedKeys = request.getParameterValues("r"); List<String> requestedKeysList = new ArrayList<String>(); for (String value : requestedKeys) { requestedKeysList.add(value); } // retrieve the providers this user currently has access to List<String> existingKeys = uddiUtils.getAssociatedBusinessKeys(user); // construct the list of providers to approve List<KeyValueDTO> pvs = uddiUtils.getProviderListAsKeyValues(); List<KeyValueDTO> providersToApprove = new ArrayList<KeyValueDTO>(); List<KeyValueDTO> existingLogins = new ArrayList<KeyValueDTO>(); for (KeyValueDTO pv : pvs) { if (existingKeys.contains(pv.getKey())) existingLogins.add(pv); else if (requestedKeysList.contains(pv.getKey())) providersToApprove.add(pv); } mav.addObject("providerRegistrationLogins", existingLogins); mav.addObject("providersToApprove", providersToApprove); mav.addObject("user", ul); return mav; } /** * This will send an email for approval to portal@gbif.org to ask if someone can see a providers details * * @param request * @param response * @return * @throws Exception */ public ModelAndView sendRegistrationLoginsRequest(HttpServletRequest request, HttpServletResponse response) throws Exception { String user = request.getParameter("user"); if (StringUtils.isEmpty(user)) { user = request.getRemoteUser(); } UserLogin ul = ldapUtils.getUserLogin(user); String[] businessKeysToRemove = request.getParameterValues("businessKeyToRemove"); List<String> existingKeys = uddiUtils.getAssociatedBusinessKeys(user); // remove the selected registration logins if (businessKeysToRemove != null) { for (String element : businessKeysToRemove) { if (existingKeys.contains(element)) uddiUtils.deleteRegistrationLogin(user, element); } } // send approval email String[] businessKeys = request.getParameterValues(REQUEST_BUSINESS_UDDI_KEY); // if not businesskeys selected, non requested return to menu if (businessKeys == null) { return new ModelAndView(new RedirectView(request.getContextPath() + "/register/")); } // send verification email SimpleMailMessage verificationMessage = new SimpleMailMessage(userTemplateMessage); verificationMessage.setTo(adminEmail); verificationMessage.setSubject("User has requested access to Provider Details"); StringBuffer sb = new StringBuffer("Please click here to review request:\n\n"); sb.append("http://"); sb.append(request.getHeader("host")); sb.append(request.getContextPath()); sb.append("/register/reviewUserRequest"); sb.append("?u=" + user); for (String businessKey : businessKeys) { sb.append("&r="); sb.append(businessKey); } verificationMessage.setText(sb.toString()); try { mailSender.send(verificationMessage); } catch (MailException e) { // simply log it and go on... logger.error("Couldn't send message", e); ModelAndView mav = new ModelAndView("emailDetailsFailureView"); return mav; } // request sent view ModelAndView mav = new ModelAndView("requestSentView"); mav.addObject("userLogin", ul); return mav; } /** * @param adminEmail the adminEmail to set */ public void setAdminEmail(String adminEmail) { this.adminEmail = adminEmail; } /** * @param adminRole the adminRole to set */ public void setAdminRole(String adminRole) { this.adminRole = adminRole; } /** * @param basisOfRecordTypes the basisOfRecordTypes to set */ public void setBasisOfRecordTypes(List<String> basisOfRecordTypes) { this.basisOfRecordTypes = basisOfRecordTypes; } /** * @param dataResourceManager The dataResourceManager to set. */ public void setDataResourceManager(DataResourceManager dataResourceManager) { this.dataResourceManager = dataResourceManager; } /** * @param geospatialManager The geospatialManager to set. */ public void setGeospatialManager(GeospatialManager geospatialManager) { this.geospatialManager = geospatialManager; } /** * @param ldapUrl The ldapUrl to set. */ public void setLdapUrl(String ldapUrl) { this.ldapUrl = ldapUrl; } /** * @param ldapUtils The ldapUtils to set. */ public void setLdapUtils(LDAPUtils ldapUtils) { this.ldapUtils = ldapUtils; } /** * @param mailSender the mailSender to set */ public void setMailSender(MailSender mailSender) { this.mailSender = mailSender; } /** * @param messageSource the messageSource to set */ public void setMessageSource(MessageSource messageSource) { this.messageSource = messageSource; } /** * @param minimumPasswordLength the minimumPasswordLength to set */ public void setMinimumPasswordLength(int minimumPasswordLength) { this.minimumPasswordLength = minimumPasswordLength; } /** * @param minimumUsernameLength the minimumUsernameLength to set */ public void setMinimumUsernameLength(int minimumUsernameLength) { this.minimumUsernameLength = minimumUsernameLength; } /** * @param passwordUtils the passwordUtils to set */ public void setPasswordUtils(PasswordUtils passwordUtils) { this.passwordUtils = passwordUtils; } /** * @param propertyStore the propertyStore to set */ public void setPropertyStore(PropertyStore propertyStore) { this.propertyStore = propertyStore; } /** * @param resourceExtractionUtils The resourceExtractionUtils to set. */ public void setResourceExtractionUtils(ResourceExtractionUtils resourceExtractionUtils) { this.resourceExtractionUtils = resourceExtractionUtils; } /** * @param resourceType2namespaceList the resourceType2namespaceList to set */ public void setResourceType2namespaceList(Map<String, String> resourceType2namespaceList) { this.resourceType2namespaceList = resourceType2namespaceList; } /** * @param resourceTypes the resourceTypes to set */ public void setResourceTypes(List<String> resourceTypes) { this.resourceTypes = resourceTypes; } /** * @param taxonomyManager The taxonomyManager to set. */ public void setTaxonomyManager(TaxonomyManager taxonomyManager) { this.taxonomyManager = taxonomyManager; } /** * @param uddiUtils The uddiUtils to set. */ public void setUddiUtils(UDDIUtils uddiUtils) { this.uddiUtils = uddiUtils; } /** * @param usernamePostfix the usernamePostfix to set */ public void setUsernamePostfix(String usernamePostfix) { this.usernamePostfix = usernamePostfix; } /** * @param userTemplateMessage the userTemplateMessage to set */ public void setUserTemplateMessage(SimpleMailMessage userTemplateMessage) { this.userTemplateMessage = userTemplateMessage; } /** * This is the entry point when the user types in the URL directly * It must have a key */ public ModelAndView showDataResources(HttpServletRequest request, HttpServletResponse response) throws Exception { // get the authenticated user from LDAP UserLogin userLogin = ldapUtils.getUserLogin(request.getRemoteUser()); ProviderDetail detail = null; String key = request.getParameter(REQUEST_BUSINESS_UDDI_KEY); if (StringUtils.isNotEmpty(key)) { detail = uddiUtils.createProviderFromUDDI(key, userLogin.getUsername()); } if (detail != null) { return retrieveRegisteredDataResources(request, response, detail); } else { logger.warn("Direct use of showDataResources with no key or invalid key: " + key); return new ModelAndView("registrationBadBusinessKey"); } } /** * Saves the values for the data provider */ @SuppressWarnings("unchecked") public ModelAndView synchroniseProvider(HttpServletRequest request, HttpServletResponse response) throws Exception { ProviderDetail provider = new ProviderDetail(); ServletRequestDataBinder binder = createBinder(request, provider); initBinder(request, binder); binder.bind(request); BindingResult result = binder.getBindingResult(); validateDataProvider(provider, result); if (result.hasErrors()) { logger.info("Errors have occurred: " + result); Map<String, Object> data = new HashMap<String, Object>(); // put the errors in the request data.put(BindingResult.MODEL_KEY_PREFIX + RegistrationController.REQUEST_PROVIDER_DETAIL, result); data.put(RegistrationController.REQUEST_CONTACT_TYPES, ProviderDetail.ContactTypes.values()); data.put(RegistrationController.REQUEST_PROVIDER_DETAIL, result.getTarget()); data.putAll(referenceDataForProvider(request)); return new ModelAndView("registrationUpdateProviderDetail", data); } else { boolean success = synchroniseProvider(request, provider, result); if (!success) { return new ModelAndView("registrationUDDIFailure"); } // return showDataResources(request, response, provider); return new ModelAndView(new RedirectView(request.getContextPath() + "/register/viewDataProvider?" + REQUEST_BUSINESS_UDDI_KEY + "=" + provider.getBusinessKey())); } } /** * Synchronises the provider with the LDAP help entry for it if it exists (UUID being set) * or creates a new one if it does not exist. * * @param request For any extra parameters * @param provider To synchronise * @param errors To add to when the uddi cannot be sync'ed with */ @SuppressWarnings("unchecked") protected boolean synchroniseProvider(HttpServletRequest request, ProviderDetail provider, Errors errors) { try { logger.debug("Synchronizing provider"); boolean creatingNewProvider = StringUtils.isEmpty(provider.getBusinessKey()); uddiUtils.synchroniseProvider(provider); if (creatingNewProvider) { uddiUtils.createRegistrationLogin(request.getRemoteUser(), provider.getBusinessKey()); } return true; } catch (Exception e) { logger.error("Unexpected error communicating with UDDI: " + e.getMessage(), e); errors.reject(ErrorMessageKeys.UDDI_COMMUNICATION_ERROR); } return false; } /** * Populates the form for displaying the data provider if there is a key in the request. If there isn't then an * empty form is used, with a prepolution of the primary contact from LDAP * * @TODO Exception handling for services down, invalid keys... */ @SuppressWarnings("unchecked") public ModelAndView updateDataProvider(HttpServletRequest request, HttpServletResponse response) throws Exception { // get the authenticated user from LDAP UserLogin userLogin = ldapUtils.getUserLogin(request.getRemoteUser()); // get the provider from UDDI if necessary ProviderDetail detail = null; String key = request.getParameter(REQUEST_BUSINESS_UDDI_KEY); if (StringUtils.isNotEmpty(key)) { detail = uddiUtils.createProviderFromUDDI(key, userLogin.getUsername()); } if (detail == null) { return new ModelAndView("registrationBadBusinessKey"); } // LDAP details override the UDDI version - is this right? // detail.getBusinessPrimaryContact().setName(namePhoneEmail[0]); // detail.getBusinessPrimaryContact().setPhone(namePhoneEmail[1]); // detail.getBusinessPrimaryContact().setEmail(namePhoneEmail[2]); Map<String, Object> data = new HashMap<String, Object>(); data.putAll(referenceDataForProvider(request)); data.put(RegistrationController.REQUEST_PROVIDER_DETAIL, detail); return new ModelAndView("registrationUpdateProviderDetail", data); } /** * This is the entry point for the AJAX call to update the resource */ @SuppressWarnings("unchecked") public ModelAndView updateDataResource(HttpServletRequest request, HttpServletResponse response) throws Exception { logger.info("Updating a resource..."); debugRequestParams(request); ResourceDetail resource = new ResourceDetail(); ServletRequestDataBinder binder = createBinder(request, resource); binder.bind(request); String businessKey = request.getParameter(REQUEST_BUSINESS_UDDI_KEY); BindingResult result = binder.getBindingResult(); validateDataResource(resource, result); if (result.getErrorCount() == 0) { // it is always the last one, due to the fact that only one is ever submitted // although it's id may be something other than 0 if (logger.isDebugEnabled()) { logger.debug("Resource name: " + resource.getName()); logger.debug("Resource description: " + resource.getDescription()); } uddiUtils.updateResource(resource, request.getParameter(REQUEST_BUSINESS_UDDI_KEY)); return new ModelAndView(new RedirectView( request.getContextPath() + "/register/showDataResources?businessKey=" + businessKey)); } else { logger.error(result.getAllErrors()); // put the errors in the request Map<String, Object> data = new HashMap<String, Object>(); data.putAll(referenceDataForResource(request, resource)); data.put(RegistrationController.REQUEST_RESOURCE, resource); data.put(BindingResult.MODEL_KEY_PREFIX + RegistrationController.REQUEST_RESOURCE, result); List<String> beanProperties = retrieveReadonlyPropertiesForResource(resource); data.putAll(referenceDataForResourceList(request)); data.put("readonlyProperties", beanProperties); return new ModelAndView("registrationResourceDetail", data); } } /** * Update registration logins, creating those for the business keys passed in the request. * * @param request * @param response * @return * @throws Exception */ public ModelAndView updateRegistrationLogins(HttpServletRequest request, HttpServletResponse response) throws Exception { String user = request.getParameter("user"); boolean sendEmail = ServletRequestUtils.getBooleanParameter(request, "sendEmail", false); // if user is not supplied in a parameter, update is for the current user if (StringUtils.isEmpty(user)) { user = request.getRemoteUser(); } String[] businessKeys = request.getParameterValues(REQUEST_BUSINESS_UDDI_KEY); String[] businessKeysToRemove = request.getParameterValues("businessKeyToRemove"); List<String> existingKeys = uddiUtils.getAssociatedBusinessKeys(user); List<String> createdRegistrations = new ArrayList<String>(); // add the selected registration logins if (businessKeys != null) { for (int i = 0; i < businessKeys.length; i++) { if (!existingKeys.contains(businessKeys[i])) { uddiUtils.createRegistrationLogin(user, businessKeys[i]); createdRegistrations.add(businessKeys[i]); } } } // if required sent a notification email if (sendEmail && !createdRegistrations.isEmpty()) { UserLogin userLogin = ldapUtils.getUserLogin(user); // send verification email SimpleMailMessage verificationMessage = new SimpleMailMessage(userTemplateMessage); verificationMessage.setTo(userLogin.getEmail()); verificationMessage.setSubject("User has been granted access to Provider Details"); StringBuffer sb = new StringBuffer( "Your request to access the details of the following providers has been granted:\n\n"); for (String createdRegistration : createdRegistrations) { ProviderDetail pd = uddiUtils.createProviderFromUDDI(createdRegistration, userLogin.getUsername()); sb.append(pd.getBusinessName()); sb.append("\n"); } verificationMessage.setText(sb.toString()); try { mailSender.send(verificationMessage); } catch (MailException e) { // simply log it and go on... logger.error("Couldn't send message", e); } } // remove the selected registration logins if (businessKeysToRemove != null) { for (String element : businessKeysToRemove) { if (existingKeys.contains(element)) uddiUtils.deleteRegistrationLogin(user, element); } } return new ModelAndView(new RedirectView(request.getContextPath() + "/register/")); } /** * Show the update user screen. * * @param request * @param response * @return * @throws Exception */ public ModelAndView userUpdate(HttpServletRequest request, HttpServletResponse response) throws Exception { ModelAndView mav = new ModelAndView("registrationUserUpdate"); return mav; } /** * Checks that Business details are all in there * * @param command The form object * @param errors The errors to add to */ protected void validateDataProvider(Object command, Errors errors) { ProviderDetail provider = (ProviderDetail) command; if (StringUtils.isEmpty(provider.getBusinessName())) { errors.rejectValue("businessName", ErrorMessageKeys.MUST_BE_SPECIFIED); } // if (StringUtils.isEmpty(provider.getBusinessCountry())) { // errors.rejectValue("businessCountry", ErrorMessageKeys.MUST_BE_SPECIFIED); // } if (StringUtils.isEmpty(provider.getBusinessDescription())) { errors.rejectValue("businessDescription", ErrorMessageKeys.MUST_BE_SPECIFIED); } int secondaryContactCount = 0; for (ProviderDetail.Contact contact : provider.getBusinessSecondaryContacts()) { logger.info("Validating secondary contact"); if (StringUtils.isEmpty(contact.getName())) { errors.rejectValue("businessSecondaryContacts[" + secondaryContactCount + "].name", ErrorMessageKeys.MUST_BE_SPECIFIED); } if (StringUtils.isEmpty(contact.getEmail())) { errors.rejectValue("businessSecondaryContacts[" + secondaryContactCount + "].email", ErrorMessageKeys.MUST_BE_SPECIFIED); } if (StringUtils.isEmpty(contact.getPhone())) { errors.rejectValue("businessSecondaryContacts[" + secondaryContactCount + "].phone", ErrorMessageKeys.MUST_BE_SPECIFIED); } secondaryContactCount++; } logger.info("Metadata validation error count: " + errors.getErrorCount()); } /** * Validate this details of this data resource * * @param resourceDetail * @param result */ private void validateDataResource(ResourceDetail resourceDetail, BindingResult result) { if (StringUtils.isEmpty(resourceDetail.getName())) { result.rejectValue("name", ErrorMessageKeys.MUST_BE_SPECIFIED); } if (StringUtils.isEmpty(resourceDetail.getCode())) { result.rejectValue("code", ErrorMessageKeys.MUST_BE_SPECIFIED); } if (StringUtils.isEmpty(resourceDetail.getAccessPoint())) { result.rejectValue("accessPoint", ErrorMessageKeys.MUST_BE_SPECIFIED); } if (resourceDetail.getNorthCoordinate() != null) { if (resourceDetail.getNorthCoordinate() > 90 || resourceDetail.getNorthCoordinate() < -90) result.rejectValue("northCoordinate", ErrorMessageKeys.INVALID_LATITUDE); } if (resourceDetail.getSouthCoordinate() != null) { if (resourceDetail.getSouthCoordinate() > 90 || resourceDetail.getSouthCoordinate() < -90) result.rejectValue("southCoordinate", ErrorMessageKeys.INVALID_LATITUDE); } if (resourceDetail.getEastCoordinate() != null) { if (resourceDetail.getEastCoordinate() > 180 || resourceDetail.getEastCoordinate() < -180) result.rejectValue("eastCoordinate", ErrorMessageKeys.INVALID_LONGITUDE); } if (resourceDetail.getWestCoordinate() != null) { if (resourceDetail.getWestCoordinate() > 180 || resourceDetail.getWestCoordinate() < -180) result.rejectValue("westCoordinate", ErrorMessageKeys.INVALID_LONGITUDE); } if (resourceDetail.getWestCoordinate() != null && resourceDetail.getEastCoordinate() != null && resourceDetail.getWestCoordinate() > resourceDetail.getEastCoordinate()) { result.rejectValue("westCoordinate", ErrorMessageKeys.WEST_GREATER_THAN_EAST); } if (resourceDetail.getNorthCoordinate() != null && resourceDetail.getSouthCoordinate() != null && resourceDetail.getSouthCoordinate() > resourceDetail.getNorthCoordinate()) { result.rejectValue("southCoordinate", ErrorMessageKeys.SOUTH_GREATER_THAN_NORTH); } } /** * @param password * @return */ private boolean validatePassword(String password) { if (password != null && password.length() > minimumPasswordLength) return true; return false; } /** * Check for invalid characters. * * @param username * @return */ private boolean validateUsername(String username) { if (username != null && username.length() > minimumUsernameLength) { Pattern p = Pattern.compile("^[A-Za-z]\\w{5,30}$"); Matcher m = p.matcher(username); boolean valid = m.matches(); return valid; } return false; } /** * User verification. * * @param request * @param response * @return * @throws Exception */ public ModelAndView verification(HttpServletRequest request, HttpServletResponse response) throws Exception { String firstName = request.getParameter("fn"); String surname = request.getParameter("sn"); String email = request.getParameter("e"); String username = request.getParameter("u"); String password = request.getParameter("p"); String decryptedPassword = passwordUtils.encryptPassword(password, false); UserLogin userLogin = new UserLogin(firstName, surname, email, username, decryptedPassword); // check the user hasn't already been created if (!ldapUtils.userNameInUse(username)) { ldapUtils.createNewUser(userLogin); List<DataProviderDTO> dataProviders = dataResourceManager .findDataProvidersForUser(userLogin.getEmail()); for (DataProviderDTO dataProvider : dataProviders) { uddiUtils.createRegistrationLogin(username, dataProvider.getUuid()); } } return new ModelAndView( new RedirectView(request.getContextPath() + "/register/?u=" + username + "&p=" + password)); } /** * The entry point once a user has logged in. */ @SuppressWarnings("unchecked") public ModelAndView viewAdminMenu(HttpServletRequest request, HttpServletResponse response) throws Exception { UserLogin userLogin = ldapUtils.getUserLogin(request.getRemoteUser()); // retrieve login/business key mapping List<String> businessKeys = uddiUtils.getAssociatedBusinessKeys(request.getRemoteUser()); List<ProviderDetail> pds = new ArrayList<ProviderDetail>(); for (int i = 0; i < businessKeys.size(); i++) { ProviderDetail pd = uddiUtils.createProviderFromUDDI(businessKeys.get(i), userLogin.getFullName()); pds.add(pd); } ModelAndView mav = new ModelAndView("registrationMain"); mav.addObject("providerDetails", pds); if (StringUtils.isNotEmpty(userLogin.getFullName())) { mav.addObject("username", userLogin.getFullName()); } else { mav.addObject("username", userLogin.getUsername()); } return mav; } /** * Populates the form for displaying the data provider if there is a key in the request. If there isn't then an * empty form is used, with a prepolution of the primary contact from LDAP * * @TODO Exception handling for services down, invalid keys... */ @SuppressWarnings("unchecked") public ModelAndView viewDataProvider(HttpServletRequest request, HttpServletResponse response) throws Exception { // get the provider from UDDI if necessary ProviderDetail provider = retrieveProviderFromUDDI(request); if (provider == null) { return new ModelAndView("registrationBadBusinessKey"); } Map<String, Object> data = new HashMap<String, Object>(); data.putAll(referenceDataForProvider(request)); data.put(RegistrationController.REQUEST_PROVIDER_DETAIL, provider); return new ModelAndView("registrationProviderDetail", data); } /** * Populates the form for displaying the data provider if there is a key in the request. If there isn't then an * empty form is used, with a prepolution of the primary contact from LDAP * * @TODO Exception handling for services down, invalid keys... */ @SuppressWarnings("unchecked") public ModelAndView viewDataResource(HttpServletRequest request, HttpServletResponse response) throws Exception { // get the provider from UDDI if necessary ProviderDetail provider = retrieveProviderFromUDDI(request); if (provider == null) { return new ModelAndView("registrationBadBusinessKey"); } // retrieve resource details ResourceDetail resource = retrieveDataResource(request, provider); if (resource == null) { return new ModelAndView("registrationBadBusinessKey"); } Map<String, Object> data = new HashMap<String, Object>(); data.putAll(referenceDataForResource(request, resource)); data.put(RegistrationController.REQUEST_PROVIDER_DETAIL, provider); data.put(RegistrationController.REQUEST_RESOURCE, resource); List<String> beanProperties = retrieveReadonlyPropertiesForResource(resource); data.put("readonlyProperties", beanProperties); return new ModelAndView("registrationResourceDetail", data); } }