Author: veithen
Date: Mon Jun 1 16:58:10 2009
New Revision: 780724
URL: http://svn.apache.org/viewvc?rev=780724&view=rev
Log:
Simplified the handling of chunked and identity encoding.
Added:
webservices/commons/trunk/modules/tcpmon/modules/tcpmon-core/src/main/java/org/apache/ws/commons/tcpmon/core/filter/ReadOnlyFilterWrapper.java
(with props)
webservices/commons/trunk/modules/tcpmon/modules/tcpmon-core/src/main/java/org/apache/ws/commons/tcpmon/core/filter/http/EntityCompletionListener.java
(with props)
Removed:
webservices/commons/trunk/modules/tcpmon/modules/tcpmon-core/src/main/java/org/apache/ws/commons/tcpmon/core/filter/EntityProcessor.java
Modified:
webservices/commons/trunk/modules/tcpmon/modules/tcpmon-core/src/main/java/org/apache/ws/commons/tcpmon/core/filter/http/ChunkedDecoder.java
webservices/commons/trunk/modules/tcpmon/modules/tcpmon-core/src/main/java/org/apache/ws/commons/tcpmon/core/filter/http/HttpFilter.java
webservices/commons/trunk/modules/tcpmon/modules/tcpmon-core/src/main/java/org/apache/ws/commons/tcpmon/core/filter/http/IdentityDecoder.java
Added:
webservices/commons/trunk/modules/tcpmon/modules/tcpmon-core/src/main/java/org/apache/ws/commons/tcpmon/core/filter/ReadOnlyFilterWrapper.java
URL:
http://svn.apache.org/viewvc/webservices/commons/trunk/modules/tcpmon/modules/tcpmon-core/src/main/java/org/apache/ws/commons/tcpmon/core/filter/ReadOnlyFilterWrapper.java?rev=780724&view=auto
==============================================================================
---
webservices/commons/trunk/modules/tcpmon/modules/tcpmon-core/src/main/java/org/apache/ws/commons/tcpmon/core/filter/ReadOnlyFilterWrapper.java
(added)
+++
webservices/commons/trunk/modules/tcpmon/modules/tcpmon-core/src/main/java/org/apache/ws/commons/tcpmon/core/filter/ReadOnlyFilterWrapper.java
Mon Jun 1 16:58:10 2009
@@ -0,0 +1,32 @@
+/*
+ * Copyright 2004,2005 The Apache Software Foundation.
+ *
+ * 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 org.apache.ws.commons.tcpmon.core.filter;
+
+/**
+ * Wrapper that makes a filter read-only.
+ */
+public class ReadOnlyFilterWrapper implements StreamFilter {
+ private final StreamFilter parent;
+
+ public ReadOnlyFilterWrapper(StreamFilter parent) {
+ this.parent = parent;
+ }
+
+ public void invoke(Stream stream) {
+ parent.invoke(new ReadOnlyStream(stream));
+ }
+}
Propchange:
webservices/commons/trunk/modules/tcpmon/modules/tcpmon-core/src/main/java/org/apache/ws/commons/tcpmon/core/filter/ReadOnlyFilterWrapper.java
------------------------------------------------------------------------------
svn:eol-style = native
Modified:
webservices/commons/trunk/modules/tcpmon/modules/tcpmon-core/src/main/java/org/apache/ws/commons/tcpmon/core/filter/http/ChunkedDecoder.java
URL:
http://svn.apache.org/viewvc/webservices/commons/trunk/modules/tcpmon/modules/tcpmon-core/src/main/java/org/apache/ws/commons/tcpmon/core/filter/http/ChunkedDecoder.java?rev=780724&r1=780723&r2=780724&view=diff
==============================================================================
---
webservices/commons/trunk/modules/tcpmon/modules/tcpmon-core/src/main/java/org/apache/ws/commons/tcpmon/core/filter/http/ChunkedDecoder.java
(original)
+++
webservices/commons/trunk/modules/tcpmon/modules/tcpmon-core/src/main/java/org/apache/ws/commons/tcpmon/core/filter/http/ChunkedDecoder.java
Mon Jun 1 16:58:10 2009
@@ -16,18 +16,23 @@
package org.apache.ws.commons.tcpmon.core.filter.http;
-import org.apache.ws.commons.tcpmon.core.filter.EntityProcessor;
import org.apache.ws.commons.tcpmon.core.filter.Stream;
import org.apache.ws.commons.tcpmon.core.filter.StreamException;
+import org.apache.ws.commons.tcpmon.core.filter.StreamFilter;
import org.apache.ws.commons.tcpmon.core.filter.StreamUtil;
/**
* Entity processor that processes HTTP chunked transfer encoding.
*/
-public class ChunkedDecoder implements EntityProcessor {
+public class ChunkedDecoder implements StreamFilter {
+ private final EntityCompletionListener listener;
private int remaining = -1; // bytes remaining in the current chunk
- public boolean process(Stream stream) {
+ public ChunkedDecoder(EntityCompletionListener listener) {
+ this.listener = listener;
+ }
+
+ public void invoke(Stream stream) {
while (stream.available() > 0) {
if (remaining > 0) {
int c = Math.min(stream.available(), remaining);
@@ -35,7 +40,7 @@
remaining -= c;
} else if (remaining == 0) {
if (stream.available() < 2) {
- return false;
+ return;
}
if (stream.get(0) == '\r' && stream.get(1) == '\n') {
stream.discard(2);
@@ -46,15 +51,16 @@
} else {
int eolIndex = StreamUtil.searchEndOfLine(stream);
if (eolIndex == -1) {
- return false;
+ return;
}
remaining = Integer.parseInt(StreamUtil.getAsciiString(stream,
0, eolIndex), 16);
stream.discard(eolIndex+2);
if (remaining == 0) {
- return true;
+ listener.onComplete();
+ return;
}
}
}
- return false;
+ return;
}
}
Added:
webservices/commons/trunk/modules/tcpmon/modules/tcpmon-core/src/main/java/org/apache/ws/commons/tcpmon/core/filter/http/EntityCompletionListener.java
URL:
http://svn.apache.org/viewvc/webservices/commons/trunk/modules/tcpmon/modules/tcpmon-core/src/main/java/org/apache/ws/commons/tcpmon/core/filter/http/EntityCompletionListener.java?rev=780724&view=auto
==============================================================================
---
webservices/commons/trunk/modules/tcpmon/modules/tcpmon-core/src/main/java/org/apache/ws/commons/tcpmon/core/filter/http/EntityCompletionListener.java
(added)
+++
webservices/commons/trunk/modules/tcpmon/modules/tcpmon-core/src/main/java/org/apache/ws/commons/tcpmon/core/filter/http/EntityCompletionListener.java
Mon Jun 1 16:58:10 2009
@@ -0,0 +1,21 @@
+/*
+ * Copyright 2004,2005 The Apache Software Foundation.
+ *
+ * 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 org.apache.ws.commons.tcpmon.core.filter.http;
+
+public interface EntityCompletionListener {
+ void onComplete();
+}
Propchange:
webservices/commons/trunk/modules/tcpmon/modules/tcpmon-core/src/main/java/org/apache/ws/commons/tcpmon/core/filter/http/EntityCompletionListener.java
------------------------------------------------------------------------------
svn:eol-style = native
Modified:
webservices/commons/trunk/modules/tcpmon/modules/tcpmon-core/src/main/java/org/apache/ws/commons/tcpmon/core/filter/http/HttpFilter.java
URL:
http://svn.apache.org/viewvc/webservices/commons/trunk/modules/tcpmon/modules/tcpmon-core/src/main/java/org/apache/ws/commons/tcpmon/core/filter/http/HttpFilter.java?rev=780724&r1=780723&r2=780724&view=diff
==============================================================================
---
webservices/commons/trunk/modules/tcpmon/modules/tcpmon-core/src/main/java/org/apache/ws/commons/tcpmon/core/filter/http/HttpFilter.java
(original)
+++
webservices/commons/trunk/modules/tcpmon/modules/tcpmon-core/src/main/java/org/apache/ws/commons/tcpmon/core/filter/http/HttpFilter.java
Mon Jun 1 16:58:10 2009
@@ -20,9 +20,8 @@
import java.util.LinkedList;
import java.util.List;
-import org.apache.ws.commons.tcpmon.core.filter.EntityProcessor;
import org.apache.ws.commons.tcpmon.core.filter.HeaderParser;
-import org.apache.ws.commons.tcpmon.core.filter.ReadOnlyStream;
+import org.apache.ws.commons.tcpmon.core.filter.ReadOnlyFilterWrapper;
import org.apache.ws.commons.tcpmon.core.filter.Stream;
import org.apache.ws.commons.tcpmon.core.filter.StreamFilter;
import org.apache.ws.commons.tcpmon.core.filter.StreamUtil;
@@ -31,7 +30,7 @@
/**
* Base class for {...@link HttpRequestFilter} and {...@link
HttpResponseFilter}.
*/
-public abstract class HttpFilter implements StreamFilter {
+public abstract class HttpFilter implements StreamFilter,
EntityCompletionListener {
private static final int STATE_FIRST_LINE = 0;
private static final int STATE_HEADER = 1;
private static final int STATE_CONTENT = 2;
@@ -42,7 +41,7 @@
private int state = STATE_FIRST_LINE;
private final Headers headers = new Headers();
private ContentFilterFactory contentFilterFactory;
- private EntityProcessor transferDecoder;
+ private StreamFilter transferDecoder;
private StreamFilter[] contentFilterChain;
public HttpFilter(boolean decodeTransferEncoding) {
@@ -96,6 +95,11 @@
}
headerParser.skip();
state = STATE_CONTENT;
+ if (transferDecoder != null) {
+ stream.pushFilter(decodeTransferEncoding
+ ? transferDecoder
+ : new
ReadOnlyFilterWrapper(transferDecoder));
+ }
if (contentFilterChain != null) {
for (int i=contentFilterChain.length-1; i>=0; i--)
{
stream.pushFilter(contentFilterChain[i]);
@@ -106,23 +110,6 @@
return;
}
}
- case STATE_CONTENT: {
- if (transferDecoder != null) {
- Stream decoderStream =
- decodeTransferEncoding ? stream : new
ReadOnlyStream(stream);
- if (transferDecoder.process(decoderStream)) {
- state = STATE_COMPLETE;
- if (contentFilterChain != null) {
- for (int i=0; i<contentFilterChain.length;
i++) {
- stream.popFilter();
- }
- }
- completed();
- }
- break;
- }
- // Fall through
- }
default:
stream.skipAll();
}
@@ -138,10 +125,10 @@
String name = header.getName();
String value = header.getValue();
if (name.equalsIgnoreCase("Content-Length")) {
- transferDecoder = new IdentityDecoder(Integer.parseInt(value));
+ transferDecoder = new IdentityDecoder(Integer.parseInt(value),
this);
} else if (name.equalsIgnoreCase("Transfer-Encoding")) {
if (value.equals("chunked")) {
- transferDecoder = new ChunkedDecoder();
+ transferDecoder = new ChunkedDecoder(this);
}
} else if (name.equalsIgnoreCase("Content-Type")) {
if (contentFilterFactory != null) {
@@ -153,4 +140,9 @@
((HeaderHandler)it.next()).handleHeaders(headers);
}
}
+
+ public void onComplete() {
+ state = STATE_COMPLETE;
+ completed();
+ }
}
Modified:
webservices/commons/trunk/modules/tcpmon/modules/tcpmon-core/src/main/java/org/apache/ws/commons/tcpmon/core/filter/http/IdentityDecoder.java
URL:
http://svn.apache.org/viewvc/webservices/commons/trunk/modules/tcpmon/modules/tcpmon-core/src/main/java/org/apache/ws/commons/tcpmon/core/filter/http/IdentityDecoder.java?rev=780724&r1=780723&r2=780724&view=diff
==============================================================================
---
webservices/commons/trunk/modules/tcpmon/modules/tcpmon-core/src/main/java/org/apache/ws/commons/tcpmon/core/filter/http/IdentityDecoder.java
(original)
+++
webservices/commons/trunk/modules/tcpmon/modules/tcpmon-core/src/main/java/org/apache/ws/commons/tcpmon/core/filter/http/IdentityDecoder.java
Mon Jun 1 16:58:10 2009
@@ -16,23 +16,27 @@
package org.apache.ws.commons.tcpmon.core.filter.http;
-import org.apache.ws.commons.tcpmon.core.filter.EntityProcessor;
import org.apache.ws.commons.tcpmon.core.filter.Stream;
+import org.apache.ws.commons.tcpmon.core.filter.StreamFilter;
/**
* Entity processor that processes HTTP identity transfer encoding.
*/
-public class IdentityDecoder implements EntityProcessor {
+public class IdentityDecoder implements StreamFilter {
+ private final EntityCompletionListener listener;
private int remaining;
- public IdentityDecoder(int contentLength) {
+ public IdentityDecoder(int contentLength, EntityCompletionListener
listener) {
remaining = contentLength;
+ this.listener = listener;
}
- public boolean process(Stream stream) {
+ public void invoke(Stream stream) {
int c = Math.min(stream.available(), remaining);
stream.skip(c);
remaining -= c;
- return remaining == 0;
+ if (remaining == 0) {
+ listener.onComplete();
+ }
}
}