Header

  1. View current page

    딥뿔이 자라나는 노트

Profile_image?t=1225424611&type=big
나를 바꾼 똑똑한 생활 습관, 스프링노트 - 여러분도 지금 시작해보세요!
71

뜨거운 루비 - 함께 전하는 루비 뉴스

개인적으로 루비 소식을 계속 전하려는 노력을 여기, 저기에서 해왔지만, 혼자의 힘으로는 꾸준한 정보를 제공하는 일이 쉽지 않다. 그래서 함께 모여서 뉴스 사이트를 만들어보면 어떨까 싶어 아래처럼 뜨거운 루비라는 다소 촌스러운(^^) 이름의 사이트를 하나 꾸렸다.

 

http://hot.rubykr.org/

 

회원 가입없이 누구나 글을 쓸 수 있도록 했으니, 여러분이 참여해주셔서 RubyFlow처럼 유용한 사이트가 될 수 있기를 바란다. 그리고 한국 루비 커뮤니티에도 뜨거운 열정과 재미있는 이야기꺼리를 계속 전달해줄 수 있으면 좋겠다.

 

여기까지가 새로운 사이트 오픈에 대한 짧은 변이었고, 지금부터는 조금 더 재미있는 이야기를 해보자. 뜨거운 루비는 웹 개발에 익숙한 사람이면 누구나 1~2일만에 만들 수 있는 규모의 작은 사이트다. 그렇지만, 조금만 더 들여다보면 이 글을 읽는 분들이 흥미를 보일만한 내용들이 몇가지 있다. 이 사이트가 슬러거의 사촌쯤되는 DB를 전혀 사용하지 않은 매시업 사이트라는 점, 레일스가 아니라 Sinatra라는 생소한 마이크로 프레임워크를 사용했다는 점, 오픈소스라는 점 등이다.

 

지금부터 개발하면서 떠올렸던 몇가지 키워드를 가지고 이야기를 풀어보자.

 

레일스 닮은 꼴, Merb

Merb는 레일스의 대안으로 루비계에서 새롭게 떠오르고 있는 스타다. 레일스가 했던 경험 위에서 후발 주자라는 이점을 살려 더 가볍고, 나은 그리고 성능도 좋은 레일스를 추구하고 있다. 레일스가 아닌 대안 프레임워크를 사용해보자라는 것이 이 프로젝트의 목표 중 하나였기에, 자연스럽게 Merb를 손에 잡고 문서를 따라하며 만들기 시작했다. 그런데 재밌는 사실은 Merb가 레일스와 비슷하다는 점이 단점으로 작용했다는 것이다. 거의 같지만 약간씩 다른 모습이 신기하기도 했지만, 어디인지 모르게 거슬리는 묘한 기분이었다. 그리고 결정적으로 Merb가 벌써 레일스 수준으로 복잡한 프레임워크가 되어 있다는 느낌이 들었다. Merb는 레일스와 함께 계속 발전해주기를 기대한다. 서로 계속 디자인과 내부 구현을 섞어가면서 말이다. 이미 나한테는 Merb와 레일스가 거의 같은 것으로 보인다. 이번에 만들려는 사이트는 굉장히 기능이 작은 사이트이기 때문에, 개발 환경도 레벨이 맞아야한다는 생각에 살포시 rm 명령을 내렸다.

 

작지만 강한 Sinatra

023 작은 웹 애플리케이션 개발에 최적화된 Sinatra라고 글을 썼던 기억이 떠올랐다. 그 때의 느낌이 꽤 좋았는지, 가장 먼저 떠오르다. 그리고 다시 꺼내들어보니 역시나 완성도 높은 좋은 프레임워크라는 느낌이 들었다. 루비로 만들어진 웹 프레임워크는 기본기가 탄탄하다. 레일스라는 스타로 부터 어떻게 만들어야 프로그래머를 기쁘게 할 수 있는지에 대한 암묵적인 교육을 받아왔고, Rack이라는 베이스 라이브러리가 있기 때문이다. 경험과 이를 받쳐주는 라이브러리가 있으니, 평균이 높은건 어찌보면 당연하다.

 

일단, 간결한 directory 구조가 마음에 든다.

 

 

