Author: remy.maucherat(a)jboss.com
Date: 2008-03-07 12:59:02 -0500 (Fri, 07 Mar 2008)
New Revision: 487
Modified:
trunk/java/org/apache/catalina/connector/CometEventImpl.java
trunk/java/org/apache/catalina/connector/CoyoteAdapter.java
trunk/java/org/jboss/web/comet/CometEvent.java
Log:
- Rework event.close, which is likely going to be asynchronous to actual IO (so if it does
a real close right away,
there will be a problem).
Modified: trunk/java/org/apache/catalina/connector/CometEventImpl.java
===================================================================
--- trunk/java/org/apache/catalina/connector/CometEventImpl.java 2008-03-07 12:57:03 UTC
(rev 486)
+++ trunk/java/org/apache/catalina/connector/CometEventImpl.java 2008-03-07 17:59:02 UTC
(rev 487)
@@ -77,11 +77,8 @@
}
public void close() throws IOException {
- if (request == null) {
- throw new
IllegalStateException(sm.getString("cometEvent.nullRequest"));
- }
request.setComet(false);
- response.finishResponse();
+ request.resume();
}
public EventType getType() {
Modified: trunk/java/org/apache/catalina/connector/CoyoteAdapter.java
===================================================================
--- trunk/java/org/apache/catalina/connector/CoyoteAdapter.java 2008-03-07 12:57:03 UTC
(rev 486)
+++ trunk/java/org/apache/catalina/connector/CoyoteAdapter.java 2008-03-07 17:59:02 UTC
(rev 487)
@@ -141,12 +141,21 @@
boolean error = false;
boolean read = false;
+ boolean close = false;
try {
+ if (response.isClosed()) {
+ // The response IO has been closed asynchronously, so call end
+ // in most cases
+ request.getEvent().setType(CometEvent.EventType.END);
+ request.setComet(false);
+ close = true;
+ }
if (status == SocketStatus.OPEN_READ) {
- if (response.isClosed()) {
+ if (!request.isComet()) {
// The event has been closed asynchronously, so call end instead
of
// read to cleanup the pipeline
request.getEvent().setType(CometEvent.EventType.END);
+ close = true;
} else {
try {
// Fill the read buffer of the servlet layer
@@ -167,18 +176,22 @@
}
}
} else if (status == SocketStatus.OPEN_WRITE) {
- if (response.isClosed()) {
+ if (!request.isComet()) {
// The event has been closed asynchronously, so call end instead
of
// read to cleanup the pipeline
request.getEvent().setType(CometEvent.EventType.END);
+ close = true;
} else {
request.getEvent().setType(CometEvent.EventType.WRITE);
}
} else if (status == SocketStatus.OPEN_CALLBACK) {
- if (response.isClosed()) {
+ if (!request.isComet()) {
// The event has been closed asynchronously, so call end instead
of
// read to cleanup the pipeline
+ // In nearly all cases, the close does a resume which will end
up
+ // here
request.getEvent().setType(CometEvent.EventType.END);
+ close = true;
} else {
request.getEvent().setType(CometEvent.EventType.EVENT);
}
@@ -190,11 +203,13 @@
error = true;
} else if (status == SocketStatus.STOP) {
request.getEvent().setType(CometEvent.EventType.END);
+ close = true;
} else if (status == SocketStatus.TIMEOUT) {
- if (response.isClosed()) {
+ if (!request.isComet()) {
// The event has been closed asynchronously, so call end instead
of
// read to cleanup the pipeline
request.getEvent().setType(CometEvent.EventType.END);
+ close = true;
} else {
request.getEvent().setType(CometEvent.EventType.TIMEOUT);
}
@@ -205,16 +220,13 @@
// Calling the container
connector.getContainer().getPipeline().getFirst().event(request,
response, request.getEvent());
- if (!error && !response.isClosed() &&
(request.getAttribute(Globals.EXCEPTION_ATTR) != null)) {
+ if (!error && (request.getAttribute(Globals.EXCEPTION_ATTR) !=
null)) {
// An unexpected exception occurred while processing the event, so
// error should be called
request.getEvent().setType(CometEvent.EventType.ERROR);
error = true;
connector.getContainer().getPipeline().getFirst().event(request,
response, request.getEvent());
}
- /*if (response.isClosed() || !request.isComet()) {
- res.action(ActionCode.ACTION_COMET_END, null);
- } else*/
if (!error && read && request.ready()) {
// If this was a read and not all bytes have been read, or if no
data
// was read from the connector, then it is an error
@@ -223,6 +235,9 @@
error = true;
connector.getContainer().getPipeline().getFirst().event(request,
response, request.getEvent());
}
+ if (error || close) {
+ response.finishResponse();
+ }
return (!error);
} catch (Throwable t) {
if (!(t instanceof IOException)) {
@@ -233,7 +248,7 @@
} finally {
req.getRequestProcessor().setWorkerThreadName(null);
// Recycle the wrapper request and response
- if (error || response.isClosed() || !request.isComet()) {
+ if (error || close || response.isClosed()) {
res.action(ActionCode.ACTION_COMET_END, null);
request.recycle();
request.setFilterChain(null);
Modified: trunk/java/org/jboss/web/comet/CometEvent.java
===================================================================
--- trunk/java/org/jboss/web/comet/CometEvent.java 2008-03-07 12:57:03 UTC (rev 486)
+++ trunk/java/org/jboss/web/comet/CometEvent.java 2008-03-07 17:59:02 UTC (rev 487)
@@ -107,12 +107,8 @@
/**
* Ends the request, which marks the end of the comet session. This will send
* back to the client a notice that the server has no more data to send
- * as part of this request. If this method is called from a Tomcat provided thread
- * (during the processing of an event), the container will not call an END event.
- * If this method is called asynchronously, an END event will be sent to the
- * servlet (note that this event will be sent whenever another event would have
- * been sent, such as a READ or TIMEOUT event, so the servlet may not recieve the
- * END event immediately after the asynchronous close).
+ * as part of this request. An END event will be sent to the
+ * servlet.
*
* @throws IOException if an IO exception occurs
*/
Show replies by date