[Ubuntu] SSH 접속 시 텔레그램 알람보내기 #3 (명령어로 메시지발송 테스트)

[Ubuntu] SSH 접속 시 텔레그램 알람보내기 #3 (명령어로 메시지발송 테스트)
Photo by Dima Solomin / Unsplash

지난 편을 작성하고서 일이 바빠져서... 글 작성이 너무 늦어져서, 다시 하던 것을 마무리하고자 한다. 아마 이번 편과 다음 편까지 총 4편으로 마무리가 될 것 같다. 사실 중간 과정없이 쉘스크립트만 공유해도 무관한데... 내가 공부했던 과정을 기록하면 다른 사람도 혹시 그 과정에서 얻는 것이 있지 않을까 싶었고, 나도 이걸 기록하면서 얻는 것이 있을 것 같아서이다.


연관 포스트

  1. [Ubuntu] SSH 접속 시 텔레그램 알람보내기 #1 (봇생성편)
  2. [Ubuntu] SSH 접속 시 텔레그램 알람보내기 #2 (메시지발송편)
  3. [Ubuntu] SSH 접속 시 텔레그램 알람보내기 #3 (명령어로 메시지발송 테스트)
  4. [Ubuntu] SSH 접속 시 텔레그램 알람보내기 #4 (최종편)

A. 명령어로 url 호출

리눅스 명령어로 url을 호출 할 수 있는 명령어는 대표적으로(=내가 알고 있는) curl과 wget이 있다. 내 경우에는 URL을 통해서 무언가를 다운받을 경우에는 wget을 주로 사용하고, Restful API와 같은 특정 URL을 호출하는 경우에는 curl을 사용하는 편이다.[1]

지난 문서와 동일한 메시지를 curl 명령어로 전송해보면...

$ curl https://api.telegram.org/bot57412121:AAEF-Zjsdlsd-----YPk/sendMessage?chat_id=5545034869&text=test
[1] 1859
$ {"ok":false,"error_code":400,"description":"Bad Request: message text is empty"}
[1]+  Done                    curl https://api.telegram.org/bot57412121:AAEF-Zjsdlsd-----YPk/sendMessage?chat_id=5545034869
$

curl에 단순히 URL 전체[2]를 붙여넣으니 전송이 안된다. 참고문서 2를 보면서 명령어를 손봐야한다.

일단, 위 에러내용을 보니 정상적으로 get 방식으로 전달한 파라미터가 잘 전달되지 않은 것으로 보아서 분리해본다.

$ curl -d 'chat_id=55450--869&text=test' https://api.telegram.org/bot57412121:AAEF-Zjsdlsd-----YPk/sendMessage

위 명령어를 실행하니 아래와 같은 json 형태의 반환값(웹브라우저에서 보였던 값)이 보이고, 메시지도 정상적으로 발송되었다.

{"ok":true,"result":{"message_id":5,"from":{"id":6215--8963,"is_bot":true,"first_name":"simplism-ssh-alarm","username":"simplism_ssh_alarm_bot"},"chat":{"id":55450--869,"first_name":"SIMPLISM","type":"private"},"date":1690266482,"text":"test"}}

  1. 참고문서 1을 보면 자세한 내용을 확인 할 수 있다. ↩︎

  2. 참고로 위 url은 API Token을 임으로 변형한 것이므로 정상적으로 실행되지 않는다. ↩︎

처음 curl 명령어를 실행했을 때는 실패했지만, 두번째 get파라미터를 -d 옵션으로 분리하고서는 정상적으로 메시지 발송에 성공했다!

B. 조금 더 복잡하게

프로그래밍으로 치면, 이제 ==Hello World!==만 끝난 것이다. 단순하게 login과 같은 띄어쓰기도 안되어있는 메시지만 보낼꺼라면 저걸로 충분하지만... 난 좀 더 많은 정보를 메시지에 담고 싶었다.

  1. SSH 세션이 열린 서버의 호스트명과 IP주소
  2. 접속한 사용자계정과 IP주소
  3. 접속한 시간

일단 최소 위의 3가지 정보는 메시지에 담고 싶었다.

예를 들어 아래처럼...

simplism-beebox(192.168.0.11) ssh session open! (user=simplism, ip=192.168.0.3, datetime=2023-07-25 (Tue) 15:07:22)

위와 같은 메시지를 받으면, 어떤 리눅스 서버(hostname, server ip)에 누가(user), 언제(datetime), 어디서(client ip) 접속했는지 바로 알 수 있으니까!

