Close / Interupt a ConsoleReader.readLine() properly with JLine2

129 views
Skip to first unread message

Matthieu Manchon

unread,
Jun 25, 2020, 4:58:54 AM6/25/20
to jline-users
Hi,

I am working on a java 7 shell with JLine2 on CentOs, and when I try to interupt the Thread runing the ConsoleReader.readLine() or close the ConsoleReader, I got some error :

Here the ConsoleReader.close() error :
Exception in thread "Thread-602" java.lang.UnsupportedOperationException: read() with timeout cannot be called as non-blocking operation is disabled
    at jline.internal.NonBlockingInputStream.read(NonBlockingInputStream.java:132)
    at jline.internal.NonBlockingInputStream.read(NonBlockingInputStream.java:243)
    at jline.internal.InputStreamReader.read(InputStreamReader.java:257)
    at jline.internal.InputStreamReader.read(InputStreamReader.java:194)
    at jline.console.ConsoleReader.readCharacter(ConsoleReader.java:2151)
    at jline.console.ConsoleReader.readCharacter(ConsoleReader.java:2141)
    at jline.console.ConsoleReader.readBinding(ConsoleReader.java:2226)
    at jline.console.ConsoleReader.readLine(ConsoleReader.java:2467)
    at jline.console.ConsoleReader.readLine(ConsoleReader.java:2378)
    at jline.console.ConsoleReader.readLine(ConsoleReader.java:2366)
    at jline.console.ConsoleReader.readLine(ConsoleReader.java:2354)
    at com.mds.cli.interactiveshell.app.InteractiveShellApp$1.readLine(InteractiveShellApp.java:164)
    at com.mds.cli.interactiveshell.app.InteractiveShellApp$1.run(InteractiveShellApp.java:153)
    at java.lang.Thread.run(Thread.java:745)

Here the thead.interupt() error :
[ERROR] Failed to disable interrupt character
java.lang.InterruptedException
    at java.lang.Object.wait(Native Method)
    at java.lang.Object.wait(Object.java:503)
    at java.lang.UNIXProcess.waitFor(UNIXProcess.java:263)
    at jline.internal.TerminalLineSettings.waitAndCapture(TerminalLineSettings.java:339)
    at jline.internal.TerminalLineSettings.exec(TerminalLineSettings.java:311)
    at jline.internal.TerminalLineSettings.stty(TerminalLineSettings.java:282)
    at jline.internal.TerminalLineSettings.undef(TerminalLineSettings.java:158)
    at jline.UnixTerminal.disableInterruptCharacter(UnixTerminal.java:162)
    at jline.console.ConsoleReader.readLine(ConsoleReader.java:2452)
    at jline.console.ConsoleReader.readLine(ConsoleReader.java:2378)
    at jline.console.ConsoleReader.readLine(ConsoleReader.java:2366)
    at jline.console.ConsoleReader.readLine(ConsoleReader.java:2354)
    at com.mds.cli.interactiveshell.app.InteractiveShellApp$1.readLine(InteractiveShellApp.java:164)
    at com.mds.cli.interactiveshell.app.InteractiveShellApp$1.run(InteractiveShellApp.java:153)
    at java.lang.Thread.run(Thread.java:745)

If I interupt the thread AND close the ConsoleReader, my app is blocked and never exit.

Someone can explain me what I miss or do wrong ?

Here some code :
boolean exit = false;
ConsoleReader jlineConsole = new ConsoleReader();
Thread thread = new Thread(new Runnable() {

            @Override
            public void run() {
                try {
                    do {
                        readLine();
                    } while(exitCode == null);
                } catch (IOException e) {
                    exitCode = -1;
                }
            }
           
            private void readLine() throws IOException {
                try {
                    jlineConsole.setHandleLitteralNext(false);
                    jlineConsole.setHandleUserInterrupt(true);
                    String line = jlineConsole.readLine();
                    if(line != null) {
                        // add line in queue
                    }
                } catch(UserInterruptException ignore) { }
            }
        });
        thread.start();
        while (!exit) {
            String line = queue.poll();
            if (line!=null) {
                execute(line); // can set exit to true
            } else {
                queue.wait();
            }
        }
        thread.interrupt();
        //jlineConsole.close();

matthieu...@gmail.com

unread,
Aug 3, 2020, 9:52:16 AM8/3/20
to jline-users
Hello,

I finally succed to exit myJLine app without any error, with a terminal reset before the thread.interrupt(); And I don't try anymore to close the reader, I let the JVM release all at exit.

Thanks for JLine and this forum (helping a lot on many others topics).
Reply all
Reply to author
Forward
0 new messages