Se eu entendi corretamente, você quer estabelecer uma conexão SSH entre A e B, digamos de A para B. É possível estabelecer uma conexão TCP de A para B (B não está por trás de um firewall que faz isso impossível), mas você está preocupado que permitir que um usuário de A efetue login em B pode permitir uma violação de segurança em B se A não for confiável.
O OpenSSH fornece uma solução simples para isso. Em ~/.ssh/authorized_keys
, você pode restringir uma chave a ser válido para executar apenas um comando. Crie um novo par de chaves em A:
serverA$ ssh-keygen -N '' -f ~/.ssh/copy_to_B.id_rsa
serverA$ cat ~/.ssh/copy_to_B.id_rsa.pub
Pegue a chave pública gerada e adicione um comando forçado no final da linha. Adicione também a opção restrict
para evitar coisas como o encaminhamento de porta (o que poderia, por exemplo, permitir que A faça solicitações provenientes do perímetro do firewall de B). A nova linha em ~/.ssh/authorized_keys
em B ficaria assim:
ssh-rsa AAAA… luc@serverA restrict command="cat >~/backups/B/latest.tgz"
Agora, ao usar essa chave para efetuar login em B, o comando cat >~/backups/B/latest.tgz
será executado, independentemente do que você passar para ssh
. Desta forma, tudo o que B pode fazer é gravar no arquivo
serverA$ tar … | ssh -i ~/.ssh/copy_to_B.id_rsa luc@serverB whatever
Se o servidor SSH em B não for recente o suficiente, talvez não tenha restrict
. Se ele não tiver restrict
, use no-port-forwarding
, além de todas as outras opções no-…
disponíveis (confira man sshd
em B).
Você pode se referir ao comando original no comando forçado através da variável SSH_ORIGINAL_COMMAND
, mas tenha cuidado, pois se você fizer algo complicado aqui, será difícil garantir que você não esteja abrindo uma falha de segurança. Aqui está um invólucro simples que permite que B grave em qualquer arquivo em ~/backups/B
passando o nome do arquivo desejado como um comando - note que o wrapper coloca listas brancas, para evitar coisas como escrever para ../../.ssh/authorized_keys
.
ssh-rsa AAAA… luc@serverA restrict command="case $SSH_ORIGINAL_COMMAND in *[!-.A-Za-z0-9_]*) echo >&2 'bad target file'; exit 120;; [!-.]*) cat >~/backups/B/\"$SSH_ORIGINAL_COMMAND\";; *) echo >&2 'bad target file'; exit 120;; esac"