Come posso screen-raschiare uscita da telnet in Perl?
Domanda
I può impostare una connessione telnet in Perl senza problemi, e hanno appena scoperto Maledizioni, e mi chiedo se posso usare i due insieme per raschiare l'uscita dalla sessione telnet.
posso visualizzare su una riga, colonna base il contenuto del STDOUT utilizzando il semplice script di seguito:
use Curses;
my $win = new Curses;
$win->addstr(10, 10, 'foo');
$win->refresh;
my $thischar=$win->inch(10,10);
print "Char $thischar\n";
E con il sottostante posso aprire una connessione telnet e inviare \ ricevere comandi senza alcun problema:
use net::telnet;
my $telnet = new Net::Telnet (Timeout => 9999,);
$telnet->open($ipaddress) or die "telnet open failed\n";
$telnet->login($user,$pass);
my $output = $telnet->cmd("command string");
... Ma quello che mi piacerebbe davvero fare è ottenere la risposta telnet (che comprende i caratteri di controllo del terminale) e poi cercare una base fila \ colonna utilizzando maledizioni. Qualcuno sa di un modo per collegare le due cose insieme? Mi sembra che le maledizioni possono operare solo su STDOUT
Soluzione
Siete alla ricerca di :: VT102 , che emula un VT102 terminale (convertendo i caratteri di controllo del terminale in uno stato schermo virtuale). C'è un esempio che mostra come usarlo con Net :: Telnet in VT102 / examples / telnet-usage.pl (la directory esempi si trova all'interno della directory VT102 per qualche motivo).
E 'stato di circa 7 anni da quando ho usato questo (il sistema che stavo automatizzando passato a un'interfaccia web-based), ma è abituato a lavorare.
Altri suggerimenti
Le maledizioni fa il contrario. È una libreria C per ottimizzare aggiornamenti dello schermo da un programma scrivere su un terminale, originariamente progettato per essere utilizzato su una connessione seriale lenta. Non ha capacità di raschiare un layout da una sequenza di caratteri di controllo.
Una scommessa migliore sarebbe un emulatore di terminale che ha un'API con la capacità di fare questo tipo di schermo raschiatura. Fuori della parte superiore della mia testa io non sono sicuro se eventuali emulatori di terminale open-source fanno questo, ma ci sono quelli certamente commerciali disponibili che possono.
Probabilmente si desidera qualcosa di simile a Aspettatevi
use strict;
use warnings;
use Expect;
my $exp = Expect->spawn("telnet google.com 80");
$exp->expect(15, #timeout
[
qr/^Escape character.*$/,
sub {
$exp->send("GET / HTTP/1.0\n\n");
exp_continue;
}
]
);
Se si interagisce esclusivamente con i comandi di testo normale e le risposte, è possibile utilizzare Aspettatevi per script che, in caso contrario, è possibile utilizzare Term :: VT102 , che consente all'utente di filtrare raschiare (leggere specifiche parti dello schermo, inviare messaggi di testo, gestire eventi in scorrimento, il movimento del cursore, i cambiamenti di contenuto dello schermo, e altri) le applicazioni che utilizzano le sequenze di escape VT102 per il controllo dello schermo (ad esempio, un'applicazione che utilizza la libreria curses).
In alternativa, è possibile utilizzare il lo script di comando per questo.
Dalla pagina man di Solaris:
DESCRIZIONE
L'utilità
script
fa un record di tutto stampato sul vostro schermo. Il record viene scritto filename . Se nessun nome di file è dato, il record viene salvato nel file dattiloscritto ...Il comando forcelle script e crea un sub-shell, in base al valore di $ SHELL, e registra il testo da questo sessione. Lo script termina quando il shell termina a forcella o quando Control-D viene digitato.
voterei anche per la risposta Expect. Dovevo fare qualcosa di simile da un'applicazione gui'ish. Il trucco (anche se noioso) per aggirare i caratteri di controllo era di mettere a nudo tutti i personaggi misc dalle stringhe restituite. E 'sorta di dipende da come disordinato lo stridore schermo finisce per essere.
Questa è la mia funzione da quello script come esempio:
# Trim out the curses crap
sub trim {
my @out = @_;
for (@out) {
s/\x1b7//g;
s/\x1b8//g;
s/\x1b//g; # remove escapes
s/\W\w\W//g;
s/\[\d\d\;\d\dH//g; #
s/\[\?25h//g;
s/\[\?25l//g;
s/\[\dm//g;
s/qq//g;
s/Recall//g;
s/\357//g;
s/[^0-9:a-zA-Z-\s,\"]/ /g;
s/\s+/ /g; # Extra spaces
}
return wantarray ? @out : $out[0];
}