Question

I'm trying to test a console application that uses jline for handling interaction with the user.

I'm starting the application using ProcessBuilder which gives me access to the application's:

I was expecting to use a workflow similar to this:

  • Start Application
  • Read Output until I see the application's prompt >
  • Send Input for my test case, e.g. login
  • Read Output until I see the expect response, e.g. Username:
  • and so on

However, the test just freezes. Stepping through the code, it appears that jline is freezing on JNI calls to _getch on Windows. I'm guessing that the problem is because I am running Java from ProcessBuilder which is headless so there is no console and that is confusing windows. Setting -Djline.terminal=jline.UnsupportedTerminal as per the Jline docs doesn't help either.

I've found a thread discussing Python pexpect for testing a (non-java) readline application.

Question: how can I test a jline based application using just java tools?

Was it helpful?

Solution

I gave up on trying to test just using java tools and went with using the python pexpect library to execute the console application. The tests were integrated into the maven build, but required a *nix host to run them:

import unittest
import pexpect
import os
import signal
import subprocess
import urllib
import urllib2
import json

from wiremock import WiremockClient

class TestInteractive(unittest.TestCase):

    cli_cmd = "java -jar " + os.environ["CLI_JAR"]

    # ... code omitted for brevity 

    def test_interactive_mode_username_and_password_sent_to_server(self):
        child = pexpect.spawn(TestInteractive.cli_cmd, timeout=10)
        child.expect   ('Username: ')
        child.sendline ('1234')
        child.expect   ('Password: ')
        child.sendline ('abcd')
        child.expect   ('Successfully authenticated')
        child.expect   ('stratos> ')
        child.sendline ('exit')
        child.expect   (pexpect.EOF)
        # CLI sends GET request to mock server url /stratos/admin/coookie
        self.assertEqual(self.wiremock.get_cookie_auth_header(), "1234:abcd")

    # ... code omitted for brevity

if __name__ == '__main__':
    try: 
        unittest.main()
    # handle CTRL-C
    except KeyboardInterrupt:
        # shut down wiremock 
        TestInteractive.wiremock.stop()
        exit(1) 

The full CLI test suite for the project I was working on can be found here.

Licensed under: CC-BY-SA with attribution
Not affiliated with StackOverflow
scroll top