Rsync parece incompatível com .bashrc (causa "o seu shell está limpo?")

16

Acontece que o rsync não pode funcionar com um servidor remoto que possui um arquivo .bashrc?

No cliente local, obtive ao executar o rsync:

protocol version mismatch -- is your shell clean?
(see the rsync man page for an explanation)
rsync error: protocol incompatibility (code 2) at compat.c(180) [sender=3.0.7]

Como sugerido aqui, remover o .bashrc no servidor resolveu o problema. Como resolvê-lo sem remover o arquivo .bashrc (temporariamente)?

Computist
fonte
11
Verifique se o ssh está ativado para essa conta.
Lamy
As respostas abaixo provavelmente estão incorretas. Recentemente, comecei a receber esse erro após uma atualização de rotina do Ubuntu, mesmo que nada tenha mudado nos meus arquivos .bashrc.
Cerin
Não - se a remoção do arquivo .bashrc o corrigir (como foi declarado nesta pergunta), o problema será gerado pelo .bashrc. Uma atualização certamente pode introduzir uma incompatibilidade de protocolo real, que é um problema totalmente diferente.
Randall Randall

Respostas:

21

Você pode ter problemas se o .bashrcservidor remoto enviar algo ao terminal. O Rsync pode não esperar isso e pode ter problemas como resultado.

Você pode corrigir isso removendo qualquer comando no .bashrctexto de saída ou canalizando qualquer saída para / dev / null.

Greg Hewgill
fonte
3
Então, como canalizar qualquer saída para / dev / null se eu puder modificar apenas arquivos no cliente?
Computist
11
Suponho que você poderia, como administrador do sistema, obter assistência. Você também pode modificar arquivos no servidor de outra maneira, como FTP ou scp.
Greg Hewgill
Sim, meu arquivo .bashrc continha um eco "*** Iniciando o ROOT Shell ***" e echo "(Use sudo em vez de um shell raiz sempre que possível!)". A remoção desses ecos resolveu o problema.
precisa saber é o seguinte
11
Na página de manual do rsync: "incompatibilidade de versão do protocolo - seu shell está limpo?" Essa mensagem geralmente é causada pelos scripts de inicialização ou pelo recurso remoto do shell, produzindo lixo indesejado no fluxo que o rsync está usando para seu transporte. A maneira de diagnosticar esse problema é executar seu shell remoto como este: ssh remotehost / bin / true> out.dat e, em seguida, observe o arquivo out.dat. Se tudo estiver funcionando corretamente, out.dat deve ser um arquivo de tamanho zero.
precisa saber é o seguinte
8

O .bashrc realmente não é o local correto para gerar saída, pois causa esse tipo de problema. Muitas pessoas se safam disso, até que tentam executar o rsync :-)

Qualquer saída desejada (e a lógica e os comandos associados) devem ser movidos para o seu .bash_profile (consulte, por exemplo, a pergunta sobre falha do servidor ".profile vs. .bash_profile vs. .bashrc" para discussão adicional sobre as diferenças entre os arquivos).

Dessa forma, você não precisará sacrificar a obtenção da saída quando efetuar o login, nem lidar com as alterações temporárias no seu .bashrc quando desejar usar o rsync.

Randall
fonte
6

Eu sempre tive arquivos .bashrc nas minhas contas de usuário e nunca tive esse problema até que tentei hoje sincronizar algo no meu servidor usando a conta raiz. Sua postagem me ajudou a encontrar a solução:

meus arquivos $ user / .bashrc sempre começam com a seção a seguir para evitar esse tipo de problema. Eu o repliquei no .bashrc e no rsync'ing do root agora funciona como um encanto!

# If not running interactively, don't do anything
case $- in
    *i*) ;;
      *) return;;
esac

HTH, karsten

karsten
fonte
Isso geralmente não funciona rsync, porque, por qualquer motivo, é classificado como "shell interativo". Mas é uma boa linha para adicionar de qualquer maneira, porque pode danificar shells não interativos, caso contrário, se houver alguma saída.
Michael Schubert
Eu acho que essa é a melhor solução para a questão. A resposta de aceitação "remover qualquer comando no .bashrc que produza texto" não é prática.
Qinsi 27/07/18
4

Por motivos complexos, o rsync / scp / sftp executa .bashrc ao conectar-se a outro host. Você deve ter qualquer um destes comandos na parte superior do seu .bashrc :

ou

[[ $- != *i* ]] && return

ou

[ -z "$PS1" ] && return

Qualquer um dos comandos acima permitirá apenas a execução do restante dos comandos .bashrc para sessões interativas . Até onde eu sei, você não precisa delas para nenhum outro tipo de sessão (e, de fato, eu vi o bashrc padrão do Arch e Debian usando essa técnica no bashrc).

Se, no entanto, você quiser ser mais paranóico ao permitir que seus comandos bashrc sejam executados mesmo para sessões não interativas, você deve pelo menos agrupar os comandos do bashrc que produzem saída como esta ( referência ) para que eles sejam executados apenas em sessões interativas:

if shopt -q login_shell; then
    # this is an interactive session, we _can_ display output
    ...code that produces output goes here...
fi

Observe que outros sugerem mover comandos que produzam texto para o seu bash_profile, mas tenho minhas dúvidas sobre se isso sempre é bom (por razões explicadas aqui )

ndemou
fonte