[SP-pm] Perl para automação em acesso a x3270 IBM
Marcio - Google
marciorp at gmail.com
Thu Jul 12 19:15:23 PDT 2012
Em 12 de julho de 2012 09:30, Eden Cardim <edencardim em gmail.com> escreveu:
>>>>>> "Marcio" == Marcio <- Google <marciorp em gmail.com>> writes:
>
> Marcio> Olá Prof. Eden,
> Marcio> Montei esse primeiro exemplo, tipo "Olá mundo!", mais esbarrei em um
> Marcio> erro que não consigo resolver.
>
> Marcio> #!/usr/bin/perl
>
> Marcio> use strict;
> Marcio> use warnings;
> Marcio> use Expect;
>
> Marcio> my $exp = Expect->spawn('s3270');
>
> Marcio> $exp->log_file('/home/marcio/teste3.log');
>
> Marcio> my $cmd1 = "connect(10.1.8.192:23)\n";
> Marcio> $cmd1 .= "wait(InputField)\n";
>
> Marcio> $exp->send($cmd1);
> Marcio> $exp->expect(100, [qr/.{1920}/ => sub {
> Marcio> my($self) = @_;
> Marcio> print $self->match;
>
> Marcio> exp_continue;
> Marcio> },
> Marcio> timeout => sub { die 'o sistema parou de responder' }
> Marcio> ]
> Marcio> )
>
> Marcio> Roda certinho, pelo menos não dá erro nenhum, o problema é que como se
> Marcio> no lugar do "\n" no final dos comandos, ele trocasse por "^M", e ai dá
> Marcio> erro no s3270. No mesmo exemplo usando o IPC::Run não acontece isso.
>
> Tem certeza que é o *mesmo* exemplo? Posta aí pra gente ver. Esses "^M"
> são da codificação do seu terminal local. Se fosse um problema pro s3270
> você não veria nada no output.
>
Olá o código ai, é o mesmo exemplo só que usando o IPC::Run. Por
desencargo, rodei os dois agora a pouco novamente, e mesma coisa. Com
o Expect dá erro, e com o IPC:Run não.
#!/usr/bin/perl
my @s3270 = s3270;
use IPC::Run qw( start pump finish timeout );
$IPCRUNDEBUG=details;
my $h = start \@s3270, \$in, \$out, \$err, timeout( 100 );
$in .= "connect(10.1.8.192:23)\n";
$in .= "wait(InputField)\n";
finish $h or die "s3270 returned $?";
warn $err if $err;
print $out;
Saída no terminal:
U U U C(10.1.8.192) I 4 43 80 0 0 0x0 0.167
ok
U F U C(10.1.8.192) I 4 24 80 15 34 0x0 -
ok
> Marcio> Veja a saída no terminal:
>
> Marcio> connect(10.1.8.192:23)^M
> Marcio> wait(InputField)^M
> Marcio> L U U N N 4 24 80 0 0 0x0 0.024^M
> Marcio> error^M
> Marcio> data: Wait: Not connected^M
> Marcio> L U U N N 4 24 80 0 0 0x0 -^M
> Marcio> error^M
>
> Marcio> E o arquivo de log (/home/marcio/teste3.log):
>
> Marcio> connect(10.1.8.192:23)^M
> Marcio> wait(InputField)^M
> Marcio> L U U N N 4 24 80 0 0 0x0 0.026
> Marcio> error
> Marcio> data: Wait: Not connected
> Marcio> L U U N N 4 24 80 0 0 0x0 -
> Marcio> error
>
> Marcio> Tem alguma ideia?
>
> Bom, é difícil depurar à distância asssim. Me parece que o erro não tem
> nada a ver com o \n, o que está acontecendo é que o terminal do outro
> lado está esperando mais input e você não está fornencendo, por isso dá
> erro. Eu não entendo nada de TN3270 mas geralmente esses terminais mais
> antigos precisam negociar o encerramento da conexão.
Na verdade não sou especialista também, mais ele processa cada linha
como um comando individual, e no exemplo ai o primeiro é para conectar
no host. Quando eu rodo ele no modo interativo, onde vou digitando os
comando, no final de cada linha teclo <ENTER> e ele processa o
comando. No script o \n faz a função de teclar o <ENTER> no modo
interativo.
>
> Marcio> Em tempo, essa expressão (qr/.{1920}/) pega o retorno com
> Marcio> 1920 caracteres. Vou colocar várias expressões, agora como
> Marcio> faço uma tipo "default", se não casar com nenhuma das
> Marcio> anteriores cai nessa última?
>
> Sim, e já está aí no exemplo: é o timeout => sub {} faz isso. Essa
> subroutina roda se passar o tempo que você especificou (nesse caso, 100
> segundos) e a saída não casar com nenhuma das expressões.
Então, isso que não entendi. Se o retorno não casar com nenhuma
expressão ele vai cair aqui, mais só depois de ocorrer o timeout, ou
seja, mesmo que ocorra algum retorno, ele só vai processar depois de
100 segundos (ou o que eu definir). É isso? Se for, volta a pergunta,
tem como colocar uma expressão default que seja processada antes do
timeout se nenhuma das outras casar?
>
> Marcio> Desculpe a lerdeza, mais é que como disse não sou
> Marcio> programador, tó quebrando um galho para resolver um problema
> Marcio> do meu sistema Asterisk.
>
> Não precisa se desculpar em todos os posts, nós já entendemos ;)
É que fico até constrangido fazendo perguntas tão banais a mestres ... :-)
Brinco com microcontroladores (eletrônica) por hobby, e a coisa mais
difícil e conseguir ajuda de algum expert/engenheiro nos fóruns
especializados da areá. Os kras se consideram superiores, e nunca
foram aprendizes e tiveram dúvidas.
>
> O problema agora tem mais a ver com o entendimento do funcionamento do
> TN3270 do que com programação. A única referência a respeito disso que
> eu encontrei foi isso aqui: http://ibm.co/PSEH13
Então, para mim o TN3270 não tem muito mistério ou o que mexer, pois
quando eu conecto eu já caio em uma tela da aplicação e a partir dai é
digitar usuário/senha e ir selecionando opções no menus e depois
digitando e lendo dados. Eu não uso comandos e outros recursos.
Quando conecto pelo s3270 no modo interativo ou mesmo o c3270, eu
consigo fazer todas as operações necessárias.
Outro detalhes é que o exemplo com o IPC::Run funcionou, então não
pode ser alguns detalhe do Expect?
Pelo que eu andei lendo da documentação, to achando que o Expect é
mesmo a melhor opção em relação ao IPC::Run. Desculpa Nelson ... :-)
>
> Boa sorte
Obrigado, to precisando ... ;-)
>
> --
> Eden Cardim
> +55 11 9644 8225
Abs,
Marcio.
More information about the SaoPaulo-pm
mailing list