A função reboot()
incorporada, que tem funcionado perfeitamente nos hosts Ubuntu 14.04 e FreeBSD 10.x, mas não funciona nos hosts Ubuntu 16.04.
O que está acontecendo no Ubuntu 14.04:
Recebo uma saída como esta e o sistema reinicia, após a reinicialização do Fabric reconecta.
[ubuntu] out:
[ubuntu] out:
[ubuntu] out: Broadcast message from root<strong i="9">@ubuntu</strong>
[ubuntu] out:
[ubuntu] out: (/dev/pts/0) at 15:02 ...
[ubuntu] out:
[ubuntu] out:
[ubuntu] out:
[ubuntu] out:
[ubuntu] out: The system is going down for reboot NOW!
[ubuntu] out:
[ubuntu] out:
O que está acontecendo no Ubuntu 16.04:
Se eu pressionar a tecla Enter neste estado, o Fabric realmente continua, mas mostra esta mensagem antes:
No handlers could be found for logger "paramiko.transport"
Warning: sudo() received nonzero return code -1 while executing 'reboot'!
Estou usando este código para reinicializar:
def reboot_():
with settings(warn_only=True):
print 'rebooting'
start_time = time.time()
reboot(wait=1200)
print 'reboot took: {} seconds'.format(time.time() - start_time)
É exatamente o mesmo com run ('reboot')
Sendo o mesmo com um run
manual não é surpreendente - claramente algo mudou em relação ao modo de reinicialização do Ubuntu, conexões SSH, etc.
Nada óbvio vem à mente, mas reboot()
(Fab's, não Linux's) é bem básico - ele simplesmente chama sudo('reboot')
e ajusta temporariamente as configurações gerais de reconexão do Fabric para que possa lidar com a reconexão após uma sequência de reinicialização não trivial (versus o padrão, que desistiria muito rapidamente).
Consulte https://github.com/fabric/fabric/blob/c0224a52df59821f21a8c0bd47ce15e42c2046a4/fabric/operations.py#L1244 - você pode querer tentar ajustar isso.
Além disso, tente habilitar o registro do Paramiko (consulte a parte inferior de nossa página de solução de problemas - http://www.fabfile.org/trou troubleshooting.html), pois isso pode fornecer uma pista.
Na verdade, pensando bem, parece que o reboot
do Ubuntu nunca sai ou envia um código de saída para os manipuladores de execução do Fabric ( run
/ sudo
) do Fabric ( run
/ sudo
), já que você nota que sudo
é o que fica furioso quando você mash Enter depois de esperar.
Se você olhar o código reboot()
, ele espera que a chamada sudo('reboot')
saia eventualmente, para que possa A) esperar um pouco e B) iniciar a reconexão.
O fato de que, no final do Fabric, a execução está apenas pendurada dentro de sudo
significa que algo remotamente está violando essa expectativa. Meio estranho. _Talvez_ um bug no próprio Fabric, mas parece mais um mau comportamento no lado remoto. (PS: em quais versões de tecido você está vendo isso?)
Pensamento improvisado - talvez pudéssemos definir timeout=
no sudo
, em seguida, except TimeoutException: pass
ao redor dele. Isso garantiria que, mesmo nessa situação (estranha), o padrão seria tentar uma reconexão.
A única desvantagem seria o caso em que reboot
está realmente travando e o sistema não está realmente reiniciando, mas não é como se fôssemos tornar as coisas _piores_ para esse caso com a mudança acima - o travamento infinito simplesmente aconteceria em o loop de conexão em vez de dentro de sudo
.
Um outro comportamento alterado realmente estranho no Ubuntu 16.04 é o seguinte. Quando executo poweroff
em uma sessão ssh, a máquina desliga, mas as sessões SSH travam! Não há como usar Ctrl + C, Ctrl + D ou nada. Tudo que posso fazer é esperar um _muito_ e então o ssh aborta com:
packet_write_wait: Connection to 192.168.56.11: Broken pipe
Eu realmente não estou interessado em lidar com conexões SSH, mas este pode ser exatamente o mesmo problema que ocorre com a reinicialização.
Acabei de executar uma reinicialização quebrada (Ubuntu 16.04 atualizado no AWS, Fabric == 1.12.0), mas de uma maneira diferente. Para mim, apenas joga:
Fatal error: sudo() received nonzero return code -1 while executing!
Requested: reboot
Executed: sudo -S -p 'sudo password:' /bin/bash -l -c "reboot"
Executando sudo reboot
no terminal manualmente (reinicializações do host).
Pode ser digno de nota:
$ readlink /sbin/reboot
/bin/systemctl
$ readlink /sbin/shutdown
/bin/systemctl
E outra coisa estranha. Mudei o código de reinicialização para usar aws-cli e, após sua chamada (que leva cerca de 1 segundo, parece que é assíncrono), executo sudo('add-apt-repository --yes ppa:nginx/stable')
. Sempre funcionou, mas agora, após a reinicialização, retornou -1 também:
sudo: add-apt-repository --yes ppa:nginx/stable
Fatal error: sudo() received nonzero return code -1 while executing!
Requested: add-apt-repository --yes ppa:nginx/stable
Executed: sudo -S -p 'sudo password:' /bin/bash -l -c "add-apt-repository --yes ppa:nginx/stable"
Então tentei fazer tecido para reconectar adicionando fabric.network.disconnect_all()
. Resultou na solicitação de uma senha (por quê ??):
[...] sudo: add-apt-repository --yes ppa:nginx/stable
[...] Login password for 'ubuntu':
E só começou a funcionar depois que eu adicionei, por exemplo, time.sleep(60 * 3)
após a reinicialização. O que obviamente é um band-aid ruim, e agora estou confuso sobre como lidar adequadamente com o problema da senha. Parece que está relacionado a este problema.
O problema parece ser que "reiniciar" às vezes é "muito rápido", antes que o status do comando volte pela conexão ssh.
(Dica: se você estiver em uma conexão ssh congelada como resultado: digite \n~.
aka enter, til, ponto final. Esse é o caractere de escape ssh padrão e, em seguida, o comando de desconexão para ssh. Se você apenas tentar ctrl- c ou ctrl-d, ssh tenta passar isso para o processo em execução no outro lado.)
Uma solução é usar shutdown -r +1
, o que agendará a reinicialização para o próximo minuto e, em seguida, esperará um minuto para que ele inicie e, em seguida, tentará se reconectar. É certo que esperar um minuto não é bom.
Uma coisa hacky para tentar: shutdown -r +0
deve ser equivalente a reboot
, mas em meus testes limitados de Ubuntu-16.04 rodando no VirtualBox, tende a dar uma fração de segundo a mais, mostrando o próximo prompt do shell antes de desconectar uma sessão ssh manual.
este é provavelmente um dup de # 1444
Se o daemon init for alterado para upstart, a reinicialização funcionará conforme o esperado. Parece que o systemd está eliminando o sshd imediatamente.
Havia um bug no pacote de systemd do Debian / Ubuntu que, ao desligar, matou o serviço de rede antes do SSH, então tudo travou.
Foi corrigido no último lançamento pontual. Não sei sobre o status do pacote Ubuntu.
Relatou o bug para o Ubuntu:
https://bugs.launchpad.net/ubuntu/+source/openssh/+bug/1645002
Eu também tive problemas com relação ao uso de reboot () em alguns de meus scripts. Descobri que ao conectar com uma senha, a reinicialização estava funcionando corretamente, mas ao usar a autenticação de arquivo de chave, a conexão desligou (e a reinicialização foi feita).
O bug do ubuntu https://bugs.launchpad.net/ubuntu/+source/openssh/+bug/1645002 está marcado como corrigido em 16.10, mas ainda não em 16.04, e não está claro quando será.
O comportamento atual para mim é que paramiko / fabric detecta instantaneamente que a conexão ssh foi fechada, mas é antes de paramiko / fabric ver que o comando reboot foi concluído. Pelo menos ele não trava indefinidamente como no relatório original.
Fatal error: sudo() received nonzero return code -1 while executing!
...
Aborting.
Simplesmente reboot()
fez isso de forma consistente para mim em um punhado de testes contra AWS EC2 e uma VM virtualbox local. (Eu sempre usei a autenticação de arquivo de chave.)
Eu encontrei uma solução alternativa curta e elegante, como sugeri sem tantos detalhes acima:
reboot(command="shutdown -r +0")
Isso funcionou como esperado para mim (em meu punhado de testes contra AWS EC2 e VM virtualbox local, todos rodando ubuntu 16.04 atualizado). Observe que "shutdown -r now" se comportou como "reboot" e não pareceu funcionar.
Dei uma olhada rápida nas páginas de manual do freebsd e openbsd e parece que eles têm um comando de desligamento que oferece suporte a esses parâmetros. Suspeito que o comando "shutdown -r +0" funcionaria para praticamente qualquer sistema Unix em que "reboot" funcionasse. Portanto, pode ser considerado para alterar o comando padrão ou atualizar a documentação. (Mas eu estaria interessado em ver um relatório de um teste em um sistema BSD primeiro.)
shutdown -r +0
não é suficiente para nós. Como a reinicialização não aceita um tempo limite manual, eu até tentei algo como:
try:
sudo("shutdown -r +0", timeout=300)
except NetworkError:
pass
# in case the sudo times out during reboot
sleep(15)
Apesar de todo esse aceno de mão, o próximo comando trava indefinidamente. É possível que o pool de conexão esteja mantendo (e usando) a conexão inativa? Em caso afirmativo, existe uma solução alternativa? Posso reduzir temporariamente o tempo limite do nível de conexão?
Na verdade, você precisa substituir a conexão existente, da mesma forma que reboot()
:
https://github.com/fabric/fabric/blob/1.13.2/fabric/operations.py#L1289 -L1294
Peço desculpas para reviver um problema antigo, também posso confirmar que esse problema ocorre ao tentar reinicializar um contêiner LXC. A sugestão de @ploxiln de usar command="shutdown -r +0"
funcionou para nós.
Confirmando este erro em uma nova instalação do FreeBSD 11.1 com o bash instalado:
reboot(wait=1)
resulta em:
Fatal error: sudo() received nonzero return code -1 while executing!
Requested: reboot
Executed: sudo -S -p 'sudo password:' /usr/local/bin/bash -l -c "reboot"
Aborting.
Traceback (most recent call last):
…
raise env.abort_exception(msg)
hosts.FabricException: sudo() received nonzero return code -1 while executing!
Acabei precisando disso para fazer as coisas andarem depois de ler os comentários de @ambsw-technology e
sudo('shutdown -r +0')
time.sleep(30)
fabric.state.connections.connect(env.host_string)
Para sua informação, ainda vejo isso em servidores 18.04.2 LTS.
Alguma correção para isso? também tendo problemas com 16.04
Comentários muito úteis
O bug do ubuntu https://bugs.launchpad.net/ubuntu/+source/openssh/+bug/1645002 está marcado como corrigido em 16.10, mas ainda não em 16.04, e não está claro quando será.
O comportamento atual para mim é que paramiko / fabric detecta instantaneamente que a conexão ssh foi fechada, mas é antes de paramiko / fabric ver que o comando reboot foi concluído. Pelo menos ele não trava indefinidamente como no relatório original.
Simplesmente
reboot()
fez isso de forma consistente para mim em um punhado de testes contra AWS EC2 e uma VM virtualbox local. (Eu sempre usei a autenticação de arquivo de chave.)Eu encontrei uma solução alternativa curta e elegante, como sugeri sem tantos detalhes acima:
Isso funcionou como esperado para mim (em meu punhado de testes contra AWS EC2 e VM virtualbox local, todos rodando ubuntu 16.04 atualizado). Observe que "shutdown -r now" se comportou como "reboot" e não pareceu funcionar.
Dei uma olhada rápida nas páginas de manual do freebsd e openbsd e parece que eles têm um comando de desligamento que oferece suporte a esses parâmetros. Suspeito que o comando "shutdown -r +0" funcionaria para praticamente qualquer sistema Unix em que "reboot" funcionasse. Portanto, pode ser considerado para alterar o comando padrão ou atualizar a documentação. (Mas eu estaria interessado em ver um relatório de um teste em um sistema BSD primeiro.)