My client code was the problem. I had been thinking of the comet
interaction with the server as similar to a socket, open it once and
then read and write merrily from either end. I forgot that comet is
still operating over http and the client needs to send http headers for
each request. So the fix in my client code is simply to open a new
HttpURLConnection for each client request, which hopefully does not
establish a new socket connection to the server each time ("Each
HttpURLConnection instance is used to make a single request but the
underlying network connection to the HTTP server may be transparently
shared by other instances" -- from javadoc for HttpURLConnection). See
added "initConnection()" line below.
Peter
### from CometTestClient below ###
public void test() throws IOException {
out.println("test 1");
out.flush();
String line = read(urlConn.getInputStream());
System.out.println(line);
---> initConnection(); // reconnect to url - sends new http headers
out.println("test 2");
out.flush();
line = read(urlConn.getInputStream());
System.out.println(line);
out.close();
urlConn.disconnect();
}
Peter Warren wrote:
> Thanks for the suggestion. I changed the comet test servlet to read
> directly from the input stream as shown in the advanced io example. I'm
> still seeing the same behavior. No comet read event gets generated on
> the server, only the begin event which contains the client's first
> message. The client then sends its second message and blocks waiting
> for the server. No events are generated on the server in response to
> the client's second message. Any other tips for me?
>
> Thanks,
> Peter
>
> from the CometTestServlet:
>
> public void event(CometEvent cometEvent) throws IOException,
> ServletException {
> ...
> if (cometEvent.getEventType() == CometEvent.EventType.BEGIN) {
> log("Begin for session: " + request.getSession(true).getId());
> String clientMessage = read(request);
> if (clientMessage != null && clientMessage.length() > 0) {
> response.getWriter().println(clientMessage);
> response.getWriter().flush();
> }
> }
> ...
>
> private String read(HttpServletRequest request) throws IOException {
> InputStream is = request.getInputStream();
> StringBuffer inputBuffer = new StringBuffer();
> byte[] buf = new byte[512];
> do {
> int n = is.read(buf); // can throw an IOException
> if (n > 0) {
> inputBuffer.append(new String(buf, 0, n));
> log("Read " + n + " bytes: " + new String(buf, 0, n) + "
> for session: "
> + request.getSession(true).getId());
> } else if (n < 0) {
> log("comet read error");
> }
> } while (is.available() > 0);
> return inputBuffer.toString();
> }
>
> from the CometTestClient:
>
> public void test() throws IOException {
> out.println("test 1");
> out.flush();
>
> String line = read(urlConn.getInputStream());
> System.out.println(line);
>
> out.println("test 2");
> out.flush();
>
> line = read(urlConn.getInputStream());
> System.out.println(line);
>
> out.close();
> urlConn.disconnect();
> }
>
> private String read(InputStream is) throws IOException {
> StringBuffer inputBuffer = new StringBuffer();
> byte[] buf = new byte[512];
> do {
> int n = is.read(buf); // can throw an IOException
> if (n > 0) {
> inputBuffer.append(new String(buf, 0, n));
> } else if (n < 0) {
> return ("read error");
> }
> } while (is.available() > 0);
> return inputBuffer.toString();
> }
>
> Filip Hanik - Dev Lists wrote:
>
>> take a look at the documentation, the way you are reading it is
>> incorrect.
>> you need to take advantage of the available() method
>>
>> Filip
>>
>> Peter Warren wrote:
>>
>>> My BEGIN block in my comet servlet now looks like the code below (added
>>> a while loop to read until the buffer is empty). Is that what you had
>>> in mind? The buffer in the BEGIN event only contains the client's first
>>> message. Am I not emptying the buffer correctly? Although, I wouldn't
>>> expect the buffer to contain the client's second message since the
>>> client blocks for an ack from the server before sending its second
>>> message. Any other thoughts on what happens to the client's second
>>> message and why no READ event is generated?
>>>
>>> Thanks for your help,
>>> Peter
>>>
>>> if (cometEvent.getEventType() == CometEvent.EventType.BEGIN) {
>>> log("Begin for session: " +
>>> request.getSession(true).getId());
>>> BufferedReader reader =
>>> cometEvent.getHttpServletRequest().getReader();
>>> String line = null;
>>> while ((line = reader.readLine()) != null) {
>>> log("servlet received: " + line);
>>>
>>> cometEvent.getHttpServletResponse().getWriter().println("servlet
>>> received: " + line);
>>> cometEvent.getHttpServletResponse().getWriter().flush();
>>> }
>>> }
>>>
>>>
>>>
>>>> Filip Hanik wrote:
>>>>
>>>> it could be because the data from the request already came in with the
>>>>
>>>>
>>> request.
>>>
>>>
>>>> when the BEGIN happens, perform the actions as if there was a READ as
>>>>
>>>>
>>> well, ie, empty out the buffer.
>>>
>>>
>>>> Filip
>>>>
>>>>
>>> Peter Warren wrote:
>>>
>>>
>>>> The following client code generates a comet BEGIN event on the server
>>>> but not a subsequent READ event, as I was expecting. How come? Is my
>>>> code wrong? Are my expectations wrong? See sequence of events
>>>> commented in code below.
>>>>
>>>> // client test method that sends messages to server and listens for
>>>> responses
>>>> public void test() throws IOException {
>>>> out.println("test 1");
>>>> out.flush();
>>>>
>>>> // server receives client's message, generates a BEGIN event,
>>>> and sends response to client
>>>>
>>>> in = new BufferedReader(new
>>>> InputStreamReader(urlConn.getInputStream()));
>>>> System.out.println(in.readLine());
>>>>
>>>> // client receives server's response and prints it
>>>>
>>>> out.println("test 2");
>>>> out.flush();
>>>>
>>>> System.out.println(in.readLine());
>>>>
>>>> // client code blocks here waiting for server response.
>>>> // server never generates a READ event. How come?
>>>> // Does the HttpURLConnection (see full code below) need to be
>>>> set up differently?
>>>> // Am I using the PrintWriter incorrectly when sending to the
>>>> comet servlet?
>>>>
>>>> out.close();
>>>> urlConn.disconnect();
>>>> }
>>>>
>>>> Thanks for any help,
>>>> Peter
>>>>
>>>> -- system --
>>>>
>>>> using:
>>>> tomcat 6.0.13 on windows xp sp 2
>>>> java 1.6.0_01
>>>>
>>>> -- test client & comet servlet source below --
>>>>
>>>> ## begin test client ##
>>>>
>>>> import java.io.BufferedReader;
>>>> import java.io.IOException;
>>>> import java.io.InputStreamReader;
>>>> import java.io.PrintWriter;
>>>> import java.net.HttpURLConnection;
>>>> import java.net.URL;
>>>>
>>>> public class CometTestClient {
>>>>
>>>> private HttpURLConnection urlConn;
>>>>
>>>> private PrintWriter out;
>>>>
>>>> private BufferedReader in;
>>>>
>>>> public static void main(String[] args) throws Exception {
>>>> CometTestClient test = new CometTestClient();
>>>> test.test();
>>>> }
>>>>
>>>> public CometTestClient() throws IOException {
>>>> initConnection();
>>>> }
>>>>
>>>> private void initConnection() throws IOException {
>>>> URL url = new URL("http://127.0.0.1/CometTest");
>>>> urlConn = (HttpURLConnection) url.openConnection();
>>>> urlConn.setDoInput(true);
>>>> urlConn.setDoOutput(true);
>>>> urlConn.connect();
>>>> out = new PrintWriter(urlConn.getOutputStream());
>>>> }
>>>>
>>>> public void test() throws IOException {
>>>> out.println("test 1");
>>>> out.flush();
>>>>
>>>> in = new BufferedReader(new
>>>> InputStreamReader(urlConn.getInputStream()));
>>>> System.out.println(in.readLine());
>>>>
>>>> out.println("test 2");
>>>> out.flush();
>>>>
>>>> System.out.println(in.readLine());
>>>>
>>>> out.close();
>>>> urlConn.disconnect();
>>>> }
>>>> }
>>>>
>>>> ## end test client ##
>>>>
>>>> ## begin comet servlet ##
>>>>
>>>> import java.io.BufferedReader;
>>>> import java.io.IOException;
>>>>
>>>> import javax.servlet.ServletException;
>>>> import javax.servlet.http.HttpServlet;
>>>> import javax.servlet.http.HttpServletRequest;
>>>>
>>>> import org.apache.catalina.CometEvent;
>>>> import org.apache.catalina.CometProcessor;
>>>>
>>>> public class CometTestServlet extends HttpServlet implements
>>>> CometProcessor {
>>>> private static final long serialVersionUID = 5472498184127924791L;
>>>>
>>>> public void event(CometEvent cometEvent) throws IOException,
>>>> ServletException {
>>>> HttpServletRequest request =
>>>> cometEvent.getHttpServletRequest();
>>>> // don't want timeout events
>>>> cometEvent.setTimeout(1000000);
>>>> if (cometEvent.getEventType() == CometEvent.EventType.BEGIN) {
>>>> log("Begin for session: " +
>>>> request.getSession(true).getId());
>>>> BufferedReader reader =
>>>> cometEvent.getHttpServletRequest().getReader();
>>>> String line = reader.readLine();
>>>> if (line != null) {
>>>> log("servlet received: " + line);
>>>>
>>>> cometEvent.getHttpServletResponse().getWriter().println("servlet
>>>> received: " + line);
>>>>
>>>> cometEvent.getHttpServletResponse().getWriter().flush();
>>>> } else {
>>>> cometEvent.close();
>>>> }
>>>> } else if (cometEvent.getEventType() ==
>>>> CometEvent.EventType.ERROR) {
>>>> log("Error for session: " +
>>>> request.getSession(true).getId()
>>>> + ", " + cometEvent.getEventSubType());
>>>> cometEvent.close();
>>>> } else if (cometEvent.getEventType() ==
>>>> CometEvent.EventType.END) {
>>>> log("End for session: " +
>>>> request.getSession(true).getId());
>>>> cometEvent.close();
>>>> } else if (cometEvent.getEventType() ==
>>>> CometEvent.EventType.READ) {
>>>> log("Read for session: " +
>>>> request.getSession(true).getId());
>>>> BufferedReader reader =
>>>> cometEvent.getHttpServletRequest().getReader();
>>>> String line = reader.readLine();
>>>> if (line != null) {
>>>>
>>>> cometEvent.getHttpServletResponse().getWriter().println("servlet
>>>> received: " + line);
>>>> } else {
>>>> cometEvent.close();
>>>> }
>>>> }
>>>> }
>>>> }
>>>>
>>>> ## end comet servlet ##
>>>>
>>>> ---------------------------------------------------------------------
>>>> To start a new topic, e-mail: [email protected]
>>>> To unsubscribe, e-mail: [EMAIL PROTECTED]
>>>> For additional commands, e-mail: [EMAIL PROTECTED]
>>>>
>>>>
>>>>
>>>>
>>>>
>>> ---------------------------------------------------------------------
>>> To start a new topic, e-mail: [email protected]
>>> To unsubscribe, e-mail: [EMAIL PROTECTED]
>>> For additional commands, e-mail: [EMAIL PROTECTED]
>>>
>>>
>>>
>>>
>>>
>> ---------------------------------------------------------------------
>> To start a new topic, e-mail: [email protected]
>> To unsubscribe, e-mail: [EMAIL PROTECTED]
>> For additional commands, e-mail: [EMAIL PROTECTED]
>>
>>
>>
>>
>
> ---------------------------------------------------------------------
> To start a new topic, e-mail: [email protected]
> To unsubscribe, e-mail: [EMAIL PROTECTED]
> For additional commands, e-mail: [EMAIL PROTECTED]
>
>
>
>
---------------------------------------------------------------------
To start a new topic, e-mail: [email protected]
To unsubscribe, e-mail: [EMAIL PROTECTED]
For additional commands, e-mail: [EMAIL PROTECTED]