Como usar a sessão ssh sem formatação de cor

1

Como criar uma sessão ssh por ssh foo@bar , exceto nenhum formato de cor? A única exigência é que a configuração seja declarada no comando ssh e não possa ser definida no arquivo de configuração.

Como um aparte, a razão é que eu quero obter o resultado do shell ssh para um programa Scala, git repos mais detalhes se você estiver interessado . Portanto, os códigos de cores, como [03m (talvez outros), devem ser removidos. Eu não posso esperar que o host remoto faça algumas configurações e não deixe nenhuma cor.

UPDATE

  1. Sobre a biblioteca JSch SSH, há algumas configurações para explicar:

    1. setPtyType("dumb") , o parâmetro dumb definindo a sessão com dumb terminal de emulação semelhante a Linux , VT100 etc. O terminal dumb emulation não é um código de cores no resultado. Use echo $TERM imprimirá dumb depois de definir essa propriedade.
    2. setPty(bool enable) padrão é false , mas se eu especificar a configuração setPty(false) , o resultado será interrompido. Infelizmente eu não encontrei uma API para obter os valores de pty em tempo de execução e a biblioteca é a falta de documentos, mesmo que seja a biblioteca SSH padrão de fato de Java.
  2. porque eu quero usar o ssh em um ssh?

    1. Esse recurso é necessário porque algum arquivo de chave pode estar no host remoto. Portanto, preciso fazer o login do host remoto primeiro e depois fazer login de outro host.
    2. faça o login de um terminal e use ssh connect para outro host é uma operação normal.
  3. Qual é a saída da biblioteca Scala se ela tiver alguns códigos de cores?
    etapas:

    • use JSch para criar uma conexão de sessão ssh.
    • use ls
    • conecte-se ao novo shell
    • use cd /var no novo shell
    • use ls no novo shell.

//use 'JSch' create a ssh session connection. 
val shell = new Shell(Auth("hostname", "username", 22, "pwd"))
//use 'ls' 
shell.exc("ls")

//connect to new shell   
val newShell = shell.newShell(Auth("xxx.xxx.xxx.xxx", "root", 22, "pwd")).right.get

//use 'cd /var' on the new shell  
newShell.exc("cd /var")
//use 'ls' on the new shell.
newShell.exc("ls")

newShell.exit()

shell.disconnect()

O comando shell.exc("ls") é produzido perfeitamente porque eu uso a propriedade dumb como JSch.setPtyType() . Não os códigos de cores são impressos.

O problema dos códigos de cores ocorreu em newShell.exc("ls") , imprime:

[0m[01;34mbackups[0m  [01;34mcache[0m  [01;34mlib[0m  [01;34mlocal[0m  [01;36mlock[0m  [01;34mlog[0m  [01;34mmail[0m  [01;34mopt[0m  [01;36mrun[0m  [01;34mspool[0m  [30;42mtmp[0m

Obviamente, contém alguns códigos de cores. val newShell é gerado por um comando simples ssh -t -o StrictHostKeyChecking=no foo@bar , então é diferente com JSch ways.

Atualmente, quero apenas descartar os códigos de cores e manter as informações de resposta contendo apenas texto:

backups  cache  lib  local  lock  log  mail  opt  run  spool  tmp

Espero que fique claro a questão. Obrigado novamente.

ATUALIZAR novamente

Desculpe pelos meus dois erros.

  1. TERM=dumb não precisa de nada porque JSch tem a configuração dumb e o novo ssh vai enganá-lo.
  2. setPty(true) (ou -T parâmetro) é afetado, meu teste falhou por causa de outro problema que as constantes MAGIC_SPLIT devem ser iniciadas / terminadas com \n em vez de \r\n neste modo.

Quais são as mudanças que devo fazer?

Use setPty(true) para todo o protocolo de mensagens, que contém JSch e ssh com o parâmetro -T, em vez de dumb , porque é uma resposta mais clara.

Qual é o problema deixado?

Algum host remoto responderá uma mensagem de erro stdin: is not a tty depois do sucesso, faça login no host remoto que é importante porque echo $? falhará. Mas está fora do tópico já.

Sobre este tópico

Voltar para a pergunta how to use ssh session with no color formatting? , a resposta é usar o parâmetro -T para ssh .

E, finalmente, muito obrigado pela paciência do @ sourcejedi.

    
por LoranceChen 19.08.2017 / 07:49

1 resposta

3

Você acabou de fazer isso.

Espera-se que os programas locais cuja saída é canalizada para outro programa detectem que eles não estão conectados a nenhum terminal, por isso não podem usar códigos de cores (que variam entre terminais, daí a variável de ambiente TERM).

E quando o programa local ssh é enviado para outro programa e você não passa as opções -tt , ele suprime a alocação de um "pseudo-terminal" e usa pipes. Veja também man ssh .

Se o seu código estava alocando um "pseudo-terminal" em vez de usar um pipe para capturar a saída, você deveria notar esse fato. Na maioria dos contextos, o código requerido é mais obscuro e mais longo do que se você usasse um pipe; na maioria das vezes você não precisa (ou, como você diz, quer) dos recursos extras de um PTY.

EXCETO acho que sua pergunta está errada (na parte UPDATE)

Suponha que você não esteja executando ssh e, em vez disso, executando sshpass -p '${auth.password}' ssh ...

sshpass, de acordo com a página man , está executando o ssh "em um TTY dedicado, acreditando que está obtendo a senha de um usuário interativo" (sim, é outro PTY).

Nesse caso, você precisaria desabilitar o comportamento normal do terminal novamente para a conexão SSH interna. Ou seja usando ssh -T (não ssh -t como em um dos commits de código!).

Acho que o prefixo com TERM=dumb também alcança um efeito muito semelhante. É um pouco de trabalho. ssh -T evita a necessidade de mexer com o TERM. Mas eu testei TERM=dumb sshpass sh -c 'echo $TERM' no meu computador, parece passar por OK e talvez pareça mais simples para você.

Próxima pergunta: Por que seu teste está dizendo que isso é necessário, quando seu código também já está trabalhando para definir TERM=dumb , antes de iniciar o comando (inner) ssh ? Você esperaria que o ssh tivesse herdado TERM=dumb já. Veja o código do Jsch. Eu acho que seu setPtyType("dumb") não terá nenhum efeito, porque você não tem nenhuma chamada para setPty(true) .

Meu entendimento é contradito por sua afirmação de que setPty(false) "quebra", mas você não diz como.

    
por 19.08.2017 / 09:01