집을 비우면 호두가 뭘 하는지 너무나 궁금했던 아내는 결국 '펫츠뷰'라는 제품을 구매하기에 이르렀다. 이윽고 도착한 제품은 과연 네트워크 지식이 전무한 사람이라도 설치하기가 쉽도록 되어 있긴 했으나 아래와 같은 점이 너무나 거슬렸다.
개요
집을 비우면 호두가 뭘 하는지 너무나 궁금했던 아내는 결국 '펫츠뷰'라는 제품을 구매하기에 이르렀다. 이윽고 도착한 제품은 과연 네트워크 지식이 전무한 사람이라도 설치하기가 쉽도록 되어 있긴 했으나 아래와 같은 점이 너무나 거슬렸다.
전용 앱을 통하거나
펫츠뷰 회사 홈페이지를 통해서 보아야 한다
우리 집 거실에 놓인 카메라를 남의 서버를 통하거나 남의 앱을 통해서 본다는게 아무래도 못내 께름칙하거니와, 윈도폰에는 펫츠뷰 앱이 없다는 점도 너무나 안타까울 따름이다.
목표
기본적으로 펫츠뷰 서버를 통하지 않고, 내 폰에서도 볼 수 있도록 해야 한다.
구현방법
카메라 API 확인
펫츠뷰는 국내 회사지만, 카메라 자체는 외제 IP CAM 에다가 자사 연동 기능과 상표만 붙여서 파는 걸로 보였다. IP cam 이므로 카메라의 ip 에 직접 접속해보니 웹 UI 가 존재했다. 중국어의 흔적이 있는 걸로 보아서는 중국 제품인 것 같긴 한데... 여튼 웹 UI 소스를 이리저리 까서 확인한 바로는 여러 회사의 IPCAM 들이 공통적으로 사용하는 CGI API 를 쓰고 있는 점을 알 수 있었다.
서버
집에서 하는 일 별로 없이 노는 라즈베리파이2가 나설 차례다. 요녀석은 사실 미디어서버의 기능도 하고 있지만, 집구석에서 미디어서버 기능을 쓰는 동안은 펫츠뷰를 볼 일이 없으니 부하가 겹치지 않는다는 판단 하에 이놈에게 조금 더 짐을 지우기로 했다.
필요한 기능은 간단한데, 화면을 보여주는 부분과 카메라를 움직이는 부분이다. 사실 IP cam 의 웹 UI 가 있으니까 그걸 그냥 쓰면 되지 않을까 하는 생각도 잠시 했었지만 외부에서 캠으로 바로 접근할 수 있는 경로를 노출하는 건 마음이 께름칙하고, 웹 UI가 딱히 완성도가 높은 것도 아니었기 때문에 인증을 거쳐서 제한된 기능에만 접근 가능하도록 제작하기로 했다.
간단하게 만드는건 역시 node.js 가 편하니까 node.js 에서 http 를 통해 단순한 웹서버로 개발했다.
카메라 화면
이 IP cam 에서는 몇 개의 동영상 스트림을 지원하긴 하는데 하나같이 애매한 놈들 뿐이었다. iOS 기기를 위한 mov 형태의 스트림과 rtsp 프로토콜을 통한 스트림 등이 있었지만 웹에서 바로 보여줄 수는 없었기 때문에 둘 다 OUT.
IP CAM 자체적으로 현재 화면을 jpg 이미지로 제공하는 부분이 있어서 해당 이미지를 사용하기로 했다.
고화질과 저화질 이미지가 있는 경로가 /tmpfs/snap.jpg 와 /tmpsf/auto.jpg 로 미묘하게 달라서(아마 이건 펌웨어의 버그인 것 같지만...고칠 수가 없으니 무슨 소용이 있겠는가) 꽤 삽질을 했던 것을 빼면 별다른 어려움은 없었다.
카메라 이동
처음에는 웹 UI 소스를 참조해서 좌우상하 버튼을 누를 때마다 일정 간격으로 이동하도록 했지만 사용해보니 불편하기 짝이 없었다. 그래서 cgi 문서를 확인하고 좌우상하로 이동 시작 => 이동 중단 신호가 올 때까지 계속 이동하도록 구현을 변경하고, 웹페이지에서 버튼 mousedown/touchstart 에서 이동 시작 신호, mouseup/touchend 이벤트에서 이동 중단 신호를 보내도록 변경했다.
인증
그냥 미리 지정한 ID / PW 만 가지고 인증하도록 했다. 각 요청마다 http 헤더나 get 파라미터로 딸려오는 인증 정보를 확인하는 정도에서 끝.
웹
간단하게 html 을 작성하고, jquery 에서 ajax 를 통해 요청을 보낼 때 http 헤더에 인증 정보를 넣도록 beforeSend 핸들러를 간단히 추가했다. 위에서 말한 대로 버튼의 mousedown/mouseup, touchstart/touchend 핸들러를 적절히 코딩하고, 로그인 유지 기능은 localStorage 를 써서 간단하게 붙였다.
쓰고 나니 그냥 다 간단하게 해서 자세히 쓸 내용이 없네..
네트워크
어차피 도메인 갖고 있는게 있으니 서브 도메인을 하나 추가해서 우리집 외부 IP 로 설정했다. 그리고 포트 포워딩을 통해서 특정 포트로 오는 요청을 라즈베리파이로 돌려주면 끝.
결과
이미지 방식이다보니 소리를 들을 수가 없고, 마이크를 통해 IP cam 에 달린 스피커로 소리를 전송하는 기능도 API 를 찾지 못해서 붙일수가 없었다. 그래도 한나절 붙들고 만든 것 치고는 좋은 결과인듯.
(감시의 눈길을 피할 수 없게 된 호두)