0%

Hoplon入門- Part1: Bootのバージョン

HoplonはClojureとClojureScriptで書けるフルスタックなWebフレームワークです。ClojureのビルドツールにはBootを使います。Bootには1.x系2.x系がありますが残念ながら後方互換性がありません。現状ではHoplonはBoot 1で動作します。バージョンの問題で少し嵌まりますがClojureはScalaほど消耗しません。

プロジェクト

適当なディレクトリにHoplon用のプロジェクトを作成します。

$ cd ~/clojure_apps/
$ tree -L 1
.
├── Dockerfile
├── docker-compose.yml
└── m2

Dockerfile

ビルドツールはLeiningenとBootの1.x系と2.x系をインストールします。Bootのコマンドはそれぞれboot1boot2としています。デフォルトではBootは非rootユーザーが推奨されるためDockerには作業ユーザーのdockerを作成しています。

~/clojure_apps/Dockerfile
FROM clojure
MAINTAINER Masato Shimizu <ma6ato@gmail.com>

WORKDIR /usr/src/app

ADD https://github.com/boot-clj/boot/releases/download/2.0.0/boot.sh /tmp/
RUN mv /tmp/boot.sh /usr/local/bin/boot2 && \
chmod 755 /usr/local/bin/boot2

ADD https://clojars.org/repo/tailrecursion/boot/1.1.1/boot-1.1.1.jar /tmp/
RUN mv /tmp/boot-1.1.1.jar /usr/local/bin/boot1 && \
chmod 755 /usr/local/bin/boot1

RUN adduser --disabled-password --gecos '' --uid 1000 docker && \
mkdir /home/docker/.m2 && \
chown -R docker:docker /usr/src/app /home/docker/.m2

VOLUME /home/docker/.m2
USER docker
RUN lein

Hoplonで使うBootについて

Hoplonは現状Boot 1で動作します。Runtime Exception #41にissueがあります。残念ながらBootには後方互換性がありません。Boot2を使うとjava.lang.RuntimeExceptionが発生します。

docker-compose.yml

Docker Composeの設定ファイルです。boot1サービスではHoplonのデフォルト8000ポートをpotsディレクティブに指定します。

lein: &defaults
image: clojure
volumes:
- .:/usr/src/app
- ./m2:/home/docker/.m2
boot1:
<<: *defaults
entrypoint: ["boot1"]
ports:
- "8000:8000"

アプリの作成

HoplonアプリのビルドツールはBootですがテンプレートはLeiningenを使います。アプリ名はspike-hoplonとしました。

$ lein new hoplon spike-hoplon

Docker Composeを使う場合は以下を実行します。

$ docker-compose run --rm lein new hoplon spike-hoplon

Getting Startedの説明とは構成が異なりますが、以下のディレクトリ構造ができました。

$ cd ~/clojure_apps/spike-hoplon/
$ tree
.
├── README.md
├── build.boot
└── src
├── index.cljs.hl
└── main.inc.css

作成したプロジェクトはdocker-compose.ymlのworking_dirに指定します。

lein: &defaults
image: clojure
volumes:
- .:/usr/src/app
- ./m2:/home/docker/.m2
working_dir: /usr/src/app/spike-hoplon
boot1:
<<: *defaults
entrypoint: ["boot1"]
ports:
- "8000:8000"

アプリの起動

build.bootファイルではhoplonのバージョンが6.0.0-alpha2になっています。このまま起動するとjava.io.FileNotFoundExceptionが発生します。The getting started example doesn’t seem to work. #64にあるissueのようにバージョンを5.10.25に下げます。

~/clojure_apps/spike-hoplon/build.boot
...
:dependencies '[[tailrecursion/boot.task "2.2.4"]
[tailrecursion/hoplon "5.10.25"]]

5.10.25project.cljは以下のようになっています。

(defproject tailrecursion/hoplon "5.10.25"
:description "Hoplon web development environment."
:url "http://github.com/tailrecursion/hoplon"
:license {:name "Eclipse Public License"
:url "http://www.eclipse.org/legal/epl-v10.html"}
:plugins [[lein-marginalia "0.7.1"]]
:dependencies [[io.hoplon.vendor/jquery "1.8.2-0"]
[org.clojure/tools.reader "0.8.5"]
[tailrecursion/javelin "3.6.3"]
[tailrecursion/castra "2.2.2"]
[clj-tagsoup "0.3.0"]
[org.clojure/core.incubator "0.1.2"]
[org.clojure/clojurescript "0.0-2234"]])

leinのhoplon-templatehoplon.cljを読むとbuild.bootファイルの生成時にtailrecursion/hoplonのバージョンを設定しています。バージョンはancient-cljを使い、Mavenリポジトリから最新のバージョンを取得しているようです。

hoplon.clj
(def deps
'[tailrecursion/boot.core
tailrecursion/boot.task
tailrecursion/hoplon])

(defn latest-deps-strs [deps]
(mapv #(latest-version-string! % {:snapshots? false}) deps))

Hoplonは6.0.0-alpha1からBoot 2になり新しい書式のbuild.bootにあわせディレクトリ構造も変わっています。hoplon-templateが生成するbuild.bootはBoot 1の書式なのでビルドに失敗しています。leinのhoplon-templateを使わない方が良さそうですが、初めてなのでこのままBootのdevelopmentタスクを実行してJettyを起動してみます。

$ boot1 development

Docker Composeのrunコマンド使う場合は--service-portsフラグを付けて起動します。

$ docker-compose run --rm --service-ports boot1 development
Compiling Hoplon dependencies...
Jetty server stored in atom here: #'tailrecursion.boot.task.ring/server...
Compiling Hoplon pages...
• src/index.cljs.hl
Compiling ClojureScript...
2015-06-15 01:44:32.185:INFO:oejs.Server:jetty-7.6.8.v20121106
2015-06-15 01:44:32.258:INFO:oejs.AbstractConnector:Started SelectChannelConnector@0.0.0.0:8000
↳ Elapsed time: 27.392 sec › 00:01:19

ブラウザーから起動を確認します。

hoplon-hello.png