org.jasig.portlet.courses.dao.xml.HttpClientCoursesDaoImpl.java Source code

Java tutorial

Introduction

Here is the source code for org.jasig.portlet.courses.dao.xml.HttpClientCoursesDaoImpl.java

Source

/**
 * Licensed to Apereo under one or more contributor license
 * agreements. See the NOTICE file distributed with this work
 * for additional information regarding copyright ownership.
 * Apereo licenses this file to you under the Apache License,
 * Version 2.0 (the "License"); you may not use this file
 * except in compliance with the License.  You may obtain a
 * copy of the License at the following location:
 *
 *   http://www.apache.org/licenses/LICENSE-2.0
 *
 * Unless required by applicable law or agreed to in writing,
 * software distributed under the License is distributed on an
 * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
 * KIND, either express or implied.  See the License for the
 * specific language governing permissions and limitations
 * under the License.
 */
package org.jasig.portlet.courses.dao.xml;

import java.io.Serializable;
import java.util.HashMap;
import java.util.Map;

import javax.portlet.PortletRequest;

import org.apache.commons.codec.binary.Base64;
import org.apache.commons.logging.Log;
import org.apache.commons.logging.LogFactory;
import org.jasig.portlet.courses.dao.ICacheableCoursesDao;
import org.jasig.portlet.courses.dao.xml.HttpClientCoursesDaoImpl.CoursesCacheKey;
import org.jasig.portlet.courses.model.xml.TermList;
import org.jasig.portlet.courses.model.xml.personal.CoursesByTerm;
import org.jasig.portlet.courses.model.xml.personal.TermsAndCourses;
import org.jasig.portlet.courses.util.IParameterEvaluator;
import org.jasig.portlet.courses.util.TermCodeParameterEvaluator;
import org.springframework.http.HttpEntity;
import org.springframework.http.HttpHeaders;
import org.springframework.http.HttpMethod;
import org.springframework.web.client.RestOperations;

/**
 * HttpClientCoursesDaoImpl retrieves courses from a Basic Authentication
 * protected XML feed.
 * 
 * @author Jen Bourey, jennifer.bourey@gmail.com
 * @version $Revision$
 */
public class HttpClientCoursesDaoImpl implements ICacheableCoursesDao<CoursesCacheKey, CoursesCacheKey> {
    public static final String PROPERTY_KEY_TERMCODE = "#TERMCODE#";

    private final Log log = LogFactory.getLog(getClass());

    private String termsUrlFormat = null;
    private String coursesUrlFormat = null;
    private Map<String, IParameterEvaluator> urlParamEvaluators = new HashMap<String, IParameterEvaluator>();
    private IParameterEvaluator usernameEvaluator;
    private IParameterEvaluator passwordEvaluator;
    private RestOperations restTemplate;

    public void setTermsUrlFormat(String urlFormat) {
        this.termsUrlFormat = urlFormat;
    }

    public void setCoursesUrlFormat(String urlFormat) {
        this.coursesUrlFormat = urlFormat;
    }

    public void setUrlParams(Map<String, IParameterEvaluator> params) {
        this.urlParamEvaluators = params;
    }

    public void setUsernameEvaluator(IParameterEvaluator usernameEvaluator) {
        this.usernameEvaluator = usernameEvaluator;
    }

    public void setPasswordEvaluator(IParameterEvaluator passwordEvaluator) {
        this.passwordEvaluator = passwordEvaluator;
    }

    public void setRestTemplate(RestOperations restTemplate) {
        this.restTemplate = restTemplate;
    }

    @Override
    public CoursesCacheKey getTermListKey(PortletRequest request) {
        final String username = usernameEvaluator.evaluate(request);
        final String password = passwordEvaluator.evaluate(request);
        final Map<String, String> params = createParameters(request, urlParamEvaluators);
        return new CoursesCacheKey(username, password.toCharArray(), params);
    }

    @Override
    public TermList getTermList(CoursesCacheKey key) {
        final TermsAndCourses termsAndCourses = getTermsAndCourses(key, termsUrlFormat);
        return termsAndCourses.getTermList();
    }

