📄 httpconnectionhelper.java
字号:
.displayDebug(
"[HTTPConnectionHelper append] ("
+ len
+ " bytes appended to "
+ (this.connectionStatus == STATUS_BEFORE_SERVER_CONNECTION ? " current ByteArrayEncoder"
: " socket") + ")", 101);
}
return this;
}
/**
* write a string to the current HTTP request.
*
* @param str The string to write
* @return The current HTTPConnectionHelper
* @throws JUploadIOException If any problem occurs during the writing
* operation.
* @see #append(byte[])
*/
public HTTPConnectionHelper append(String str) throws JUploadIOException {
this.uploadPolicy.displayDebug("[HTTPConnectionHelper append] " + str,
70);
if (this.connectionStatus == STATUS_BEFORE_SERVER_CONNECTION) {
this.byteArrayEncoder.append(str);
} else if (this.connectionStatus == STATUS_WRITING_REQUEST) {
ByteArrayEncoder bae = new ByteArrayEncoderHTTP(this.uploadPolicy,
this.byteArrayEncoder.getBoundary(), this.byteArrayEncoder
.getEncoding());
bae.append(str);
bae.close();
this.append(bae);
}
return this;
}
/**
* Appends a string to the current HTTP request.
*
* @param bae The ByteArrayEncoder to write. It is expected to be correctly
* encoded. That is: it is up to the caller to check that its
* encoding is the same as the current HTTP request encoding.
* @return The current HTTPConnectionHelper
* @throws JUploadIOException If any problem occurs during the writing
* operation.
* @see #append(byte[])
*/
public HTTPConnectionHelper append(ByteArrayEncoder bae)
throws JUploadIOException {
this.uploadPolicy.displayDebug("[HTTPConnectionHelper append] "
+ bae.getString(), 70);
return this.append(bae.getEncodedByteArray());
}
/**
* Read the response of the server. This method delegates the work to the
* HTTPInputStreamReader. handles the chunk HTTP response.
*
* @return The HTTP status. Should be 200, when everything is right.
* @throws JUploadException
*/
public int readHttpResponse() throws JUploadException {
// This method expects that the connection is writing data to the
// server.
if (this.connectionStatus != STATUS_WRITING_REQUEST) {
throw new JUploadIOException(
"Bad status of the connectionHelper in initRequest: "
+ getStatusLabel());
}
this.connectionStatus = STATUS_READING_RESPONSE;
// Let's connect in InputStream to read this server response.
if (this.httpInputStreamReader == null) {
this.httpInputStreamReader = new HTTPInputStreamReader(this,
this.uploadPolicy);
}
// Let's do the job
try {
this.outputStream.flush();
} catch (IOException ioe) {
throw new JUploadIOException("flushing outputStream, in "
+ getClass().getName() + ".readHttpResponse()");
}
this.httpInputStreamReader.readHttpResponse();
if (this.httpInputStreamReader.gotClose) {
// RFC 2868, section 8.1.2.1
dispose();
}
// We got the response
this.connectionStatus = STATUS_CONNECTION_CLOSED;
//
return this.httpInputStreamReader.gethttpStatusCode();
}
// ////////////////////////////////////////////////////////////////////////////////////
// /////////////////////// PRIVATE METHODS
// ////////////////////////////////////////////////////////////////////////////////////
/**
* creating of a new {@link ByteArrayEncoderHTTP}, and initializing of the
* following header items: First line (POST currentProtocol URI), Host,
* Connection, Keep-Alive, Proxy-Connection.
*
* @throws JUploadIOException
*/
private void initByteArrayEncoder() throws JUploadIOException {
if (this.byteArrayEncoder != null && !this.byteArrayEncoder.isClosed()) {
this.byteArrayEncoder.close();
this.byteArrayEncoder = null;
}
this.byteArrayEncoder = new ByteArrayEncoderHTTP(this.uploadPolicy,
this.boundary);
this.connectionStatus = STATUS_BEFORE_SERVER_CONNECTION;
this.proxy = null;
try {
this.proxy = ProxySelector.getDefault().select(this.url.toURI())
.get(0);
} catch (URISyntaxException e) {
throw new JUploadIOException("Error while managing url "
+ this.url.toExternalForm(), e);
}
this.useProxy = ((this.proxy != null) && (this.proxy.type() != Proxy.Type.DIRECT));
this.useSSL = this.url.getProtocol().equals("https");
// Header: Request line
// Let's clear it. Useful only for chunked uploads.
this.byteArrayEncoder.append(this.method);
this.byteArrayEncoder.append(" ");
if (this.useProxy && (!this.useSSL)) {
// with a proxy we need the absolute URL, but only if not
// using SSL. (with SSL, we first use the proxy CONNECT method,
// and then a plain request.)
this.byteArrayEncoder.append(this.url.getProtocol()).append("://")
.append(this.url.getHost());
}
this.byteArrayEncoder.append(this.url.getPath());
// Append the query params.
// TODO: This probably can be removed as we now have everything in POST
// data. However in order to be
// backwards-compatible, it stays here for now. So we now provide
// *both* GET and POST params.
if (null != this.url.getQuery() && !"".equals(this.url.getQuery()))
this.byteArrayEncoder.append("?").append(this.url.getQuery());
this.byteArrayEncoder.append(" ").append(
this.uploadPolicy.getServerProtocol()).append("\r\n");
// Header: General
this.byteArrayEncoder.append("Host: ").append(this.url.getHost())
.append("\r\nAccept: */*\r\n");
// We do not want gzipped or compressed responses, so we must
// specify that here (RFC 2616, Section 14.3)
this.byteArrayEncoder.append("Accept-Encoding: identity\r\n");
// Seems like the Keep-alive doesn't work properly, at least on my
// local dev (Etienne).
if (!this.uploadPolicy.getAllowHttpPersistent()) {
this.byteArrayEncoder.append("Connection: close\r\n");
} else {
if (!this.bChunkEnabled
|| this.bLastChunk
|| this.useProxy
|| !this.uploadPolicy.getServerProtocol()
.equals("HTTP/1.1")) { // RFC 2086, section 19.7.1
this.byteArrayEncoder.append("Connection: close\r\n");
} else {
this.byteArrayEncoder.append("Keep-Alive: 300\r\n");
if (this.useProxy)
this.byteArrayEncoder
.append("Proxy-Connection: keep-alive\r\n");
else
this.byteArrayEncoder.append("Connection: keep-alive\r\n");
}
}
// Get specific headers for this upload.
this.uploadPolicy.onAppendHeader(this.byteArrayEncoder);
}
/**
* Indicates whether the current socket should be reused ... if any.
*/
private boolean isKeepAlive() {
if (this.socket == null) {
return true;
} else if (!this.uploadPolicy.getAllowHttpPersistent()) {
return false;
} else {
if (!this.bChunkEnabled
|| this.bLastChunk
|| this.useProxy
|| !this.uploadPolicy.getServerProtocol()
.equals("HTTP/1.1")) { // RFC 2086, section 19.7.1
return false;
} else {
return true;
}
}
}
/**
* Construction of a random boundary, to separate the uploaded files, in the
* HTTP upload request.
*
* @return The calculated boundary.
*/
private final String calculateRandomBoundary() {
StringBuffer sbRan = new StringBuffer(11);
sbRan.append("-----------------------------");
String alphaNum = "1234567890abcdefghijklmnopqrstuvwxyz";
int num;
for (int i = 0; i < 11; i++) {
num = (int) (Math.random() * (alphaNum.length() - 1));
sbRan.append(alphaNum.charAt(num));
}
return sbRan.toString();
}
// ////////////////////////////////////////////////////////////////////////////////////
// /////////////////// OVERRIDE OF OutputStream METHODS
// ////////////////////////////////////////////////////////////////////////////////////
/** {@inheritDoc} */
@Override
public void write(int b) throws IOException {
try {
append(b);
} catch (JUploadIOException e) {
// Hum, HTTPConnectionHelper catch IOException, and throws a
// JUploadIOException. Now we get the cause, that is the original
// IOException. Not optimized.
if (e.getCause() == null) {
// This should not happen
throw new IOException(e);
} else if (e.getCause() instanceof IOException) {
throw (IOException) e.getCause();
} else {
// Hum, can something like an OutOfMemory. We must throw it.
throw new IOException(e.getCause());
}
}
}
/** {@inheritDoc} */
@Override
public void write(byte[] b, int off, int len) throws IOException {
try {
append(b, off, len);
} catch (JUploadIOException e) {
// Hum, HTTPConnectionHelper catch IOException, and throws a
// JUploadIOException. Now we get the cause, that is the original
// IOException. Not optimized.
if (e.getCause() == null) {
// This should not happen
throw new IOException(e);
} else if (e.getCause() instanceof IOException) {
throw (IOException) e.getCause();
} else {
// Hum, can something like an OutOfMemory. We must throw it.
throw new IOException(e.getCause());
}
}
}
/** {@inheritDoc} */
@Override
public void write(byte[] b) throws IOException {
write(b, 0, b.length);
}
/**
* This method is the override of {@link OutputStream#close()} one. It may
* not been called. You must use the {@link #sendRequest()} or
* {@link #readHttpResponse()} methods instead.
*
* @see java.io.OutputStream#close()
*/
@Override
public void close() throws IOException {
throw new IOException("Forbidden action. Please use the "
+ getClass().getName() + ".sendRequest() method");
}
/**
* Flushes the output stream. Useful only when the HTTPConnectionHelper is
* writing to the socket toward the server, that is when the status is:
* STATUS_WRITING_REQUEST.
*
* @see java.io.OutputStream#flush()
*/
@Override
public void flush() throws IOException {
if (this.connectionStatus == STATUS_WRITING_REQUEST) {
this.outputStream.flush();
} else {
throw new IOException("Wrong status in " + getClass().getName()
+ ".flush method: " + getStatusLabel());
}
}
}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -