Spica*

プログラミングの話。

Lilypond用テキストファイルを修正したらすぐにビルドするやつ書いた

https://gist.github.com/esperia/b11a9ee01725832194f45dee2546745b

使い方は中に書きました。

以前紹介したようなdockerimageを使って、ファイルの変更があったら自動的にビルドするように実装しました。

大げさなものではなく、gulp.watchを使ってファイルの変更検知をした後、コマンドを実行するだけのものです。

Lilypond入門した

きれいな楽譜が書きたいけど、FinaleNotepadが扱いにくすぎてやめたのでこっち使うことにした。 高校のころMML書いてたので、性にあってるかなーとか勝手に思ってる…

始め方1 LilyBin

一番簡単なのは、 LilyBinを使うことです。これはブラウザベースでLilypondを使えるサービスです。なので、開くだけですぐに楽譜がかけます。

ただ、楽譜公開する予定とかなければ、なるべくオフラインでしておきたいところです。

始め方2 Docker image

で、僕はMacをよく使うんですが、普通にやるとdependenciesのインストール数が多すぎて、インストールの時間とか容量とか大変なことになります。Homebrew入れている人は brew info homebrew/tex/lilypond して頂くと気持ちが分かるかなと…

==> Dependencies
Build: pkg-config ✔, libtool ✘, flex ✘
Required: gettext ✔, pango ✘, ghostscript ✘, mftrace ✘, fontforge ✘, fondu ✘, texinfo ✘, libffi ✘, libunistring ✘, bdw-gc ✘, gmp ✘, readline ✔
==> Requirements
Required: tex ✔, x11 ✔

なので、とりあえず始める方はDocker使うのがオススメです。Docker Hubに、Lilypondの環境が一式入ったDocker Imageがありますので、これを使いましょう。

https://hub.docker.com/r/markauskas/lilypond/

まずは、Dockerをインストールして、 docker pull markauskas/lilypond しましょう。

その後、下記を test.ly としてローカルに保存し、

\version "2.16.2"
\relative c' {
  c d e f g a b c
}

下記のプログラムで実行します。

docker run --rm -v $(pwd):/app -w /app markauskas/lilypond lilypond test.ly

するとPDFとmidiができると思います。この手順は先程のDockerHubへのリンク内でも考慮されています。

エディタについて

僕はまだ始めたところなので、エディタに関してはまだ未調査です。

調べてみたい場合は、ググるか、より簡単な編集手段より、各種エディタをチェックしてみて下さい。見た感じ完全なMac向けは少ない感じします。

僕は今のところvimを使っています。プラグインは、vim-lilypond-integrator を使っています。プラグイン管理はdein.vimを使用。

はじめよう

とりあえず下記は順に見ておいて損はないです。

さらに詳しく見る場合は、記譜法リファレンスが良いかもです。

おわり

まだ僕もlilypond入門したところなんですが、それはインストールでかなり時間使ってしまったからなのです。なので始める人が居たら、そのハードルが少しでも下がってくれることを願うばかりです。

Dockerの方法も、バージョンとか上げるときどうすんのよ、とか調査できていないので、本当はもうちょっと調べたいところです…。

VimFxを導入した

Vimperatorがe10sにまだ対応しなくて、Firefox重くてつらくてChromeに移行したけど、

Vimium設定が微妙にかゆいところ届かなくて困ってて、

Yet another like vimなブラウザ操作の何かを探してたところ、VimFxと出会った。

はてなブックマークアドオンもe10sまだ対応していない(よね?)ので、とりあえずその辺のconfigいじれるかやってみたらできたので、ブログ書いておくなど。

VimFxについて

VimFxのすばらしい解説があったのでこちら必読。

tonkuma.hatenablog.com

コンフィグの有効化

ここに基本的な流れが書いてあるけど、少し悩んだのでブログ書いておく。

環境はMac OS X (Yosemite)。

github.com

  1. ~/.config/vimfxディレクトリを作る。
  2. ~/.config/vimfx/config.js, ~/.config/vimfx/frame.js という二つのからファイルを作る。
  3. about:config 画面を開き、 extensions.VimFx.config_file_directory の項目を探す
  4. この項目の値を ~/.config/vimfx とする
  5. 変更したら about:config は閉じておk
  6. 適当なタブでキーバインド gC を実行する(g を押した後続けて C を押す)。
  7. すると、右下に「設定ファイルの再読み込みに成功しました」と出る。
  8. ~/.config/vimfx/config.js に下記のプログラムを入力する。入力できたら再度 gC で再読み込みして、 ccはてブURL開く。
vimfx.addCommand({
  name: 'open_hatena_bookmark_entry',
  description: 'Open Hatena Bookmark Entry',
}, ({vim}) => {
  let location = new vim.window.URL(vim.browser.currentURI.spec)
  vim.window.gBrowser.loadURI(`http://b.hatena.ne.jp/entry/${encodeURIComponent(location.href)}`)
})

let map = (shortcuts, command, custom=false) => {
  vimfx.set(`${custom ? 'custom.' : ''}mode.normal.${command}`, shortcuts)
}

map('cc', 'open_hatena_bookmark_entry', true)

VimFx良い!

思うところ

とりあえず、VimFxのおかげでまたFirefoxユーザに戻れそうで嬉しい。

Vimperatorがダメになったんではないんですよ。僕がタブ開きまくる使い方してるせいだったり、Webの仕組みが複雑化しすぎて、シングルプロセスだと回らなくなったのが原因なんですよ!VimpVimpで、消費メモリ少ないとかシングルプロセスで動くモノだから良いところもあって、批判するつもりなんかさらさらなくて感謝の念しか無い。ただ、時代が変わりすぎて則せなくなっただけなんですよね…?

E4Xが死んだあたりで、もうVimp的にもVimp-plugins的にもつらたんなのにe10s対応ですもんね…。まだ見てないですけど今はWebExtensions推しなんでしたっけ。アドオンは古くなっても自分は古くなりとうないですね。

CentOS7でblender実行するまで

blenderコマンドラインから使えるっぽい感じだったのでインストールしてみた。

僕の場合二回エラーが出た。

./blender: error while loading shared libraries: libGLU.so.1: cannot open shared object file: No such file or directory

sudo yum install mesa-libGLU-devel で解決。

./blender: error while loading shared libraries: libXi.so.6: cannot open shared object file: No such file or directory

sudo yum install libXi-devel で解決。

Minecraft Spigotプラグイン "RSSNewsBook" を公開しました

www.spigotmc.org

これはMinecraftの世界の中でニュースを読むためのSpigotプラグインです。 URLが入っていれば、そのURLをクリックすることで、そのニュースの詳細を見ることが可能です。

第二回神戸マインクラフト勉強会にて、公開したことを発表させて頂きました。

その時のスライドはこちら。

www.slideshare.net

モチベーションに関して

スライドにもちょっと紹介していますが、僕はMinecraftと別の何かを繋ぐことを前々からしたいなと思っていました。その形はぼんやりしていて具体的ではないのですが、まずは自分の生活フローと結び付けたいと考えていました。「例えば、マイクラ内のボタンを押すと、家のエアコンがつく」とか。でもハード苦手なのでそれは敷居が高いなと。それで代わりの何かを考えていたのです。

それで、勉強会があるとのことで、これの期間を目標にしてSpigotプラグインを作ろうと思い立ちました。残り3週間、実装からローンチまでの期間としては良いくらいではないかなと。あとはアイデアだけ。何にしよう。

で、僕は毎朝出勤の際にニュースを読むのですが「ああ、とりあえずはこれかな」という感じで即決しました。なんとなくあんまり使いドコロ無いのではという気もしなくもなかったのですが、とりあえず始めないと始まらないということで、実装開始した感じです。最初なので、あまりアイデアの良し悪しは考えませんでした。

あとは、プロジェクトの作り方でしょうか。Androidアプリ開発の経験が長く、Android Studioに慣れているので、IntelliJ+Gradleベースプロジェクトにこだわりました。あとはTestabilityにもこだわりたくて、テストしにくいプロジェクトは嫌だと思ったのもあります。Gradleを選んだのはこの辺もありました。今のところは僕的には結構満足度高くて、

  • テストコードはsrc/main/test/javaに入れておけばJUnit4で実行可能。Yamlからの取得・Yamlとして保存する方法に関して今回は仕様しました
  • ソースコードを変更した後、jarにまとめる→サーバのpluginsディレクトリにjarを入れる→起動の流れをコマンド一発で行えるようにしました。これのおかげで、試すまでの時間がうんと短くなりました

時間がなくて一部シェルスクリプト使っているのだけが気になっているところ…。これも解決して、Windowsでも開発出来るようにしたいところです。

最低限の自分の要望を組み込むところまではいきたいので、これからも開発続けます!

Bukkit pluginを作るために参考にしたところ

またリンク集みたいに雑多に置いておくなど… Unityもこないだ触ったのでそれも書いておきたい…

環境

先に注意点

リンク

コンフィグファイル

プラグイン使っているとわかると思うんですが、基本的にプラグインって

  1. プラグインをダウンロードする
  2. サーバのpluginsフォルダに入れる
  3. 起動する。すると plugins/<プラグイン名>/config.yml というファイルが出来上がる
  4. サーバを止める
  5. config.yml を修正して再度起動

みたいな感じだと思います。この流れを基本とすると、開発側でやりたいことは具体的にいくつか決まってくると思います。それをちょっと下記に列挙しておきます

デフォルトの config.yml を導入

プラグインを作るには、成果物のjarに plugin.yml を含めないといけませんが、それと同じように config.yml もjarに梱包しておきます。そして下記のコードを実行すると、「 config.yml がなければ作成する」という実装ができます。

        File configYml = new File(plugin.getDataFolder(), "config.yml");
        if (!configYml.exists()) {
            plugin.saveResource(configYml.getName(), false);
        }

大切なのが plugin.getDataFolder()plugin.saveResource(fileName, false) 。前者はサーバの plugins ディレクトリのパスを取得することが可能で、後者はjarファイルに含まれている任意のファイル名のものを、 plugins/<プラグイン名>/<fileName> の位置に保存できます。

mitmproxyを使ってresponse body書換え

ふと思いついてmitmproxyを触ってみてた。今まであんまりちゃんとmitmproxyのhookできたことがなくて、ちゃんと調べてみてたんだけど、ちょっとクセがあるっぽい感じだった。

  • mitmproxyではpythonスクリプトを間に差し込み、リクエストを書き換えたりできる
  • mitmproxy -s my_script.py みたいな感じで起動すると、指定したスクリプトでリクエスト・レスポンスを書き換えることが出来る。
    • mitmdump -s my_script.py でもいける。こちらの場合、標準出力に表示されるので、スクリプトに問題があった時よく分かる
    • mitmproxy -s my_script.py での起動の場合、スクリプトエラーがあると、読まれないっぽい。エラーも出ない
    • スクリプトエラーがあると、左下の表記がちょっと違う
      • エラーあり: f:id:esperia:20160405011037p:plain:h35
      • エラーなし: f:id:esperia:20160405011044p:plain:h37
    • 引数をmy_script.pyに渡す場合は、 mitmdump -s 'my_script.py --foo 42' のように渡す

上記を踏まえて。

下記のようにスクリプトを書いた。このスクリプトは先程の Inline scripts の部分を元に書いた。

from libmproxy.models import decoded

def start(context, argv):
    f = open('test.json')
    context.mydata = f.read()
    f.close()
    print(context.mydata)

def response(context, flow):
    with decoded(flow.response):
        original = "example.com"
        target_path = '/path/to/get'
        print("handle request: %s %s" % (flow.request.host, flow.request.path))
        print("  Host: %s" % (flow.request.headers["Host"]))

        if original in flow.request.headers["Host"]:
            if flow.request.path == target_path:
                print("Match request.")
                flow.response.content = context.mydata

上記を mitmdump -T --host -s my_scripts.py で起動。うまく書き換わった。 もっと細かくプログラム組めば、オレオレセッション値とか設定できそう。

まれにデバッグとか調査とかで使うことがあるので慣れておきたいな。