[DB/Slack] MSSQL(SQL Server)과 Slack 연동하기

Juseong Han·2023년 3월 16일
1

DB와 협업툴인 Slack을 연동하면 여러가지 이점을 얻을 수 있다. 애플리케이션의 실시간 오류를 파악하거나 특정 데이터가 들어왔을 때 알림을 받는다던가 무궁무진한 프로세스를 만들 수 있다.

1. Slack에 앱 추가하기

Slack에 들어가 앱관리 페이지로 들어간다.
경로는 다음과 같다.
좌측 상단 햄버거버튼 ▷ 파일 ▷ 설정 및 관리 ▷ 앱관리


이후 'Incoming Webhook' 또는 '수신 웹후크'를 검색한다. 첨부 내 가장 위의 수신웹후크가 우리가 사용할 앱이다.


Slack에 추가를 누른다.


이후 웹훅을 받게될 채널을 지정하여 앱을 추가하여 마무리한다.

다음과 같이 추가된 incoming webhook을 클릭하고 구성을 선택한다.


웹후크 URL이 Slack에 웹훅을 보낼 URL이 될 것이다

2. 테스트해보기

기본적으로 프로그램을 통해 API를 호출하면 이정도 내용으로도 아주 간단하게 구현가능하다. 하지만 우리는 DB(MSSQL)과 연동할 것이므로 좀 다른 호출방법이 필요하다.

앱이 정상적으로 설치되었는지 curl 명령을 이용해 테스트를해본다.

curl -X POST -H "Content-Type: application/json" --data "{'text': 'test message'}" https://hooks.slack.com/services/웹후크URL

아주 잘 온다.

3. MSSQL에서 curl 호출하기

MSSQL에서 cmd 명령을 호출하려면 xp_cmdshell을 사용하면 된다.

EXEC xp_cmdshell 'curl -X POST -H "Content-Type: application/json" --data "{''text'': ''test message''}" https://hooks.slack.com/services/웹후크URL'

따옴표에 주의하자.......

아마 정상적으로 넘어갈테지만 테스트 텍스트를 한글로 바꿔서 해보면 이상한 외계어가 넘어온다.


뭐라는겨?

이는 cmd가 기본적으로 949인코딩을 사용하기 때문인데 이를 한글을 인코딩하게 하려면 65001(UTF-8)로 변경해야한다.

3-1. cmd 인코딩 변경하기

커맨드라인 인코딩을 변경하는 방법은 여러가지가 있지만 레지스트리를 편집하여 변경하는 방법에 대해 소개하겠다.

레지스트리 편집으로 들어가 ( win + r ▷ regedit 실행) 다음 경로를 찾는다.

HKEY_LOCAL_MACHINE\SYSTEM\CurrentControlSet\Control\Nls\CodePage

CodePage의 항목을 보면 ACP, MACCP, OEMCP 등의 키가 있는데 이 세가지를 전부 65001로 변경한다. 이후 컴퓨터를 재시작하면된다.

3-2. 문제

개인프로젝트를 개인 PC에서 서버를 돌린다면 매우 간단하다. 하지만 대부분은 DB는 서버와 분리되어있고 이미 운영상태에 돌아가는 서버라면 컴퓨터의 재시작은 판도라가 상자를열어서 세상을 리셋시켜야만하는 제우스의 마음과 같을 것이다.

이를 위해 재시작하지않으려 발악하며 갖가지 방법을 모두 시도했었다. 레지스트리 편집 후 chcp로 인코딩 바꾸기.. Windows용 iconv를 설치해서 인코딩 바꾸기... 그 무엇도 되지않았다.. 삽질하지 마시라고 이 글을 쓴다..ㅠㅠ

4. 해결법

powershell을 이용하는 방법이다. powershell은 기본적으로 인코딩이 한글을 지원하고, curl같은 구닥다리 통신방법을 쓰지 않고 Rest 통신만을 위한 명령또한 가지고있다.

cmd명령줄에서도 powershell 명령을 사용할 수 있는데, 이는

powershell.exe -Command "cmd"

다음과같은 명령을 하는 것이다.

각설하고 완성된 명령은 다음과같다.

EXEC xp_cmdshell 'powershell.exe -Command "[Net.ServicePointManager]::SecurityProtocol = [Net.SecurityProtocolType]::Tls12; $json = @{text = '''+ @ERR_MSG + '''} | ConvertTo-Json; Invoke-RestMethod -Uri '''+ @SLACK_URL +''' -Method POST -Body $json -ContentType ''application/json;charset=utf-8''"'
[Net.ServicePointManager]::SecurityProtocol = [Net.SecurityProtocolType]::Tls12;

위 구문은 TLS통신을 위한 설정으로 매 API호출시마다 함께 전송하면된다.

$json은 파이프라인 연결자(|) 이후의 ConvertTo-Json을 통해 Json 형식으로 변환된다.

5. 발생한 문제

나는 실시간으로 에러가 많이 떨어지면 개발자가 알 수 있도록 이를 구현했는데 몇가지 오류가 발생했다.

첫째로는 에러메시지에 따옴표가 포함된 경우이다. 이는 powershell에 명령을 전달할 때 따옴표 짝이 맞지않는 오류를 발생시킬 수 있다. 전부 REPLACE 해줬다.

둘째로는 에러스택의경우 한줄이 아닌 여러줄로 나오는 경우가 대부분이고 DB에서 보기에는 긴 공백처럼 보이지만 실제로는 개행문자인 경우가 있다. 이는 powershell에 명령을 전달할 때 명령이 여러줄로 쳐지게 되며 다음과 같은 오류를 리턴할 수 있다.

문자열에 ' 종결자가 없습니다.

해결법은 역시나 REPLACE를 이용하는 방법이다.

SET @ERR_MSG = REPLACE(@ERR_MSG, '''', '')
SET @ERR_MSG = REPLACE(@ERR_MSG, '"', '')
SET @ERR_MSG = REPLACE(REPLACE(@ERR_MSG, CHAR(10), ' '), CHAR(13), ' ')

감사합니다

profile
개발이 하고 싶어요💻 개발이 너무 재밌는 Juseong입니다.🖐

0개의 댓글