User Tools

Site Tools


lecture:ring:docs

This is an old revision of the document!


소개

Leiningen으로 새 프로젝트를 생성한다.

$ lein new hello-world
$ cd hello-world

project.clj 파일의 dependencies에 ring-core와 ring-jetty-adapter를 추가한다.

(defproject hello-world "1.0.0-SNAPSHOT"
  :description "FIXME: write"
  :dependencies [[org.clojure/clojure "1.4.0"]
                 [ring/ring-core "1.1.8"]
                 [ring/ring-jetty-adapter "1.1.8"]])

다음으로 src/hello_world/core.clj 파일을 열어, 간단한 핸들러를 작성한다.

(ns hello-world.core)
 
(defn handler [request]
  {:status 200
   :headers {"Content-Type" "text/html"}
   :body "Hello World"})

이제 핸들러를 어댑터에 연결하면 된다. Leiningen으로 REPL을 실행한다.

$ lein repl

REPL에서 위의 핸들러로 Jetty 어댑터를 실행한다.

=> (use 'ring.adapter.jetty)
=> (use 'hello-world.core)
=> (run-jetty handler {:port 3000})

이제, http://localhost:3000으로 브라우져로 접속하면 된다.

왜 링인가?

Ring을 사용할 때의 장점

  • 클로져의 함수와 맵으로 웹 어플리케이션 작성이 가능하다.
  • 자동으로 재로딩되는 개발 서버에서 웹 어플리케이션을 구동할 수 있다.
  • 웹 어플리케이션을 자바 서블릿으로 컴파일한다.
  • 웹 어플리케이션을 자바 war 파일로 패키징한다.
  • 많은 기작성된 미들웨어를 사용할 수 있다.
  • Amazon Elastic Beanstalk이나 Heroku 같은 클라우드 환경에 배포할 수 있다.

Ring은 클로져로 웹 어플리케이션을 작성하는 현재 사실상의 표준이다. Compojure나 Moustache, Noir 같은 고수준 프레임워크들은 Ring을 공통 기반으로 하고 있다.

Ring이 저수준 인터페이스를 제공하지만, 고수준 인터페이스를 사용할 때 Ring이 어떻게 동작하는지 이해하는 것은 도움이 된다. Ring에 대한 기본적인 이해없이는, 미들웨어 작성을 할 수가 없고, 디버깅하는 것도 매우 어렵다.

개념

Ring으로 개발되는 웹 어플리케이션은 다음 4개의 구성요소를 갖는다.

  • 핸들러
  • 요청
  • 응답
  • 미들웨어

핸들러

핸들러는 웹 어플리케니션을 정의하는 함수이다. 핸들러는 HTTP 요청을 나타내는 클로져 맵을 인자로 받고, HTTP 응답을 나타내는 클로져 맵을 리턴한다.

다음 예제를 보자.

(defn what-is-my-ip [request]
  {:status 200
   :headers {"Content-Type" "text/plain"}
   :body (:remote-addr request)})

이 함수는 맵을 리턴하는데, Ring은 이것을 HTTP 응답으로 바꾼다. 응답은 웹 어플리케이션을 접근하는데 사용된 IP 주소를 담은 평이한 TEXT 파일로 리턴된다.

핸들러는 다양한 방법을 거쳐 웹 어플리케이션으로 전환될 수 있다. 다음 섹션에서 이를 설명한다.

요청

HTTP 요청은 클로져 맵으로 나타낸다. 항상 존재하는 표준키도 있지만, 요청은 미들웨어에 의해 사용자 키를 갖기도 한다.

표준키들:

  • :server-port : 요청이 처리되는 포트
  • :server-name : 서버 이름, 혹은 서버 IP 주소
  • :remote-addr : 클라이언트, 혹은 요청이 보내진 최종 프록시의 IP 주소
  • :uri : 요청 URI (도메인 이름 뒤의 전체 경로)
  • :query-string : 쿼리 스트링
  • :scheme : 전송 프로토콜 :http 혹은 :https
  • :request-method : HTTP 요청 메소드 :get, :head, :options, :put, :post, :delete.
  • :content-type : 요청 바디의 MIME type
  • :content-length : 요청 바디의 바이트 길이.
  • :character-encoding : 요청 바디에서 사용되는 문자 인코딩.
  • :headers : 해당 헤더 값 스트링에 대한 소문자 헤더 이름 스트링의 클로져 맵.
  • :body : 요청 바디에 대한 InputStream.

응답

응답 맵은 핸들러에 의해 만들어지는데, 3개의 키를 갖는다.

  • :status : HTTP 상태 코드. (200, 302, 404 등)
  • :headers : HTTP 헤더 이름에 대한 헤더 값의 클로져 맵. 이 값은 스트링일 경우 하나의 이름/값 헤더가 HTTP 응답으로 보내지고, 스트링 컬렉션인 경우 이름/값 헤더가 각 값에 따라 보내진다.
  • :body : 응답 바디가 응답 상태 코드에 적절하다면, 응답 바디를 나타낸다. 바디는 다음 4가지 타입중 하나일 수 있다.
    • String : 바디가 클라이언트에 바로 보내진다.
    • ISeq : 시퀀스의 각 요소가 클라이언트에 스트링으로 보내진다.
    • File : 참조된 파일의 콘텐츠가 클라이언트에 보내진다.
    • InputStream : 스트림의 콘텐츠가 파일에 보내진다. 스트림이 비게 되면 스트림은 닫힌다.

미들웨어

응답 만들기

lecture/ring/docs.1367994505.txt.gz · Last modified: 2019/02/04 14:26 (external edit)