글쓴이 보관물: dryrain

디지털액자 (2)

먼저 하드웨어 세팅을 해 봅시다. 준비물은 다음과 같습니다.

  1. 남는? TV 또는 모니터
  2. 우분투가 올라가는 업보드/라즈베리파이/미니PC
  3. OS 설치용 USB 1개
  4. 유선 키보드, 마우스
  5. HDMI 케이블 1개

라즈베리파이는 라즈비안도 가능할 수 있습니다. 일단 크로미움이 깔리고 UI가 잘 뜨면 됩니다. 키보드/마우스는 무선이라도 블루투스가 아닌 unifying 수신기가 달린 제품이면 상관 없습니다.

우분투 버전은 Desktop 버전을 설치했습니다. 사용 이유는 일단 UI 가 설치되어 있어 구성의 편리함이 있을 것 같았습니다.

우선 우분투를 설치 안내에 따라 설치합니다. 그리고 kiosk 라는 사용자를 하나 만듭니다. 나중 관리를 위해 메인 계정은 살려두고 kiosk 로 자동 로그온이 되도록 할 겁니다.

우선 패키지를 업데이트 하고 몇개를 새로 설치할 겁니다. unclutter 패키지는 일정 시간이 지나면 마우스를 숨겨주는 패키지입니다.

sudo -s
apt update  && apt upgrade -y && apt install -y chromium-browser unclutter

그리고 자동 로그인을 위해 /etc/gdm3/custom.conf 파일을 편집합니다. gdm3 는 디스플레이 매니저 이름이며 다른 디스플레이 매니저를 쓴다면(lightdm 등) 그 설정 파일을 수정해주면 됩니다.

[daemon]
AutomaticLoginEnable=true # <-- 여기
AutomaticLogin=kiosk # <-- 여기

그리고 kiosk 홈 디렉토리에 chromium 을 실행하는 스크립트를 하나 만듭니다. kiosk.sh

#!/bin/bash

# Run this script in display 0 - the monitor
export DISPLAY=:0

# Hide the mouse from the display
unclutter &

# If Chromium crashes (usually due to rebooting), clear the crash #flag so we don't have the annoying warning bar
sed -i 's/"exited_cleanly":false/"exited_cleanly":true/' /home/kiosk/.config/chromium/Default/Preferences
sed -i 's/"exit_type":"Crashed"/"exit_type":"Normal"/' /home/kiosk/.config/chromium/Default/Preferences

# Run Chromium and open tabs
/usr/bin/chromium-browser --window-size=1920,1080 --kiosk --incognito --window-position=0,0 http://URL &

크로미움에는 키오스크 모드가 있습니다. 맥도날드 같은 곳에 설치된 키오스크 를 의미합니다. 전체 화면으로 실행되며 개발자 모드 비활성화, 알림 억제 등의 효과가 있습니다. 키오스크 모드라고 해서 어떤 동작을 해야 한다 라는게 명세되어 있지는 않고 각 브라우저마다 동작이 다 다릅니다. 일단 지금 상황에서는 전체화면으로 실행되고 주소 바만 없으면 되므로 키오스크 플래그를 줘서 실행합니다.

그리고 방문 기록 등 쓰레기 파일을 남기고 싶지 않으므로 incognito(private mode) 플래그를 줘서 실행합니다. URL 칸에는 URL 을 입력하면 됩니다.

다음은 kiosk.sh 를 자동 실행하게 하는 파일을 작성합니다. 디스플레이 매니저마다 설정이 다를 수 있습니다. home/kiosk/.config/ 아래에 autostart 디렉토리를 만들어 줍니다. 그리고 kiosk.desktop 를 파일을 만들고 편집합니다.

[Desktop Entry]
Type=Application
Name=Kiosk
Exec=/home/kiosk/kiosk.sh
X-GNOME-Autostart-enabled=true
StartupNotify=true
Terminal=false
kiosk 모드 작동 영상(타임랩스)

다음은 디스플레이에 표시될 웹 서버를 작성하도록 하겠습니다.

파이썬 라이브러리 소개: Celery

비동기 작업을 손쉽게 관리해주는 라이브러리 Celery 에 대해 간단히 소개 드리겠습니다.

파이썬에서는 비동기 모듈을 사용하지 않으면 기본적으로 동기 방식으로 작업을 처리합니다. asyncio를 사용하지 않고 비동기 작업을 원할 때 Celery 를 사용하면 됩니다.

