All Downloads are FREE. Search and download functionalities are using the official Maven repository.

oauth.signpost.signature.SignatureBaseString Maven / Gradle / Ivy

/*
 * Copyright (c) 2009 Matthias Kaeppler Licensed 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
 * 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 oauth.signpost.signature;

import java.io.IOException;
import java.io.InputStream;
import java.net.URI;
import java.net.URISyntaxException;
import java.util.ArrayList;
import java.util.Collection;
import java.util.Collections;
import java.util.List;
import java.util.Map;

import oauth.signpost.OAuth;
import oauth.signpost.Parameter;
import oauth.signpost.exception.OAuthMessageSignerException;
import oauth.signpost.http.HttpRequest;

public class SignatureBaseString {

    private HttpRequest request;

    private Map oauthParams;

    /** An efficiently sortable wrapper around a parameter. */
    private static class ComparableParameter implements
            Comparable {

        ComparableParameter(Parameter value) {
            this.value = value;
            String n = safeString(value.getKey());
            String v = safeString(value.getValue());
            this.key = OAuth.percentEncode(n) + ' ' + OAuth.percentEncode(v);
            // ' ' is used because it comes before any character
            // that can appear in a percentEncoded string.
        }

        final Parameter value;

        private final String key;

        private static String safeString(String from) {
            return (from == null) ? null : from.toString();
        }

        public int compareTo(ComparableParameter that) {
            return this.key.compareTo(that.key);
        }

        @Override
        public String toString() {
            return key;
        }

    }

    public SignatureBaseString(HttpRequest request,
            Map oauthParams) {
        this.request = request;
        this.oauthParams = oauthParams;
    }

    public String compute() throws OAuthMessageSignerException {

        try {
            List params = new ArrayList();
            collectHeaderParameters(params);
            collectBodyParameters(params);
            String requestUrl = collectQueryParameters(params);

            return request.getMethod() + '&'
                    + OAuth.percentEncode(normalizeUrl(requestUrl)) + '&'
                    + OAuth.percentEncode(normalizeParameters(params));
        } catch (Exception e) {
            throw new OAuthMessageSignerException(e);
        }
    }

    public String normalizeUrl(String url) throws URISyntaxException {
        URI uri = new URI(url);
        String scheme = uri.getScheme().toLowerCase();
        String authority = uri.getAuthority().toLowerCase();
        boolean dropPort = (scheme.equals("http") && uri.getPort() == 80)
                || (scheme.equals("https") && uri.getPort() == 443);
        if (dropPort) {
            // find the last : in the authority
            int index = authority.lastIndexOf(":");
            if (index >= 0) {
                authority = authority.substring(0, index);
            }
        }
        String path = uri.getRawPath();
        if (path == null || path.length() <= 0) {
            path = "/"; // conforms to RFC 2616 section 3.2.2
        }
        // we know that there is no query and no fragment here.
        return scheme + "://" + authority + path;
    }

    public String normalizeParameters(Collection parameters)
            throws IOException {
        if (parameters == null) {
            return "";
        }
        List p = new ArrayList(
                parameters.size());
        for (Parameter parameter : parameters) {
            if (!OAuth.OAUTH_SIGNATURE.equals(parameter.getKey())) {
                p.add(new ComparableParameter(parameter));
            }
        }
        Collections.sort(p);
        return OAuth.formEncode(getParameters(p));
    }

    /**
     * Collects OAuth Authorization header parameters as per OAuth Core 1.0 spec
     * section 9.1.1 FIXME: This should actually look in the request header and
     * prioritize any existing OAuth parameters (save for the realm param, cf.
     * 5.4.1) in favor of whatever was passed in the parameters map before.
     * Could also be done in OAuthConsumer.buildOAuthParemeterMap()
     */
    private void collectHeaderParameters(Collection parameters) {
        for (String key : oauthParams.keySet()) {
            parameters.add(new Parameter(key, oauthParams.get(key)));
        }
    }

    /**
     * Collects x-www-form-urlencoded body parameters as per OAuth Core 1.0 spec
     * section 9.1.1
     */
    private void collectBodyParameters(Collection parameters)
            throws IOException {

        // collect x-www-form-urlencoded body params
        String contentType = request.getContentType();
        if (contentType != null && contentType.equals(OAuth.FORM_ENCODED)) {
            InputStream payload = request.getMessagePayload();
            parameters.addAll(OAuth.decodeForm(payload));
        }
    }

    /**
     * Collects HTTP GET query string parameters as per OAuth Core 1.0 spec
     * section 9.1.1
     * 
     * @param request
     *            The HTTP request
     * @return the URL without the query parameters, if there were any
     */
    private String collectQueryParameters(Collection parameters) {

        String url = request.getRequestUrl();
        int q = url.indexOf('?');
        if (q >= 0) {
            // Combine the URL query string with the other parameters:
            parameters.addAll(OAuth.decodeForm(url.substring(q + 1)));
            url = url.substring(0, q);
        }

        return url;
    }

    /** Retrieve the original parameters from a sorted collection. */
    private List getParameters(
            Collection parameters) {
        if (parameters == null) {
            return null;
        }
        ArrayList list = new ArrayList(parameters.size());
        for (ComparableParameter parameter : parameters) {
            list.add(parameter.value);
        }
        return list;
    }
}




© 2015 - 2024 Weber Informatics LLC | Privacy Policy