View Javadoc
1   package com.foxinmy.weixin4j.http;
2   
3   import java.io.IOException;
4   import java.io.InputStream;
5   import java.io.OutputStream;
6   import java.net.HttpURLConnection;
7   import java.net.Proxy;
8   import java.net.URI;
9   import java.net.URLConnection;
10  import java.util.List;
11  import java.util.Map.Entry;
12  
13  import javax.net.ssl.HostnameVerifier;
14  import javax.net.ssl.HttpsURLConnection;
15  import javax.net.ssl.SSLContext;
16  
17  import com.foxinmy.weixin4j.http.entity.HttpEntity;
18  import com.foxinmy.weixin4j.http.factory.HttpClientFactory;
19  import com.foxinmy.weixin4j.util.IOUtil;
20  import com.foxinmy.weixin4j.util.StringUtil;
21  
22  /**
23   * HTTP 简单实现
24   *
25   * @className SimpleHttpClient
26   * @author jinyu(foxinmy@gmail.com)
27   * @date 2015年5月29日
28   * @since JDK 1.6
29   * @see
30   */
31  public class SimpleHttpClient extends AbstractHttpClient {
32  
33  	private final HttpParams params;
34  
35  	public SimpleHttpClient(HttpParams params) {
36  		this.params = params;
37  	}
38  
39  	protected HttpURLConnection createHttpConnection(HttpRequest request)
40  			throws IOException {
41  		URI uri = request.getURI();
42  		Proxy proxy = params != null ? params.getProxy() : null;
43  		URLConnection urlConnection = proxy != null ? uri.toURL()
44  				.openConnection(proxy) : uri.toURL().openConnection();
45  		if (uri.getScheme().equals("https")) {
46  			SSLContext sslContext = null;
47  			HostnameVerifier hostnameVerifier = null;
48  			if (params != null) {
49  				sslContext = params.getSSLContext();
50  				hostnameVerifier = params.getHostnameVerifier();
51  			}
52  			if (sslContext == null) {
53  				sslContext = HttpClientFactory.allowSSLContext();
54  			}
55  			if (hostnameVerifier == null) {
56  				hostnameVerifier = HttpClientFactory.AllowHostnameVerifier.GLOBAL;
57  			}
58  			HttpsURLConnection connection = (HttpsURLConnection) urlConnection;
59  			connection.setSSLSocketFactory(sslContext.getSocketFactory());
60  			connection.setHostnameVerifier(hostnameVerifier);
61  			return connection;
62  		} else {
63  			return (HttpURLConnection) urlConnection;
64  		}
65  	}
66  
67  	@Override
68  	public HttpResponse execute(HttpRequest request) throws HttpClientException {
69  		HttpResponse response = null;
70  		try {
71  			// create connection object
72  			HttpURLConnection connection = createHttpConnection(request);
73  			String method = request.getMethod().name();
74  			connection.setRequestMethod(method);
75  			connection.setDoInput(true);
76  			connection.setInstanceFollowRedirects("GET".equals(method));
77  			if ("PUT".equals(method) || "POST".equals(method)
78  					|| "PATCH".equals(method) || "DELETE".equals(method)) {
79  				connection.setDoOutput(true);
80  			} else {
81  				connection.setDoOutput(false);
82  			}
83  			// set headers
84  			HttpHeaders headers = request.getHeaders();
85  			if (headers == null) {
86  				headers = new HttpHeaders();
87  			}
88  			if (!headers.containsKey(HttpHeaders.HOST)) {
89  				headers.set(HttpHeaders.HOST, request.getURI().getHost());
90  			}
91  			// Add default accept headers
92  			if (!headers.containsKey(HttpHeaders.ACCEPT)) {
93  				headers.set(HttpHeaders.ACCEPT, "*/*");
94  			}
95  			// Add default user agent
96  			if (!headers.containsKey(HttpHeaders.USER_AGENT)) {
97  				headers.set(HttpHeaders.USER_AGENT, "jdk/httpclient");
98  			}
99  			for (Entry<String, List<String>> header : headers.entrySet()) {
100 				if (HttpHeaders.COOKIE.equalsIgnoreCase(header.getKey())) {
101 					connection.setRequestProperty(header.getKey(),
102 							StringUtil.join(header.getValue(), ';'));
103 				} else {
104 					for (String headerValue : header.getValue()) {
105 						connection.addRequestProperty(header.getKey(),
106 								headerValue != null ? headerValue : "");
107 					}
108 				}
109 			}
110 			// set inputstream
111 			HttpEntity httpEntity = request.getEntity();
112 			if (httpEntity != null) {
113 				connection.setUseCaches(false);
114 				if (httpEntity.getContentLength() > 0l) {
115 					connection.setRequestProperty(HttpHeaders.CONTENT_LENGTH,
116 							Long.toString(httpEntity.getContentLength()));
117 				}
118 				if (httpEntity.getContentType() != null) {
119 					connection.setRequestProperty(HttpHeaders.CONTENT_TYPE,
120 							httpEntity.getContentType().toString());
121 				}
122 			}
123 			// connect
124 			connection.connect();
125 			// open stream
126 			if (httpEntity != null) {
127 				OutputStream output = connection.getOutputStream();
128 				httpEntity.writeTo(output);
129 				output.flush();
130 				output.close();
131 			}
132 			// building response
133 			InputStream input = connection.getErrorStream() != null ? connection
134 					.getErrorStream() : connection.getInputStream();
135 			byte[] content = IOUtil.toByteArray(input);
136 			response = new SimpleHttpResponse(connection, content);
137 			input.close();
138 			handleResponse(response);
139 		} catch (IOException e) {
140 			throw new HttpClientException("I/O error on "
141 					+ request.getMethod().name() + " request for \""
142 					+ request.getURI().toString(), e);
143 		} finally {
144 			if (response != null) {
145 				response.close();
146 			}
147 		}
148 		return response;
149 	}
150 }