1

i got a problem in parsing when i use HTTPGET specially TIMEOUT handling and get response trough HttpResponse and passto xmlR.parse(new InputSource(instream)); and make rest procedure. but there are throw error:

05-08 11:03:38.637: WARN/System.err(522): java.io.IOException: Attempted read on closed stream.
05-08 11:03:38.667: WARN/System.err(522):     at org.apache.http.conn.EofSensorInputStream.isReadAllowed(EofSensorInputStream.java:127)
05-08 11:03:38.667: WARN/System.err(522):     at org.apache.http.conn.EofSensorInputStream.read(EofSensorInputStream.java:176)
05-08 11:03:38.677: WARN/System.err(522):     at org.apache.harmony.xml.ExpatParser.parseFragment(ExpatParser.java:515)
05-08 11:03:38.677: WARN/System.err(522):     at org.apache.harmony.xml.ExpatParser.parseDocument(ExpatParser.java:478)
05-08 11:03:38.677: WARN/System.err(522):     at org.apache.harmony.xml.ExpatReader.parse(ExpatReader.java:317)
05-08 11:03:38.677: WARN/System.err(522):     at org.apache.harmony.xml.ExpatReader.parse(ExpatReader.java:275)
05-08 11:03:38.677: WARN/System.err(522):     at com.housedisplay.mapspec.MyMapActivity.Sendsarchparameter(MyMapActivity.java:334)
05-08 11:03:38.687: WARN/System.err(522):     at com.housedisplay.mapspec.MyMapActivity.access$0(MyMapActivity.java:289)
05-08 11:03:38.697: WARN/System.err(522):     at com.housedisplay.mapspec.MyMapActivity$SearchATask.doInBackground(MyMapActivity.java:251)
05-08 11:03:38.697: WARN/System.err(522):     at com.housedisplay.mapspec.MyMapActivity$SearchATask.doInBackground(MyMapActivity.java:1)
05-08 11:03:38.697: WARN/System.err(522):     at android.os.AsyncTask$2.call(AsyncTask.java:252)
05-08 11:03:38.697: WARN/System.err(522):     at java.util.concurrent.FutureTask$Sync.innerRun(FutureTask.java:305)
05-08 11:03:38.697: WARN/System.err(522):     at java.util.concurrent.FutureTask.run(FutureTask.java:137)
05-08 11:03:38.697: WARN/System.err(522):     at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1081)
05-08 11:03:38.697: WARN/System.err(522):     at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:574)
05-08 11:03:38.697: WARN/System.err(522):     at java.lang.Thread.run(Thread.java:1020)

Code:: (timeout code based on this answer by kuester2000)

HttpGet httpGet = new HttpGet(strURL.toURI());
            HttpParams httpParameters = new BasicHttpParams();
            // Set the timeout in milliseconds until a connection is established.
            // The default value is zero, that means the timeout is not used. 
            int timeoutConnection = 3000;
            HttpConnectionParams.setConnectionTimeout(httpParameters, timeoutConnection);
            // Set the default socket timeout (SO_TIMEOUT) 
            // in milliseconds which is the timeout for waiting for data.
            int timeoutSocket = 5000;
            HttpConnectionParams.setSoTimeout(httpParameters, timeoutSocket);

            DefaultHttpClient httpClient = new DefaultHttpClient(httpParameters);
            HttpResponse response = httpClient.execute(httpGet);
            
            
            HttpEntity entity = response.getEntity();
            InputStream instream = entity.getContent();
            if (entity != null) {
                
                strResponse = convertStreamToString(instream);

                
            }
        /**********test*******/
            SAXParserFactory saxPF = SAXParserFactory.newInstance();
            
            SAXParser saxP = saxPF.newSAXParser();
            XMLReader xmlR = saxP.getXMLReader();
            System.out.println("url >>>>>" + strURL);
            HandlerFromLatLongCustom myXMLHandler = new HandlerFromLatLongCustom();
            xmlR.setContentHandler(myXMLHandler);
            xmlR.parse(new InputSource(instream));
            instream.close();
Ryan M
  • 18,333
  • 31
  • 67
  • 74
Nikunj Patel
  • 21,853
  • 23
  • 89
  • 133

1 Answers1

2

I suspect this is the problem:

strResponse = convertStreamToString(instream);

My guess is that that method (which you haven't shown) closes the stream. Aside from anything else, it will at least have read the stream, which will make it hard to read again later on...

You can either read the entire response into a byte array, which you can then wrap in as many ByteArrayInputStreams as you want, or you could use strResponse as the source to parse. That could raise encoding issues though.

It's possible that HttpClient will do all this for you - that you can simply write:

instream = entity.getContent();

and get the same data again - I don't know enough about the details around whether the stream returned is effectively "live" or whether the client code reads the data and caches it.

Also note that this code is extremely suspicious:

HttpEntity entity = response.getEntity();
InputStream instream = entity.getContent();
if (entity != null) {
    ...

If entity is null, the second line will already have thrown a NullPointerException, making the check on the third line pretty pointless...

Jon Skeet
  • 1,421,763
  • 867
  • 9,128
  • 9,194
  • better to use, strResponse = EntityUtils.toString(entity); – user370305 May 08 '12 at 06:03
  • @user370305: Potentially, yes - but again, if that consumes the network stream, there's the same problem. Do you know offhand whether it does? Fundamentally we can only read from the network once - so if the data is needed in two forms, *something* has to read it and remember it. – Jon Skeet May 08 '12 at 06:06