phpshellsshscreen-scrapingphpseclib

Programmatically navigate linux shell application


I'm trying to figure out if it would be possible to progmmatically navigate a linux shell application - text based.

Specifically I would like to achieve this by using PHP and phpSecLib, but if You know a better/easier way round this please pitch in.

I know how to use PHP+phpSecLib to log into the linux server via SSH, and run shell commands.

So we have this 3rd-party application at our backend server, where we have no option to access live data. The application has a report that we can generate, which will give us a "live" picture of various KPI's, however this report screen do not refresh automatically, thus one would have to escape back from the report and generate it again for updated KPI's

When the application is launched I'm presented with "splash screen" saying "Welcome to Ye Olde Application ver. 3.14159" (name is fictitious), shortly after a "screen/output" update happens and the "Main menu" is presented, where each menupoint is accessible by a keystroke (1-9a-z).

Main menu

                ┌────────────────────────────────────────────────┐
                │                                                │
                │   1    Foo                    bar              │
                │   2    Same                   procedure        │
                │   3    Rudolph                Reindeer         │
                │   4    Report                 generator        │
                │   5    Log-off                system           │
                │                                                │
                └────────────────────────────────────────────────┘

So in this case I would like to go into "4 Report generator" [Press 4]. After that the "screen/output" updates with a new submenu like the above, with other options. Here I would proceed into "1 Create new report" [Press 1], again a "screen/output" update. Now with new menu, go into "2 Superhandy Super-report" [Press 2].

After that i would like to save the text, from that report screen to a document for further parsing. But that's not the initial problem.

Another idea could be..

..to do it in shell-script (Bash) somehow with a macro or similar.


Solution

  • Figured it out myself ;-) Leaving it here if anybody else stumble upon the same problem.

    require_once('Net/SSH2.php');
    
    $ip = '127.0.0.1'; // The IP of the SSH server
    $username = 'username';
    $password = 'password';     
    
    $ssh = new Net_SSH2($ip);
    if (!$ssh->login($username, $password)) {
        exit('Login Failed');
    }
    
    // Set a reasonable timeout (secs)
    $ssh->setTimeout(5);        
    // Prepare ANSI "screen reader"
    $ansi = new File_ANSI();
    $ansi->setDimensions(200, 30); // set number of columns and rows of each screen
    
    // Should probably do some stuff here to make sure we're ready for next step
        
    $ssh->write("/usr/bin/3rdpartybackendapp\n"); // Start the backend application
    // Read until the "Please select" text appears
    $ssh->read('Please select');
    
    $ssh->write("4"); // Select "4: Report generator"
    $ansi->appendString($ssh->read('Please select'));
    
    $ssh->write("1"); // Select "1: Create reports"
    $ansi->appendString($ssh->read('Please select'));
        
    $ssh->write("h"); // Select "H: Dashboard report
    $ansi->appendString($ssh->read('Q  Quit'));
        
    $output = strip_tags($ansi->getScreen()) . PHP_EOL . PHP_EOL; // Collect the screen
    $fulloutput .= $output;
        
    // The report has multiple pages, so continue to read pages 
    // until there are no more pages to read. 
    // Application does not show "N  Next" on last page.
    while(false !== strpos($output, 'N  Next')) {
        $ssh->write("n"); // Select "N: Next page
        $ansi->appendString($ssh->read('Q  Quit'));
    
        $output = strip_tags($ansi->getScreen()) . PHP_EOL . PHP_EOL; // Collect the screen
        $fulloutput .= $output;
    }
    
    echo strip_tags($fulloutput); // outputs HTML
    
    // Terminate the SSH session
    $ssh->disconnect();
    

    Update

    Changed from extended My_File_ANSI to File_ANSI in the example above, see comments.