    @Override
    public CoursesCacheKey getCoursesByTermKey(PortletRequest request, String termCode, TermList termList) {
        final String username = usernameEvaluator.evaluate(request);
        final String password = passwordEvaluator.evaluate(request);
        final Map<String, String> params = createParameters(request, urlParamEvaluators);
        return new CoursesCacheKey(username, password.toCharArray(), params, termCode);
    }

    @Override
    public CoursesByTerm getCoursesByTerm(CoursesCacheKey key) {
        final TermsAndCourses termsAndCourses = getTermsAndCourses(key, coursesUrlFormat);
        return termsAndCourses.getCoursesByTerm(key.getTermCode());
    }

    protected TermsAndCourses getTermsAndCourses(CoursesCacheKey key, String url) {
        Map<String, String> params = key.getParams();

        if (log.isDebugEnabled()) {
            log.debug("Invoking uri '" + url + "' with the following parameters:  " + params.toString());
        }

        HttpEntity<?> requestEntity = getRequestEntity(key);
        HttpEntity<TermsAndCourses> response = restTemplate.exchange(url, HttpMethod.GET, requestEntity,
                TermsAndCourses.class, params);

        final TermsAndCourses termsAndCourses = response.getBody();
        return termsAndCourses;
    }

    /**
     * Get a request entity prepared for basic authentication.
     */
    protected HttpEntity<?> getRequestEntity(CoursesCacheKey credentials) {
        final String username = credentials.getUsername();
        final char[] password = credentials.getPassword();

        if (log.isDebugEnabled()) {
            boolean hasPassword = password != null;
            log.debug("Preparing HttpEntity for user '" + username + "' (password provided = " + hasPassword + ")");
        }

        HttpHeaders requestHeaders = new HttpHeaders();
        String authString = username.concat(":").concat(new String(password));
        String encodedAuthString = new Base64().encodeToString(authString.getBytes());
        requestHeaders.set("Authorization", "Basic ".concat(encodedAuthString));

        HttpEntity<?> rslt = new HttpEntity<Object>(requestHeaders);
        return rslt;

    }

    protected void setTermCodeRequestAttribute(PortletRequest request, String termCode) {
        for (IParameterEvaluator evaluator : urlParamEvaluators.values()) {
            if (evaluator instanceof TermCodeParameterEvaluator) {
                request.setAttribute(((TermCodeParameterEvaluator) evaluator).getAttributeKey(), termCode);
                return;
            }
        }
    }

    protected Map<String, String> createParameters(PortletRequest request,
            Map<String, IParameterEvaluator> params) {
        Map<String, String> result = new HashMap<String, String>();

        for (String key : params.keySet()) {
            result.put(key, params.get(key).evaluate(request));
        }
        return result;
    }

    public static final class CoursesCacheKey implements Serializable {
        private static final long serialVersionUID = 1L;

        private final SecureRequestCredentials credentials;
        private final Map<String, String> params;
        private final String termCode;

        private CoursesCacheKey(String username, char[] password, Map<String, String> params) {
            this(username, password, params, null);
        }

        private CoursesCacheKey(String username, char[] password, Map<String, String> params, String termCode) {
            this.credentials = new SecureRequestCredentials(username, password);
            this.params = params;
            this.termCode = termCode;
        }

        private String getUsername() {
            return credentials.getUsername();
        }

        private char[] getPassword() {
            return credentials.getPassword();
        }

        private Map<String, String> getParams() {
            return params;
        }

        public String getTermCode() {
            return termCode;
        }

        @Override
        public int hashCode() {
            final int prime = 31;
            int result = 1;
            result = prime * result + ((credentials == null) ? 0 : credentials.hashCode());
            result = prime * result + ((params == null) ? 0 : params.hashCode());
            return result;
        }

        @Override
        public boolean equals(Object obj) {
            if (this == obj)
                return true;
            if (obj == null)
                return false;
            if (getClass() != obj.getClass())
                return false;
            CoursesCacheKey other = (CoursesCacheKey) obj;
            if (credentials == null) {
                if (other.credentials != null)
                    return false;
            } else if (!credentials.equals(other.credentials))
                return false;
            if (params == null) {
                if (other.params != null)
                    return false;
            } else if (!params.equals(other.params))
                return false;
            return true;
        }

        @Override
        public String toString() {
            return "CoursesCacheKey [credentials=" + credentials + ", params=" + params + "]";
        }
    }
}