【问题标题】:Can you refresh or redisplay unflushed telnet input?您可以刷新或重新显示未刷新的 telnet 输入吗?
【发布时间】:2015-03-16 07:29:54
【问题描述】:

我正在编写一个老式的基于文本的 telnet 服务器,现在它是一个在 Scala 中具有基于 Akka actor 的 IO 的美化聊天室。正在发生的事情是客户端将开始输入某些内容,然后会发生一个事件,当它被写入时,它会清除任何已经输入的内容。在以下示例中,Tom 开始输入“说你好吗?”但是 Fred 在他只输入了“say How ar”之后就到达了,并且这个输入被清除了:

Tom > say How ar
Fred has arrived.
Tom > 

有没有办法让 telnet 重新显示它尚未刷新的输出缓冲区?

这里是服务器:

class TcpServer(port: Int) extends Actor {
  import TcpServer._
  import context.system

  val log = Logging(system, this)
  var connectionNum: Int = 1

  log.info(STARTING_SERVER)

  IO(Tcp) ! Bind(self, new InetSocketAddress("0.0.0.0", port))

  def receive = {
    case b @ Bound(localAddress) =>
      log.info(PORT_BOUND, localAddress)
    case c @ Connected(remote, local) =>
      log.info(CONNECTION_ACCEPTED)
      context.actorOf(ConnectionHandler.connectionProps(sender()), s"conn$connectionNum")
      connectionNum += 1
    case CommandFailed(_: Bind) =>
      log.error(BINDING_FAILED)
      context stop self
  }
}

这是 ConnectionHandler,它是伴随对象,以及它使用的消息案例类:

class ConnectionHandler(connection: ActorRef) extends Actor {
  import context._

  val log = Logging(context.system, this)

  connection ! Register(self)

  var delegate = actorOf(Props[LoginHandler], "login")
  watch(delegate)

  def receive = {
    case Received(data) =>
      val dataString = data.utf8String.trim
      log.info("Received data from connection: {}", dataString)
      delegate ! Input(dataString)

    case Output(content) =>
      connection ! Write(ByteString(content))

    case LoggedIn(user) =>
      unwatch(delegate)
      delegate ! PoisonPill

      delegate = actorOf(UserHandler.connectionProps(user), user.name.toLowerCase)
      watch(delegate)

    case Terminated =>
      log.warning("User delegate died unexpectedly.")
      connection ! ConfirmedClose

    case CloseConnection(message) =>
      connection ! Write(ByteString(message + "\n"))
      connection ! ConfirmedClose
      log.info("User quit.")

    case ConfirmedClosed =>
      log.info("Connection closed.")
      stop(self)

    case PeerClosed =>
      log.info("Connection closed by client.")
      stop(self)
  }
}

object ConnectionHandler {
  def connectionProps(connection: ActorRef): Props = Props(new ConnectionHandler(connection))
}

case class Input(input: String)
case class Output(output: String)
case class LoggedIn(user: User)
case class CloseConnection(message: String)

【问题讨论】:

    标签: scala telnet tcpserver akka-io


    【解决方案1】:

    好的,在最终正确地表达了我的谷歌查询之后,我在这里找到了我需要的内容: Force telnet client into character mode

    基本的解决方案是我强制客户端进入字符模式,并回显我关心的字符。这样做的好处是,现在我可以完成选项卡、命令历史记录以及不显示密码。

    这里是相关代码sn-p:

    val controlString = ByteString('\u00ff','\u00fb','\u0001','\u00ff','\u00fb','\u0003','\u00ff','\u00fc','\u0022')
    
    connection ! Write(controlString)
    

    【讨论】:

      猜你喜欢
      • 2018-10-01
      • 2012-04-15
      • 2020-01-04
      • 1970-01-01
      • 2021-05-07
      • 1970-01-01
      • 1970-01-01
      • 2019-11-09
      • 1970-01-01
      相关资源
      最近更新 更多