001/*
002 * (C) Copyright 2017 Nuxeo (http://nuxeo.com/) and others.
003 *
004 * Licensed under the Apache License, Version 2.0 (the "License");
005 * you may not use this file except in compliance with the License.
006 * You may obtain a copy of the License at
007 *
008 *     http://www.apache.org/licenses/LICENSE-2.0
009 *
010 * Unless required by applicable law or agreed to in writing, software
011 * distributed under the License is distributed on an "AS IS" BASIS,
012 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
013 * See the License for the specific language governing permissions and
014 * limitations under the License.
015 *
016 * Contributors:
017 *     Antoine Taillefer <ataillefer@nuxeo.com>
018 */
019package org.nuxeo.jaxrs.test;
020
021import org.apache.http.client.HttpClient;
022import org.apache.http.client.config.RequestConfig;
023import org.apache.http.impl.client.BasicCookieStore;
024import org.apache.http.impl.client.HttpClientBuilder;
025
026import com.sun.jersey.api.client.Client;
027import com.sun.jersey.api.client.filter.HTTPBasicAuthFilter;
028import com.sun.jersey.client.apache4.ApacheHttpClient4Handler;
029
030/**
031 * Helper for using the Jersey 1 {@link Client}.
032 *
033 * @since 9.3
034 */
035public final class JerseyClientHelper {
036
037    public static final int DEFAULT_CONNECTION_TIMEOUT = 60 * 1000; // 60 seconds
038
039    /**
040     * Default instance of a Jersey 1 {@link Client} relying on the Apache HTTP client,
041     * {@link #DEFAULT_CONNECTION_TIMEOUT} for the connection timeout parameters and no authentication.
042     */
043    public static final Client DEFAULT_CLIENT = clientBuilder().build();
044
045    private JerseyClientHelper() {
046        // Helper class
047    }
048
049    /**
050     * Allows to build a custom instance of a Jersey 1 {@link Client} relying on the Apache HTTP client.
051     * <p>
052     * For instance, you can set the connection timeout and credentials for basic authentication by calling:
053     *
054     * <pre>
055     * {@code
056     *     Client client = JerseyClientHelper.clientBuilder()
057     *                                       .setConnectTimeout(5000)
058     *                                       .setCredentials("joe", "password")
059     *                                       .build();
060     * }
061     *
062     * <pre>
063     */
064    public static ApacheHttpClientBuilder clientBuilder() {
065        return new ApacheHttpClientBuilder();
066    }
067
068    public static class ApacheHttpClientBuilder {
069
070        protected int socketTimeout;
071
072        protected int connectTimeout;
073
074        protected int connectionRequestTimeout;
075
076        protected boolean redirectsEnabled;
077
078        protected String username;
079
080        protected String password;
081
082        protected ApacheHttpClientBuilder() {
083            this.socketTimeout = DEFAULT_CONNECTION_TIMEOUT;
084            this.connectTimeout = DEFAULT_CONNECTION_TIMEOUT;
085            this.connectionRequestTimeout = DEFAULT_CONNECTION_TIMEOUT;
086            this.redirectsEnabled = true;
087        }
088
089        public ApacheHttpClientBuilder setSocketTimeout(final int socketTimeout) {
090            this.socketTimeout = socketTimeout;
091            return this;
092        }
093
094        public ApacheHttpClientBuilder setConnectTimeout(final int connectTimeout) {
095            this.connectTimeout = connectTimeout;
096            return this;
097        }
098
099        public ApacheHttpClientBuilder setConnectionRequestTimeout(final int connectionRequestTimeout) {
100            this.connectionRequestTimeout = connectionRequestTimeout;
101            return this;
102        }
103
104        public ApacheHttpClientBuilder setRedirectsEnabled(final boolean redirectsEnabled) {
105            this.redirectsEnabled = redirectsEnabled;
106            return this;
107        }
108
109        public ApacheHttpClientBuilder setCredentials(final String username, final String password) {
110            this.username = username;
111            this.password = password;
112            return this;
113        }
114
115        public Client build() {
116            RequestConfig requestConfig = RequestConfig.custom()
117                                                       .setSocketTimeout(socketTimeout)
118                                                       .setConnectTimeout(connectTimeout)
119                                                       .setConnectionRequestTimeout(connectionRequestTimeout)
120                                                       .setRedirectsEnabled(redirectsEnabled)
121                                                       .build();
122            HttpClient httpClient = HttpClientBuilder.create().setDefaultRequestConfig(requestConfig).build();
123            Client client = new Client(new ApacheHttpClient4Handler(httpClient, new BasicCookieStore(), true));
124            if (username != null && password != null) {
125                client.addFilter(new HTTPBasicAuthFilter(username, password));
126            }
127            return client;
128        }
129
130    }
131
132}