mrubyの初手
環境構築からmrubyを実行するCのコードをビルドするまで。
環境構築
$ mkdir hello-mruby
$ cd hello-mruby
$ vi Dockerfile+FROM ruby:1.9
+RUN apt update && \
+ apt install -y bison --no-install-recommends && \
+ git clone https://github.com/mruby/mruby && \
+ cd mruby && \
+ ./minirake
+ENV PATH /mruby/bin:$PATH
+CMD ["bash"]- ドキュメントを読むと、mrubyのビルドにはRuby 1.8か1.9、gcc、ar、bisonが必要とのことだった。
ruby:1.9のイメージをベースにして、入ってなかったbisonだけインストールした。 ./minirakeでmrubyがビルドされる。bin/以下にmrbcなどがあるのでPATHに追加しておく。
$ docker build . -t naoty/hello-mruby
$ docker run -it --rm naoty/hello-mruby
% mirb
mirb - Embeddable Interactive Ruby Shell
> MRUBY_VERSION
=> "2.0.1"
> exit
% exit- Dockerでmrubyをビルドできたことを確認した。
サンプルコードを追加する
$ vi Dockerfile FROM ruby:1.9
RUN apt update && \
apt install -y bison --no-install-recommends && \
git clone https://github.com/mruby/mruby && \
cd mruby && \
./minirake
ENV PATH /mruby/bin:$PATH
+WORKDIR /hello-mruby
+COPY . /hello-mruby/
CMD ["bash"]- サンプルコードを用意していくので
WORKDIRを用意する。
$ vi hello.rb+puts "Hello, mruby!"$ docker build . -t naoty/hello-mruby- サンプルコードを追加してDockerイメージに追加する。
$ docker run -it --rm -v $(pwd):/hello-mruby naoty/hello-mruby
% mrbc hello.rb
% exit- カレントディレクトリをマウントしてイメージを起動する。
- mrbcで
hello.rbからhello.mrbを生成する。マウントしているので、ホストにもhello.mrbが追加されている。
Cからmrubyを実行する
$ vi hello.c+#include <mruby.h>
+#include <mruby/dump.h>
+#include <stdio.h>
+
+int main() {
+ mrb_state *mrb = mrb_open();
+
+ FILE *fd = fopen("hello.mrb", "r");
+ mrb_load_irep_file(mrb, fd);
+
+ mrb_close(mrb);
+
+ return 0;
+}- 生成した
hello.mrbを実行するCのコードを書く。 - Cのコードは雰囲気で書いてるけど、
mrb_openとmrb_closeはお約束みたいで、mrb_load_irep_fileによってmrbファイルをloadするっぽい。
$ docker run -it --rm -v $(pwd):/hello-mruby naoty/hello-mruby
% gcc hello.c -I/mruby/include -L/mruby/build/host/lib -lmruby -lm -o hello
% ./hello
Hello, mruby!- 書いたCのコードをビルドするため、もう一度Dockerイメージを起動する。
hello.cをgccでビルドするには、まずヘッダーファイルmruby.hのパスを指定する必要がある。mrubyのヘッダーファイルは/mruby/include/以下にあるので、-Iオプションで指定している。- 次に、mruby本体のソースコードとともに
hello.cをビルドする必要がある。mrubyのライブラリは/mruby/build/host/lib/libmruby.aなので、-Lオプションにパスを指定し、-lオプションでmrubyを指定している。 - また、ビルドすると
/mruby/src/numeric.c:321: undefined reference to 'round'のようなエラーが出てしまう。Mathのライブラリが足りなさそうなので、-lmオプションをつけてlibm.soをリンクしている。 - 無事にビルドできた実行可能ファイルを実行してみると、
hello.rbで書いたコードが実行された。
追記
Rubyは最新で問題ないです!問題があれば直すべきなので1.9はやめましょう… / 1件のコメント https://t.co/uu6C7Y3g0k “mrubyの初手” (1 user) https://t.co/2bFP5uPQAu
— Uchio KONDO 🔫 (@udzura) August 7, 2019
ドキュメント(docs/guides/compile.md) を「2.0 or later」にアップデートします
— Yukihiro Matsumoto (@yukihiro_matz) August 7, 2019
とのことなので、ベースイメージをruby:2.6にしてみたけど問題なく上記の手順ができた。