C. 메시지를 위한 정보수집

이제 메시지 발송에 포함되는 정보들을 수집할 방법을 찾아보자

01) 서버의 호스트명과 IP주소

$ echo $(hostname)
simplism-beebox
$ echo $SSH_CONNECTION
192.168.0.3 14693 192.168.0.11 22
$ echo $SSH_CONNECTION | awk '{print $3}'
192.168.0.11
$

호스트명은 hostname이라는 명령어의 결과로 출력이 가능하니 간단하고... SSH 서버의 IP주소는 가장 간단하게 SSH 세션이 열리면 SSH_CONNECTION이라는 환경변수에 클라이언트 IP, 클라이언트 Port, 서버 IP, 서버 Port 정보가 저장된다. 그 중에서 3번째의 값이 서버 IP주소이므로 awk 명령어를 이용해서 추출해준다.

$ netstat -an | grep ESTA | grep :22
tcp        0      0 192.168.0.11:22         192.168.0.3:14693      ESTABLISHED
$

netstat명령어로 확인해보면 IP와 Port정보가 나와서 비교해보니 일치한다.

02) 클라이언트 IP주소 및 사용자명

$ echo $SSH_CONNECTION | awk '{print $1}'
192.168.0.3
$ echo $USER
simplism
$

클라이언트 IP주소는 서버 IP주소와 동일하게 SSH_CONNECTION 환경변수에서 추출하고, 사용자명은 USER 환경변수에 저장되니 해당 값에서 추출한다.

03) 접속시간

접속시간은 date 명령을 원하는 포맷(읽기 편한 형태)으로 바꿔서 출력한다.

$ echo $(date +"%Y-%m-%d (%a) %H:%M:%S")
2023-07-25 (Tue) 15:49:35
$

D. 스크립트 파일을 만들자!

이제 단일 명령어로 끝낼 수 있는 수준은 넘었으니.. 쉘스크립트 파일을 만들어보자.

$ vi LoginAlarm.sh

이제 간단한 형태로 스크립트를 만들어보면...

#/bin/sh

NOW=$(date +"%Y-%m-%d (%a) %H:%M:%S")
SERVER_IP=$(echo $SSH_CONNECTION | awk '{print $3}')
CLIENT_IP=$(echo $SSH_CONNECTION | awk '{print $1}')
SERVER_INFO=$(hostname)'('$SERVER_IP')'

API_URL=https://api.telegram.org/bot
API_TOKEN=57412121:AAEF-Zjsdlsd-----YPk
API_METHOD=sendMessage
API_FULLURL="$API_URL$API_TOKEN"/"$API_METHOD"
API_CHATID=55450--869

MSG="<b>$SERVER_INFO</b> ssh session open! (user=$USER, ip=$CLIENT_IP, datetime=$NOW)"
DAT="{\"chat_id\":\"$API_CHATID\",\"text\":\"$MSG\",\"parse_mode\":\"html\"}"

curl -X POST -H "Content-Type: application/json" -d "$DAT" $API_FULLURL

위 내용 중에서 주요 라인을 설명하면...

  1. API_TOKEN : 이 부분은 본인이 봇파더에게 받은 봇의 API TOKEN을 넣어준다.
  2. API_CHATID : 이 부분도 이전 문서에서 확인한 나의 Chat ID를 넣어준다.
  3. DAT : Telegram API를 호출할 때, 보다 다양한 값을 입력하기 위해서 JSON 형태의 데이터를 만들었다. JSON 데이터의 키(Key)를 표현하기 위해서 "(쌍따옴표)를 넣어야하는데, 키(Key)의 쌍따옴표는 앞 부분에 (backslash, 역슬래시)를 넣어서 Escape Character 처리를 해줘야 정상적으로 인식된다. 추가적으로 Bold와 같은 텍스트 강조를 위해서 parse_mode 값에 html이라는 값을 넣어줬다.

사실 위 스크립트를 만들기까지 Telegram 공식 API 문서를 열심히 읽었다.. 그 내용을 다 옮길 수가 없더라.. 더 많은 텔레그램 API와 관련된 내용은 텔레그램 API 문서를 확인해보는 것이 좋을 것 같다.

이제 스크립트 파일을 저장하고...

$ chmod u+x LoginAlarm.sh

실행이 가능하도록 퍼미션을 조정한 다음에...

