No Cygwin, quero um script Bash para:
- Crie um túnel SSH para um servidor remoto.
- Faça algum trabalho local que use o túnel.
- Então desligue o túnel.
A parte do desligamento me deixou perplexo.
Atualmente, tenho uma solução ruim. Em um shell, eu executo o seguinte para criar um túnel:
# Create the tunnel - this works! It runs forever, until the shell is quit.
ssh -nNT -L 50000:localhost:3306 jm@sampledomain.com
Então, em outra janela do shell, eu faço o meu trabalho:
# Do some MySQL stuff over local port 50000 (which goes to remote port 3306)
Finalmente, quando termino, fecho a primeira janela do shell para matar o túnel.
Eu gostaria de fazer isso tudo em um script como:
# Create tunnel
# Do work
# Kill tunnel
Como acompanho o processo do túnel, para saber qual deles matar?
Respostas:
Você pode fazer isso corretamente com um ssh 'control socket'. Para conversar com um processo SSH já em execução e obtê-lo, execute-o etc. Use o 'socket de controle' (-M para master e -S para socket) da seguinte maneira:
Observe que my-ctrl-socket será um arquivo real criado.
Eu recebi essas informações de uma resposta muito RTFM na lista de discussão do OpenSSH .
fonte
Operation not permitted
entro no ambiente de integração contínua drone.io:muxserver_listen: link mux listener ssh-ctrl-socket.wsASkszgSBlK7kqD => ssh-ctrl-socket: Operation not permitted
my-ctrl-socket
arquivo após a execução? Quando o façols -la
na pasta atual, não consigo mais ver o arquivo.while [ ! -e $ctrl_socket ]; do sleep 0.1; done
open failed: administratively prohibited: open failed
e eu não acho que a abertura do túnelVocê pode dizer ao SSH para fazer o segundo plano com a opção -f, mas não receberá o PID com $ !. Além disso, em vez de fazer com que seu script durma uma quantidade arbitrária de tempo antes de usar o encapsulamento, você pode usar -o ExitOnForwardFailure = yes com -f e o SSH aguardará que todos os encaminhamentos de portas remotas sejam estabelecidos com sucesso antes de se colocar em segundo plano. Você pode receber a saída do ps para obter o PID. Por exemplo, você pode usar
e tenha certeza de que está obtendo o PID desejado
fonte
ssh
para entrar em segundo plano&
e não criar um shell do outro lado (basta abrir o túnel) com uma bandeira da linha de comando (vejo que você já fez isso com-N
).PID=$!
kill $PID
EDIT: Fixo $? para $! e adicionou o &
fonte
trap 'kill $PID' 1 2 15
cobrirá muitos casos de falha de script.trap "kill $PID"
, porque o bash irá únicas variáveis Interpolar dentro de strings entre aspas duplasPID
variável fosse redefinida mais tarde. A variável é expandida quando otrap
built-in é chamado (a abordagem do OP) ou quando um sinal é capturado (sua abordagem); ambas as abordagens produzem o mesmo resultado aqui.Prefiro iniciar um novo shell para tarefas separadas e geralmente uso a seguinte combinação de comandos:
ou às vezes:
Esses comandos criam um shell aninhado onde eu posso fazer todo o meu trabalho; Quando termino, clico em CTRL-D e o shell pai limpa e sai também. Você pode facilmente
bash;
inserir seu script de encapsulamento ssh imediatamente antes dakill
peça, para que, ao sair do shell aninhado, seu encapsulamento seja fechado:fonte
Você pode iniciar o
ssh
com um&
a final, colocá-lo em segundo plano e pegar seu ID ao fazê-lo. Então você só precisa fazer umakill
identificação desse tipo quando terminar.fonte
Outra opção em potencial - se você pode instalar o pacote expectável, poderá criar um script para a coisa toda. Alguns bons exemplos aqui: http://en.wikipedia.org/wiki/Expect
fonte