Link to home
Start Free TrialLog in
Avatar of hanneman
hanneman

asked on

java.net.socket cannot read

Hi,

I am accessing java objects through Cold Fusion (CFMX 6.1), and attempting to do a write+read using sockets.
I can do this fine if I do a "GET /index.cfm", but if I merely write a string to the socket, e.g. "00172AR", then the bufferedreader fails to read the returned string (i know the remote socket is returning  a string because I have tested it with a C++ socket program, and also done a packet sniff on the server).

The bufferedreader must be failing because the inputstream always returns 0 from its .available() method.

Any help most appreciated. 500 points (would give more but 500 is limit?)

here is my CF function, it uses CFscript, and nearly all the method calls to the java objects should be identical to Java.


<cffunction name="SocketIO" returntype="struct" access="public" output="true">
            <cfargument name="address" type="string" required="true">
            <cfargument name="port" type="numeric" required="true">
            <cfargument name="write_lines" type="string" required="true">
            <cfargument name="read_lines" type="numeric" required="false" default="1">
            <cfargument name="timeout" type="numeric" required="false" default=3000>
            <cfset var str = "empty">
            <cfset var socket       = createObject("java","java.net.Socket")>
            <cfset var instr       = createObject("java","java.io.InputStreamReader")>
            <cfset var input       = createObject("java","java.io.BufferedReader")>
            <cfset var output       = createObject("java","java.io.PrintStream")>
            <cfset var i = 1>
            <cfset var response = structnew()>
            <cfset response.data = arraynew(1)>
            <cfset response.connection = 0>
            <cfset response.output = 0>
            <cfset response.input = 0>
            <cfset response.status = 1>
            <cfset response.bytesavailable = 0>
            <cfscript>
                                                            
                  /** initialize our socket connection to the requested host **/
                  socket.init(arguments.address,arguments.port);
                  socket.setKeepAlive(true);
                  socket.setSoTimeout(arguments.timeout);
                  
                  if(socket.isConnected()){
                  
                        response.connection = 1;
                  
                        /** initialize our input/output streams  for reading and writing to the socket **/
                        
                        try{
                              
                              output.init(socket.getOutputStream(),true);
                              sock_in = socket.getInputStream();
                              instr.init(sock_in);
                              input.init(instr);
                                                      
                              if(not output.checkError()){
                                    output.println(arguments.write_lines);
                                    output.flush();
                                    
                                    if(not output.checkError()){
                                          response.output = 1;
                                    }
                              }
                              
                        }catch(Any err){
                              arrayappend(response.data,err.message);
                              response.output = 0;
                              response.status = 0;
                        }                        
                        
                        
                        /**if write was successful and there are bytes to read, then read**/
                                                                                                                                    
                        if(response.output and sock_in.available() gt 0){
                              
                              /** read all the requested lines from the input stream **/
                              response.bytesavailable = sock_in.available();                              
                              try{
                                                            
                                    for(i=1; i LTE read_lines; i=i+1){
                                          arrayappend(response.data,input.readLine());
                                    }
                                    
                              }catch(Any err){
                                    arrayappend(response.data,err.message);
                                    response.status = 0;
                              }
                              
                        }else{
                              response.status = 0;
                        }
                                    
                  }
                                    
                  /** close all our open streams/buffers/sockets **/
                  try{
                        input.close();
                        output.close();
                        inStr.close();
                        socket.close();      
                  }catch(Any err){
                        //don't do anything, if we got this far, we still want to return our response
                  }
                  
                  return response;
            </cfscript>
      </cffunction>

-H
Avatar of zzynx
zzynx
Flag of Belgium image

I quote:
Class InputStream

available()
The available method for class InputStream always returns 0.
This method should be overridden by subclasses.

Avatar of hanneman
hanneman

ASKER

Ah, interesting zzynx, i will take that out, i had seen it used in some java code, so I thought i would try it.

If I take out all checking like that, the line:

input.readLine()

will return either "Read Timed Out" or "Connection Reset" if I increase the timeout to a large number.

managed to solve it myself:

just do inputstream.read(), it will get back one byte at a time, which i can concatenate into a string.

funny that readline() didnt seem to work though!

-H

>> funny that readline() didnt seem to work though
A line is considered to be terminated by any one of a line feed ('\n'), a carriage return ('\r'), or a carriage return followed immediately by a linefeed.
ASKER CERTIFIED SOLUTION
Avatar of zzynx
zzynx
Flag of Belgium image

Link to home
membership
This solution is only available to members.
To access this solution, you must be a member of Experts Exchange.
Start Free Trial
Cheers anyway zzynx!
I guess the guys running the socket server arent putting in a "line ends here" flag of any kind!
-H
hanneman,
if you feel like I helped you a little bit, you can always ask for the points to be decremented (to say 50)
Just a proposal ;°)
yeah okay! i have been beating my head against this brick wall for a week now, and without your first comment, i probably wouldnt have been able to solve it myself.... so:

ee_ai_construct (btw, very imaginative name for a robot....) please decrement points to 250 and give to zzynx.

am now going to the pub to have a beer and maybe dance a jig on a table....... :-)
Thanks for appreciating my efforts trying to help you.
Have a good beer/dance ;°)