Celery 는 라이브러리지만 broker 와 backend 가 필요합니다. broker는 큐이고 backend 는 샐러리가 처리한 결과물을 저장합니다. 아래 그림을 보시면 이해가 쉽습니다.

Celery 작동 흐름

python 에서 celery 라이브러리를 이용해 작업 요청을 하면 celery 라이브러리는 broker 에 메시지를 삽입합니다(큐에 추가). 다른 프로세스인 worker 는 대기하고 있다가 큐에 메시지가 들어오면 읽고 작업을 수행합니다. 작업이 완료되면 backend 에 작업 결과물을 저장합니다.

그림에서는 마치 동기적인 작업처럼 그려 놓았는데 작업 요청은 non-blocking 입니다. 따라서 시간이 오래 걸리는 여러 개의 작업을 먼저 요청해 두고 다른 작업을 하다가 나중에 결과 수신을 해도 되는 것이죠. 수신의 경우엔 blocking 입니다. 작업이 완료될때까지 계속 대기합니다. 이 경우 코드는 아래와 비슷해질 것입니다.

def main():
    # 시간이 오래 걸리는 작업 요청
    hw1 = heavy_work_1.delay()
    
    # 다른 작업 수행
    work2_result = work2()
    ...
    
    # 결과 수신
    hw_result = hw1.get()
    
    return hw_result, work2_result

이번에는 흔한 예제를 보겠습니다. 회원가입 예시인데요. 회원가입을 하게 되면 database 에 레코드를 추가하는 작업은 오래 걸리지 않지만 이메일 발송이 2초에서 3초 정도 소요되는 경우가 발생합니다. 이런 절차를 전부 기다리게 되면 고객이 가입 버튼을 누르고 2초에서 3초정도 기다리게 됩니다. 이 때 celery 에게 메일 발송 작업을 요청하고 고객에게 응답을 바로 전송하면 지연 시간 없이 다음 페이지로 넘어가게 됩니다. 확인 메일 발송에는 보통 반환값을 기다릴 필요가 없기 때문에 결과를 수신하는 코드는 제거했습니다.

def register_user(username, password, email):
    # 데이터베이스에 회원 레코드 삽입
    db_success = insert_to_database(username, password)
    
    if not db_success:
        return False
        
    # 확인 메일 발송 (non-blocking)
    send_verification_email.delay(username, email)
    
    # 메일 발송 기다리지 않고 응답 전송
    return True

두 가지 시나리오로 간단하게 celery 라이브러리를 알아봤는데요. 기회가 된다면 celery 의 지원 범위와 사용 예시를 포스팅하도록 하겠습니다.

토이프로젝트 디지털액자 (1)

원룸에 기본 옵션으로 있는 TV를 다양한 정보가 담긴 디지털 액자?로 만드는 프로젝트입니다.

자취를 하면 원룸에 옵션으로 딸려오는 TV가 있는데요. 이건 화질도 좋지 못하고 공간만 잔뜩 차지합니다. 개인적으로 TV를 자주 보지 않기 때문에 무관심으로 1년을 지낼 수도 있지만 마침 눈에 잘 밟히는 자리에 있기에 어떻게든 활용해 보려 합니다.

일단 구상하고 있는 액자 기능은 다음과 같습니다.

  1. 오전 6시에 자동으로 켜져야 함
  2. 오후 9시에 자동으로 꺼져야 함
  3. 주간 날씨와 평균 기온 표시
  4. 시간별 경산시 기온 표시
  5. 회사 이메일 / 개인 이메일 안 읽은 개수 표시
  6. 주간 일정 표시

그리고 준비물은 아래와 같습니다

  1. TV
  2. 미니 PC(라즈베리파이 같은)
  3. 리모컨 전파 발신기(?)

티비를 켜고 끄기 위해서 3번이 필요할 것 같습니다. 아니면 IoT 콘센트 등으로 전원을 내리는 방법이 있는데 다시 켰을 때 TV가 잘 켜질지는 미지수입니다.

그리고 디지털 액자를 만들기 위해 해결해야 할 문제입니다.

  1. 디스플레이 되는 웹 서버
  2. 여러 데이터 소스에서 데이터 조회 및 가공
  3. 미니 PC를 부팅했을 때 자동으로 웹 페이지 띄우기
  4. 시간에 맞춰 TV ON/OFF 신호 송신

일단 계획은 이렇게 잡고 미니 PC부터 다뤄보도록 하겠습니다.