이게 구조의 전부다. 작은 사이트를 만들때까지 app, controller, view, models, scripts, lib, vendors 이런 디렉터리를 줄줄이 달고 다닐 필요는 없을 것이다. 서버 구동도 간편한다 단순히 애플리케이션(이 사이트는 hotruby.rb)을 실행해주는 것으로 끝이다.

 

만들어지는 코드는 더 간결하다. 아래 코드가 뜨거운 루비 코드의 거의 전부다. 나머지는 뷰 템플릿과 모델 대신 스프링노트와 연동하는 부분들이다.

 

  1. %w(rubygems sinatra haml hpricot springnote).each{|lib| require lib}

    before do
      @springnote = SpringnoteStore.new
    end

    get '/' do
      @items = @springnote.items(params[:page] || 1)
      haml :index
    end

    get '/items.atom' do
      header 'Content-Type' => 'application/atom+xml; charset=utf-8'
      @items = @springnote.items(1)[1..-1]
      haml :atom, :layout => false
    end

    get '/write' do
      haml :write
    end

    post '/write' do
      @springnote.write params[:rref].to_s, params[:rres].to_s, params[:rree].to_s if params[:rref].to_s.length > 0 && params[:rree].to_s.length > 0
      redirect '/'
    end

    helpers do
      def sidebar
        @springnote.sidebar.source.to_s rescue ""
      end
    end

 

요즘 Fat Model, Thin Controller를 따르는 것이 대세이기에, 이 관점에서 보면 위 코드처럼 패턴우매칭을 이용한 라우팅과 하나의 코드 블럭으로 이뤄진 액션은 좋은 접근이다. 이 30여줄의 코드와 뷰 템플릿만으로 그럴싸한 구조를 가진 사이트가 만들어지니 꽤 기분 좋은 일이 아닐 수 없다.

 

정리하면, Sinatra는 꼭 필요한 기본을 갖춘, 작은 사이트를 만드는데 최적화된 추천할만한 프레임워크다.

 

데이터 저장소로서의 스프링노트

계획은 DataMapper ORM을 사용하는 것이다. 그런데, Sinatra의 간결한 모습을 보니 갑자기 데이터베이스를 만들고, 스키마를 설정하고, 또 서버에 배포하고 설정하고 마이그레이션을 하는 일련의 과정이 너무 큰 귀찮음으로 다가왔다. Sqlite도 있지만, 이것조차도 귀찮았다. 그래서 이번에도 (언제나 그렇듯) 스프링노트를 데이터 저장소로 사용하기로 했다. 이런걸 주최측의 농간이라고 하나? 암튼, 슬러거처럼 글 목록을 관리하는 메타 페이지가 하나 있고, 사이드바의 내용을 담은 페이지도 하나 있다. 그리고 일별로 하나씩 페이지를 만들어 여기에 뉴스를 차례로 담는다.

 

결과적으로 자연스럽게, 하루에 한 페이지씩 모인 다이제스트 페이지가 생겼고, 나는 데이터 관리 및 운영에 대한 걱정에서 벗어날 수 있게 되었다(이건 스프링노트 개발자역의 deepblue가 최선을 다해서;;;;). 그리고 첨부 파일 저장소, 검색 기능, HTML Validation 등, 따로 구현하려면 시간이 필요한 기능을 거의 공짜로 얻을 수 있게 되었다. 아직 삭제 기능이 없는데, 테스트로 만든 포스트들을 지우기 위해 택한 방법은 글의 리비전 히스토리에서 몇시간 전의 글로 복구해주는 것이었다 :) 물론, 익숙한 RDBMS가 주는 장점을 누리지 못한다는 단점도 있지만, 이는 조금만 생각을 바꾸면 얼마든지 다른 방법으로 해결할 수 있기도 하다.

 

  • springnote.rb - 뜨거운 루비의 모델 구현체로 스프링노트와의 연동을 담당한다.

 

좋은 오픈 API가 있고, 또 자신의 컴퓨팅 파워와 스토리지를 거의 공짜로 제공해주는 사이트가 많다. 이제는 DB도 없이, 서버 하나도 없이 단순히 HTML 파일 몇개만 업로드하는 것으로도 충분히 화려한 애플리케이션을 만들 수 있다. 맞는 방향인지는 따져봐야겠지만, 개발자가 좀 더 생산적인 일을 하게 돕는 방향인 것만은 확실하다.

 

