Scala Programming Language
  1. Scala Programming Language
  2. SI-3442

weird interaction between repl and console input

    Details

    • Type: Bug Bug
    • Status: Closed
    • Priority: Minor Minor
    • Resolution: Won't Fix
    • Affects Version/s: None
    • Fix Version/s: None
    • Component/s: Repl / Interpreter
    • Labels:
    • Environment:

      console, repl

      Description

      Attempting to use java.io.Console to read a password throws the repl into weirdness and only reads in a single character:

      Welcome to Scala version 2.8.0.RC1 (Java HotSpot(TM) 64-Bit Server VM, Java 1.6.0_17).
      Type in expressions to have them evaluated.
      Type :help for more information.
      
      scala> val console = System.console
      console: java.io.Console = java.io.Console@12781046
      
      scala> console.readPassword("Enter pw: ")
      Enter pw: 
      res0: Array[Char] = Array(p)
      
      scala> rreess00((00))
      
      res1: Char = p
      
      scala> ::qquuiitt
      

      Also, when calls to the regular readLine method are made, the characters are not echoed to the screen:

      Welcome to Scala version 2.8.0.RC1 (Java HotSpot(TM) 64-Bit Server VM, Java 1.6.0_17).
      Type in expressions to have them evaluated.
      Type :help for more information.
      
      scala> Console.readLine("Enter stuff: ")
      Enter stuff: res0: String = stuff
      
      scala> :quit
      

      Both of these work as expected if run as a script instead of from the repl. Scripts are attached.

      1. test.scala
        0.1 kB
        Jira Admin
      2. test2.scala
        0.1 kB
        Jira Admin

        Activity

        Hide
        Erik Engbrecht added a comment -

        reads a password from the console

        Show
        Erik Engbrecht added a comment - reads a password from the console
        Hide
        Erik Engbrecht added a comment -

        regular console input via readLine

        Show
        Erik Engbrecht added a comment - regular console input via readLine
        Hide
        Paul Phillips added a comment -

        This works, and as it does, realistically I'm unlikely to pursue this without a very specific diagnosis as to how it should be changed.

        Console.withIn(System.in) { Console.readLine("Enter stuff:") }
        
        Show
        Paul Phillips added a comment - This works, and as it does, realistically I'm unlikely to pursue this without a very specific diagnosis as to how it should be changed. Console.withIn(System.in) { Console.readLine("Enter stuff:") }
        Hide
        Erik Engbrecht added a comment -

        Ok, I did a little research... The Jython repl essentially behaves like the Scala repl. Using java.io.Console essentially won't work, and input is not echoed when reading from stdin using a BufferedReader.

        JRuby's repl succeeds at echoing characters that are going into a BufferedReader, but fails the same as Jython and Scala with java.io.Console.

        I don't think this is high priority, Merely mildly annoying, and mostly annoying because I didn't know of the limitation. I won't get any heartburn if it's marked as wontfix or given a very low priority.

        Show
        Erik Engbrecht added a comment - Ok, I did a little research... The Jython repl essentially behaves like the Scala repl. Using java.io.Console essentially won't work, and input is not echoed when reading from stdin using a BufferedReader. JRuby's repl succeeds at echoing characters that are going into a BufferedReader, but fails the same as Jython and Scala with java.io.Console. I don't think this is high priority, Merely mildly annoying, and mostly annoying because I didn't know of the limitation. I won't get any heartburn if it's marked as wontfix or given a very low priority.
        Hide
        bethard added a comment -

        As far as I can tell, the `Console.withIn` thing doesn't solve the java.io.Console problem at all - you can still only type a single character:

        scala> Console.withIn(System.in) {System.console.readLine("username: ")}
        username: res10: java.lang.String = a
        
        scala> bcde
        

        This matters less for `System.console.readLine` since you can always use `Console.readLine` instead, but what are you supposed to use instead of `System.console.readPassword`?

        Show
        bethard added a comment - As far as I can tell, the `Console.withIn` thing doesn't solve the java.io.Console problem at all - you can still only type a single character: scala> Console.withIn(System.in) {System.console.readLine("username: ")} username: res10: java.lang.String = a scala> bcde This matters less for `System.console.readLine` since you can always use `Console.readLine` instead, but what are you supposed to use instead of `System.console.readPassword`?
        Hide
        Paul Phillips added a comment -

        Replying to [comment:4 bethard]:
        > As far as I can tell, the `Console.withIn` thing doesn't solve the java.io.Console problem at all - you can still only type a single character:
        >


        > scala> Console.withIn(System.in)

        {System.console.readLine("username: ")}

        That's because that's not the code which was given.

        > This matters less for `System.console.readLine` since you can always use `Console.readLine` instead

        That's the code which was given.

        > but what are you supposed to use instead of `System.console.readPassword`?

        What you're supposed to do, if that is not a rhetorical question, is fix it and submit a patch. It's not like the ticket was closed "everything's fine".

        Show
        Paul Phillips added a comment - Replying to [comment:4 bethard] : > As far as I can tell, the `Console.withIn` thing doesn't solve the java.io.Console problem at all - you can still only type a single character: > > scala> Console.withIn(System.in) {System.console.readLine("username: ")} That's because that's not the code which was given. > This matters less for `System.console.readLine` since you can always use `Console.readLine` instead That's the code which was given. > but what are you supposed to use instead of `System.console.readPassword`? What you're supposed to do, if that is not a rhetorical question, is fix it and submit a patch. It's not like the ticket was closed "everything's fine".
        Hide
        bethard added a comment -

        I guess I misunderstood the comment "this works". I thought the ticket was moved to low priority because the `Console.withIn` thing was being proffered as a workaround (but it's not). Sorry for the confusion.

        Anyway, here's a workaround (using jline which appears to be included by scala already):

        scala> new jline.ConsoleReader().readLine('*')
        ******
        res0: java.lang.String = abdefg
        
        Show
        bethard added a comment - I guess I misunderstood the comment "this works". I thought the ticket was moved to low priority because the `Console.withIn` thing was being proffered as a workaround (but it's not). Sorry for the confusion. Anyway, here's a workaround (using jline which appears to be included by scala already): scala> new jline.ConsoleReader().readLine('*') ****** res0: java.lang.String = abdefg
        Hide
        Adriaan Moors added a comment -

        Closing since there's a workaround. We're moving to vanilla jline, btw: https://issues.scala-lang.org/browse/SI-7604

        Show
        Adriaan Moors added a comment - Closing since there's a workaround. We're moving to vanilla jline, btw: https://issues.scala-lang.org/browse/SI-7604
        Hide
        Antoine Gourlay added a comment -

        In 2.10+, this workaround doesn't seem to work, but you can just get into power mode and then

        scala> repl.in.readLine("enter something: ")
        enter something: hello world
        res0: String = hello world
        

        If only that readLine method was used as the default readLine in the REPL...

        Show
        Antoine Gourlay added a comment - In 2.10+, this workaround doesn't seem to work, but you can just get into power mode and then scala> repl.in.readLine("enter something: ") enter something: hello world res0: String = hello world If only that readLine method was used as the default readLine in the REPL...

          People

          • Assignee:
            Unassigned
            Reporter:
            Erik Engbrecht
            TracCC:
            bethard, Johannes Rudolph, Paul Phillips
          • Votes:
            0 Vote for this issue
            Watchers:
            3 Start watching this issue

            Dates

            • Created:
              Updated:
              Resolved:

              Development