여러 날 동안 저는 역방향 터널 설정을 자동화하는 방법을 궁금해했습니다.
LAN 내부에서 NAT를 사용하는 원격 라즈베리가 많이 있고 인터넷에서 연결할 수 있는 서버로 사용하는 라즈베리가 하나 있습니다.
나는 원격 Raspberries 단일 명령을 보내는 시스템을 내 웹 사이트에 구현했습니다.
모든 원격 Raspberry는 사용 가능한 명령이 있는지 매분(crontab) 확인하고, 명령이 있으면 명령을 다운로드하고 실행 파일을 생성하여 실행합니다. crontab 파일의 코드는 다음과 같습니다.
#! /bin/bash
sudo wget -c --output-document=ipdiscover.php "www.myserver.com/checkforcommands.php";
comando=$(cat ipdiscover.php);
sudo rm "/esegui.sh";
echo "#! /bin/bash" >> /esegui.sh;
echo "" >> /esegui.sh;
echo -e $comando >> /esegui.sh;
echo "exit 0" >> /esegui.sh;
sudo chmod +x /esegui.sh;
sudo /esegui.sh;
sudo rm "ipdiscover.php";
sudo date >>/tmp/crontest.txt;
이 시스템은 매우 잘 작동하지만 역방향 터널을 구축하는 데 사용할 수 없습니다.
원격 서버에서 다음 코드를 실행하는 경우:
sudo /usr/bin/ssh -gNnT -R 2222:localhost:22 pi@publicserverIP;
그러면 모두 올바르게 작동하지만 crontab 스크립트에서 실행하면 작동하지 않습니다.
비밀번호 없이 인증서를 생성했고, 로그인 접근을 하지 않기 위해 원격 라즈베리에서 서버로 보냈습니다.
답변1
cron
를 통해 명령을 실행할 필요가 없습니다 sudo
.
아래와 같은 스크립트를 작성하여 서버에 대한 역방향 SSH 연결을 설정하는 사용자의 홈 디렉토리에 넣으십시오.
#!/bin/sh
### reverseSSHscript.sh ###
### (use public key authentication, so you don't need
### to enter password for your server)
PrivateKeyToAccessCentralServer='/path/to/the/private/ssh/ServerKey.pem'
(
/usr/bin/nohup \
/usr/bin/ssh -gNnT \
-i "${PrivateKeyToAccessCentralServer}" \
-o ExitOnForwardFailure=yes \
-o ServerAliveInterval=60 \
-o ServerAliveCountMax=1 \
-o TCPKeepAlive=no \
-o UserKnownHostsFile=/dev/null \
-o StrictHostKeyChecking=no \
-o CheckHostIP=no \
-R 2222:localhost:22 pi@publicserverIP
) &
그런 다음 cron 작업을 생성하여 실행합니다.
echo "@reboot User /path2the_script_shown_above/reverseSSHscript.sh" |
sudo tee /etc/cron.d/reverseSSH2home
그러면 작동할 것입니다. 그런데, 단지 안전을 유지하기 보다는
일부 제한된 환경에서 이 스크립트를 실행하고 싶을 수도 있습니다 .User
root
reverseSSHscript.sh
또한 다중 세션 생성을 방지하기 위해 연결이 이미 설정되었는지 확인하는 일부 논리를 구현해야 합니다 .
정기적으로 cron에서 몇 가지 추가 검사를 실행하여 역방향 연결 포트가 서버에 아직 활성 상태인지 테스트합니다. 이 같은:
chkRemPort() {
# Connect to intermediate host and check if remote forwarded port is alive
echo $(/usr/bin/ssh -4 -f -q \
-o BatchMode=yes \
-o UserKnownHostsFile=/dev/null \
-o StrictHostKeyChecking=no \
-o CheckHostIP=no \
-i /path/to/the/private/ssh/ServerKey.pem \
pi@publicserverIP \
/bin/nc -w 3 -zv localhost 2222 2>&1 | /bin/grep succeeded > /dev/null ; \
[ $? -eq 0 ] && { echo 'OK'; } || { echo 'FAILED'; }; exit; )
}
확인에 실패하면 서버에 대한 새 역방향 세션을 설정해 보십시오.
서버의 포트 간 충돌을 방지하려면 각 Raspberry Pi의 PS 역방향 포트가 달라야 합니다.