덧) 이 기능을 구현하기 위해  먼저 SpringnoteClient 라이브러리를 만들었는데, 이 사이트를 만드는 것보다 더 오랜 시간이 걸린 것 같기도 하다. :)

 

간결함이 살아있는 Haml

루비 프로젝트에서 사용할 수 있는 다양한 템플릿 엔진에서 설명한 것 처럼, 참 다양한 템플릿 엔진이 있다. 그런데 요즘에는 유난히도 Haml의 간결한 결과물이 마음에 든다. 이건 템플릿계의 파이썬이다. 딱 필요한 코드만 쓰는 군더더기 없는 모습이 매력적이다. UI 개발직군과의 협업이 많지 않다면, 앞으로도 Haml을 애용할 것 같다.

 

나의 구세주 BlueprintCSS

나는 CSS가 참 어렵다. 내가 사용하는 브라우저에서 온전하게 렌더링되게 만드는데도 꽤 많은 시간이 필요한데, 여러 브라우저의 서로 다른 렌더러까지 고려해서 코딩하라는 현실이 매우 가혹하게 느껴지기만 한다. 그래도 BueprintCSS 프레임워크가 있다는 사실이 얼마나 다행스러운지 모른다. 요즘 새로운 프로젝트를 열면 가장 먼저 하는 일이 이 css 파일 3개를 복사하는 일이다 :)

 

새로운 생존 전략, 매시업

댓글 기능이 필요하다는 생각을 하고, 실제 구현을 완료하는데까지 걸리는 시간은 정확히 10분이었다. Disqus에서 제공하는 AJAX API 덕분이다. 언제가 CAPTCHA 기능이 필요해질텐데, 이를 위해 준비해둔 무기는 라이브러리도 젬도 아닌 reCAPTCHA API다. 다른 대안으로 Akismet도 있다. 얼마나 많은 OpenAPI를 알고, 또 사용할 수 있는지가 경쟁력이 되는 시대가 된지도 모르겠다. 어쨌거나 오늘도 나의 오픈API 예찬론은 계속된다.

 

배포의 신기원, Rack+Passenger

Sinatra를 이용해 금방 흡족한 애플리케이션을 만들었다. 이제 어떻게 배포할지가 잠깐 고민이었다. 하지만 Railsconf2008에서 Passenger가 2.0 버전부터 Rack을 지원한다는 발표를 했다는 생각에 미치자 모든 근심이 사라졌다. 그리고 실제로 RC1을 설치하고 문서를 따라 설정해보니 30분여를 투자해서 쉽게 설정을 마칠 수 있었다.

 

Passenger는 정말 루비 웹 프레임워크를 한단계 진보시키고 있다는 생각이 든다. 너무 프로모션을 열심히 해서 불필요한 buzz를 만든다는 안티성 발언도 있지만, 뭐 어떤가 많은 사람들이 Passenger를 통해 루비 애플리케이션 배포가 매우 쉬워졌음을 알게 되면 좋을 일이라고 본다.

 

Rack은 루비 개발자에게 커다란 선물이다. Rack 덕분에 수많은 웹프레임워크들이 시너지를 낼 수 있고, 자신만의 에지를 날카롭게 하는데만 집중할 수 있게 되었다. (참고: RACK속에 들어간 레일스) 좋은 세상이다.

 

소스 코드

뜨거운 루비는 오픈소스 프로젝트다. 누구든 개발에 동참하실 수 있다는 의미다. 그리고 협업을 간절하게 원하고 있다고 하다. 전체 소스코드는 언제나처럼 github에 있다.

 

  1. git clone git://github.com/deepblue/hotruby.git

 

결언

처음에는 뉴스 공유 사이트가 필요하다는 순수한 목적(?)에서 시작한 프로젝트였지만, 뒤로 갈수록 흥미로운 기술들에 빠져들어 정말 며칠동안 굉장히 즐거웠다. 다시 순수한 목적으로 돌아와서 이 사이트가 도움되는 사이트가 되기를 희망해본다.

 

참고

 

Tags

History

Last edited on 06/11/2008 23:41 by deepblue

Comments (0)

You must log in to leave a comment. Please sign in.