View Javadoc
1   /*
2    * Licensed to the Apache Software Foundation (ASF) under one or more
3    * contributor license agreements.  See the NOTICE file distributed with
4    * this work for additional information regarding copyright ownership.
5    * The ASF licenses this file to You under the Apache License, Version 2.0
6    * (the "License"); you may not use this file except in compliance with
7    * the License.  You may obtain a copy of the License at
8    *
9    *      http://www.apache.org/licenses/LICENSE-2.0
10   *
11   * Unless required by applicable law or agreed to in writing, software
12   * distributed under the License is distributed on an "AS IS" BASIS,
13   * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
14   * See the License for the specific language governing permissions and
15   * limitations under the License.
16   */
17  package org.apache.commons.vfs2.provider.http;
18  
19  import org.apache.commons.httpclient.Cookie;
20  import org.apache.commons.httpclient.HostConfiguration;
21  import org.apache.commons.httpclient.HttpClient;
22  import org.apache.commons.httpclient.HttpConnectionManager;
23  import org.apache.commons.httpclient.MultiThreadedHttpConnectionManager;
24  import org.apache.commons.httpclient.UsernamePasswordCredentials;
25  import org.apache.commons.httpclient.auth.AuthScope;
26  import org.apache.commons.httpclient.params.HttpClientParams;
27  import org.apache.commons.httpclient.params.HttpConnectionManagerParams;
28  import org.apache.commons.vfs2.FileSystemException;
29  import org.apache.commons.vfs2.FileSystemOptions;
30  import org.apache.commons.vfs2.UserAuthenticationData;
31  import org.apache.commons.vfs2.UserAuthenticator;
32  import org.apache.commons.vfs2.util.UserAuthenticatorUtils;
33  
34  /**
35   * Create a HttpClient instance.
36   */
37  public final class HttpClientFactory {
38  
39      private HttpClientFactory() {
40      }
41  
42      public static HttpClient createConnection(final String scheme, final String hostname, final int port,
43              final String username, final String password, final FileSystemOptions fileSystemOptions)
44              throws FileSystemException {
45          return createConnection(HttpFileSystemConfigBuilder.getInstance(), scheme, hostname, port, username, password,
46                  fileSystemOptions);
47      }
48  
49      /**
50       * Creates a new connection to the server.
51       *
52       * @param builder The HttpFileSystemConfigBuilder.
53       * @param scheme The protocol.
54       * @param hostname The hostname.
55       * @param port The port number.
56       * @param username The username.
57       * @param password The password
58       * @param fileSystemOptions The file system options.
59       * @return a new HttpClient connection.
60       * @throws FileSystemException if an error occurs.
61       * @since 2.0
62       */
63      public static HttpClient createConnection(final HttpFileSystemConfigBuilder builder, final String scheme,
64              final String hostname, final int port, final String username, final String password,
65              final FileSystemOptions fileSystemOptions) throws FileSystemException {
66          HttpClient client;
67          try {
68              final HttpConnectionManager mgr = new MultiThreadedHttpConnectionManager();
69              final HttpConnectionManagerParams connectionMgrParams = mgr.getParams();
70  
71              client = new HttpClient(mgr);
72  
73              final HostConfiguration config = new HostConfiguration();
74              config.setHost(hostname, port, scheme);
75  
76              if (fileSystemOptions != null) {
77                  final String proxyHost = builder.getProxyHost(fileSystemOptions);
78                  final int proxyPort = builder.getProxyPort(fileSystemOptions);
79  
80                  if (proxyHost != null && proxyHost.length() > 0 && proxyPort > 0) {
81                      config.setProxy(proxyHost, proxyPort);
82                  }
83  
84                  final UserAuthenticator proxyAuth = builder.getProxyAuthenticator(fileSystemOptions);
85                  if (proxyAuth != null) {
86                      final UserAuthenticationData authData = UserAuthenticatorUtils.authenticate(proxyAuth,
87                              new UserAuthenticationData.Type[] { UserAuthenticationData.USERNAME,
88                                      UserAuthenticationData.PASSWORD });
89  
90                      if (authData != null) {
91                          final UsernamePasswordCredentials proxyCreds = new UsernamePasswordCredentials(
92                                  UserAuthenticatorUtils.toString(UserAuthenticatorUtils.getData(authData,
93                                          UserAuthenticationData.USERNAME, null)),
94                                  UserAuthenticatorUtils.toString(UserAuthenticatorUtils.getData(authData,
95                                          UserAuthenticationData.PASSWORD, null)));
96  
97                          final AuthScope scope = new AuthScope(proxyHost, AuthScope.ANY_PORT);
98                          client.getState().setProxyCredentials(scope, proxyCreds);
99                      }
100 
101                     if (builder.isPreemptiveAuth(fileSystemOptions)) {
102                         final HttpClientParams httpClientParams = new HttpClientParams();
103                         httpClientParams.setAuthenticationPreemptive(true);
104                         client.setParams(httpClientParams);
105                     }
106                 }
107 
108                 final Cookie[] cookies = builder.getCookies(fileSystemOptions);
109                 if (cookies != null) {
110                     client.getState().addCookies(cookies);
111                 }
112             }
113             /**
114              * ConnectionManager set methods must be called after the host & port and proxy host & port are set in the
115              * HostConfiguration. They are all used as part of the key when HttpConnectionManagerParams tries to locate
116              * the host configuration.
117              */
118             connectionMgrParams.setMaxConnectionsPerHost(config, builder.getMaxConnectionsPerHost(fileSystemOptions));
119             connectionMgrParams.setMaxTotalConnections(builder.getMaxTotalConnections(fileSystemOptions));
120 
121             connectionMgrParams.setConnectionTimeout(builder.getConnectionTimeout(fileSystemOptions));
122             connectionMgrParams.setSoTimeout(builder.getSoTimeout(fileSystemOptions));
123 
124             client.setHostConfiguration(config);
125 
126             if (username != null) {
127                 final UsernamePasswordCredentials creds = new UsernamePasswordCredentials(username, password);
128                 final AuthScope scope = new AuthScope(hostname, AuthScope.ANY_PORT);
129                 client.getState().setCredentials(scope, creds);
130             }
131         } catch (final Exception exc) {
132             throw new FileSystemException("vfs.provider.http/connect.error", exc, hostname);
133         }
134 
135         return client;
136     }
137 }