$ ./LoginAlarm.sh
{"ok":true,"result":{"message_id":6,"from":{"id":6215--8963,"is_bot":true,"first_name":"simplism-ssh-alarm","username":"simplism_ssh_alarm_bot"},"chat":{"id":55450--869,"first_name":"SIMPLISM","type":"private"},"date":1690269331,"text":"simplism-beebox(192.168.0.11) ssh session open! (user=simplism, ip=192.168.0.3, datetime=2023-07-25 (Tue) 16:15:30)","entities":[{"offset":0,"length":16,"type":"bold"},{"offset":16,"length":12,"type":"url"},{"offset":16,"length":12,"type":"bold"},{"offset":28,"length":1,"type":"bold"},{"offset":67,"length":12,"type":"url"}]}}

실행했을 때 ok 값이 true로 나온다면 성공이다!

E. 마치면서..

이제 만든 쉘스크립트에 몇 가지 기능을 손을 보고... SSH 세션이 열릴 때 실행되도록 설정만 하면 된다. 여기까지 따라왔다면 아마 뒷 부분은 어렵지 않을 것 같다.

일단, 포스트가 너무 길어지니까 여기서 마무리하고 다음 편에서 마무리 해보겠다!

F. 참고문서

  1. [Linux] wget, curl 차이, 우노, 운호(Noah), 2021/04/21
  2. curl로 REST API 테스트, 기록만이살길, 기록만이살길, 2021/03/28

Read more

AI 환각 (AI Hallucination)에 대한 단상

AI 환각 (AI Hallucination)에 대한 단상

ℹ️단상 (斷想, 생각나는 대로의 단편적인 생각) 생각을 어떻게든 적어두지 않으면 시간이 지나 잊혀져서 약간은 두서없을 나의 생각을 적는 다는 의미로 "~에 대한 단상"이라는 글들을 적어보려고 한다. 오픈 AI의 ChatGPT가 촉발한 생성형 AI는 기념비적인 과학기술의 발전으로 진보할 것이라는 기대감과 다른 한 편으로는 이 놀라운 신기술로 촉발될 부작용에

By simplism
[리뷰] 켄싱턴 오르빗 (Kensington Orbit) 트랙볼 마우스

[리뷰] 켄싱턴 오르빗 (Kensington Orbit) 트랙볼 마우스

* 구매처 : 알리익스프레스 * 가격 : 35.15 $ (50,220원) 난 하루 종일 컴퓨터를 사용하는 직업이라서... 모니터, 키보드, 마우스는 중요하다. 키보드는 몇 번에 걸쳐서 바꿔왔지만, 마우스는 일반적인 마우스 -> 버티컬 마우스로 바꿔서 꽤 오랫동안 써왔던거 같다. 버티컬 마우스로 바꾸고나서 손목과 오른 팔의 통증이 많이 사라져서 만족하고 있었는데... QHD 해상도 2대의 모니터를 주력으로

By simplism
[F1] 2024년 시즌초반 감상평 및  팀별 단상

[F1] 2024년 시즌초반 감상평 및 팀별 단상

작년에 이어서 올해도 쿠팡플레이를 통해서 전 시즌 F1 중계를 볼 수 있다. 딱히 다른 스포츠에 대해서 관심이 유독 없는데... 홍대병(마이너 취향??)인건지 사이버포뮬러의 영향(어릴 때 많이 보고.. 어른이 되서도 몇 번을 다시 본 것 같음..)인 것인지 F1이 너무 재미있더라. 넷플릭스에서 F1 다큐시리즈(본능의 질주, 빈디젤이 나오는 분노의

By simplism
[Ubuntu] NFS 클라이언트 설치 및 NFS볼륨 마운트작업

[Ubuntu] NFS 클라이언트 설치 및 NFS볼륨 마운트작업

사용환경 * OS : Ubuntu 22.04 LTS (Jammy Jellyfish) * Dokuwiki : Release 2024-02-06a "Kaos" * NAS : Synology DSM 7.1.1 A. 시작하기 전에.. 미니PC에 dokuwiki 설치하고 본격적으로 운영하기 전에 정기적인 백업을 해야할 것 같다. 그렇다고... 수동으로 주기적으로 하기에는 너무 번거롭고.. 윈도우즈 PC에서 사용하던 백업솔루션이 ubuntu도 지원해서 그 백업솔루션을 설치하기 전에

By simplism