Time out for reading from a stream

I use InputStream.read() to read from a pipe after creating a sub-process. I had a problem that the process got stuck, so I wrote a quite complicated code with coroutines, sleep, available() and other tests to make sure I never get stuck and that join() will always return immediately.

When I’d written similar code in C It was very easy - I didn’t even need to create a thread, since I could read directly from the output with a timeout. However, the process.outputStream and errorStream don’t let me access the socket and use a timeout.

It seems that Java and then Kotlin decided to not allow that. Why?

What’s your input stream exactly? Often, when we create a stream, e.g. we connect to a network socket, we specify the timeout.

Something like that:

    ProcessBuilder()
        .directory(workingDir)
        .redirectOutput(ProcessBuilder.Redirect.PIPE)
        .redirectError(ProcessBuilder.Redirect.PIPE)
        .command(command)
        .start()

I can’t get the socket from process.inputStream

Possibly a simple withTimeout does the trick for you?

withTimeout(1000L) {
    // read from input stream...
}

Thank you. I tried to use it like this:

    fun read() =  runBlocking {
            withTimeoutOrNull(500) {
                reader.readLine()
            }
        }

   fun readAllLines() {
     while (true) {
       val line = read()
       if (line != null)
         processLine(line)
       else
         break 
   }
 }

For some reason I have to call it twice, before and after the process ends, but I think it is due to the operating system and not to Kotlin or JVM

  readAllLines()
  process.waitFor()
  readAllLines()