scala - 如何为阻塞调用设置超时?

标签 scala sockets serversocket blocking

我有一个与多个客户端一起工作的多线程聊天服务器(每个客户端都在一个新线程中处理)。

如果客户端断开连接,服务器上的相关线程将卡在 inputstream.readLine() 上,这是一个阻塞调用。

如何设置某种超时,以便在 2000 毫秒后关闭套接字并释放线程而没有响应?

class Handler(socket: Socket) extends Runnable {
  def run() : Unit = {
    val inputstream = new BufferedReader(new InputStreamReader(socket.getInputStream()))
    val outputstream = new BufferedWriter(new OutputStreamWriter(socket.getOutputStream()))
    var break = false
    while(break != true){
      val input = inputstream.readLine() // blocking call
// how do i time out after 2000ms?
      input match {
        case "update" =>
          outputstream.write("message")
          outputstream.newLine()
          outputstream.flush()
        case _ => // any other input, break and close socket
          break = true
      }
    }
    socket.close()
  }
}

object ChatServer extends App {
  val server = new ServerSocket(10000)
  while(true) {
    val socket = server.accept // blocking call
    (new Thread(new Handler(socket))).start()
    // some condition{
    //   server.close()
    // }
  }
}

最佳答案

您可以使用 BufferedReader.ready() :

True if the next read() is guaranteed not to block for input, false otherwise. Note that returning false does not guarantee that the next read will block.


class Handler(socket: Socket) extends Runnable {
  def run(): Unit = {
    val inputstream = new BufferedReader(new InputStreamReader(socket.getInputStream))
    val outputstream = new BufferedWriter(new OutputStreamWriter(socket.getOutputStream))

    var break = false
    val startTime = System.currentTimeMillis()

    while (!break) {
      if (inputstream.ready()) {
        val input = inputstream.readLine()
        input match {
          case "update" =>
            outputstream.write("message")
            outputstream.newLine()
            outputstream.flush()
          case _ => // any other input, break and close socket
            break = true
        }
      } else if (System.currentTimeMillis() - startTime >= 2000) {
        break = true
      }
    }
    socket.close()
  }
}

关于scala - 如何为阻塞调用设置超时?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/59443189/

相关文章:

scala - 如何避免 KNN 搜索的 for 循环?

java - 带有 spring mvc 的 scala 中的 JSR 303 ConstraintValidator

python - 使用 urllib2 或任何其他 http 库读取超时

android - 如何在android中通过套接字建立客户端到客户端的语音通话

java - javafx之间的socket通信

java - Java 中的 SSLServerSocket 和 SSLSocket 握手异常

java - Scala IDE - Play 2 Eclipse 插件不突出显示 Scala HTML 模板的语法

mysql - 如何从 apache-spark 中的数据帧列中的重复值中仅选择第一行?

java - Android套接字连接但无法写入

c - 为什么代码显示段错误?