c4se記:さっちゃんですよ☆

.。oO(さっちゃんですよヾ(〃l _ l)ノ゙☆)

.。oO(此のblogは、主に音樂考察Programmingに分類されますよ。ヾ(〃l _ l)ノ゙♬♪♡

音樂はSoundCloud等バラバラの場所に公開中です。申し訳ないがlinkをたどるなどして探してください。

考察は現在は主に此のblogで公表中です。

programmingは、ひろくみせるものはGitHubで、個人的なものはBitBucketで開発中です。

c4se

Monitoring Elixir Plug/Phoenix Web application easy. KomachiHeartbeat v0.1.0 ヾ(〃l _ l)ノ゙

RailsにはKomachiHeartbeatと云ふ何かと有り難いmountable engineが在り、Elixir/Phoenixにも欲しかったので移植した。

KomachiHeartbeat

github.com

Plug若しくはPhoenixのapplicationの、適当なpathにぶら下げて使ふ。例では/opsにぶら下げてある。Phoenixだとrouterで、

defmodule ExampleWeb.Router do
  use ExampleWeb, :router

  forward("/ops", KomachiHeartbeat)
end

とすると、

  • GET /ops/heartbeat
  • GET /ops/stats

と云ふ二つのendpointが出來る。heartbeatは200 okか503 errorを返す。applicationが新しいHTTP接續を受けられるなら200 okが返ってくる。受けられないならtimeoutするだらう。接續は受けられるが何か問題 (何を確認するかはpluginで擴張する) が在るなら503 errorを返すやうに出來る。

statsはapplicationの統計情報を返せる。defaultでは空っぽで、pluginで返す情報を増やす。

元のRailsのものとの違ひは、収集する情報は全てをpluginで作るやうにしてあり、入れ替へられるようにした。ElixirにはRailsと違ひ、「標準のstack」の樣なものはEcto位いしか無く、applicationによって確認すべき事が全く異なるだらうからだ。とは言へ標準のpluginは幾つか作りたいと思ってゐる。

Git repositoryの名前はEx-KomachiHeartbeatであるが、これは当然元としたものと區別出來なければならない事と、Max新幹線の樣な語呂にする爲にsuffixではなくprefixにした。

はい?

こまち (列車) - Wikipedia

Max (鉄道車両) - Wikipedia

(〃l _ l)

Testable readonly ETS. Mnemonics.ExMachina v0.1.0 ヾ(〃l _ l)ノ゙

  • 讀み取り専用
  • on-memoryで高速
  • 再起動せずに新しいver.のdataへ入れ替へられる
  • 古いver.で處理してゐた計算はそのまま古いver.を讀み出し續けられる
  • heap領域にcacheできる。讀み出したdataをsnapshotとしてsystem外に持ち運べる
  • parallel

これらを滿たしたMnemonicsと云ふElixirのlibraryを以前に作った。無停止upgrade出來るActiveHashの樣なものだ。

Mnemonicsを使ったcodeをtestしやうとする。testで使ふdataは、實働環境から独立である必要が在る、即ちtestで使ふdataははtest内に書かれてあるのが好い。又testで使ふdataは、他のtestからも独立である必要が在る、即ち或るtestが書き換へたdataが他のtestに影響しないのが好い。PostgreSQL等のDBを使ったcodeをtestするには2つの方法が在る。ひとつにはDBと遣り取りする函數をmockして了ふ。もうひとつはtest毎に一意なdataをDBに書き込む。test毎に一意であればそのdataは他のどこからも讀み出せない。RDBであれば通常は、一意なprimary keyをtestの外で生成して 與へ、與へられたkeyのdata以外には手を触れないと取り決めてやる。所謂test factoryだ。Rails/ActiveRecordだとFactoryBotが有名だ。Elixir/EctoだとExMachinaが有名である。例へばこう使ふ。

defmodule Factory do
  use ExMachina.Ecto

  def user_factory do
    id = sequence("")
    %User{id: String.to_integer(id), name: "user" <> id}
  end
end

defmodule UserTest do
  import Factory

  use ExUnit.Case

  test "authorized?" do
    user = insert(:user)
    assert User.authorized?(user)
  end
end

some_factoryと云ふ函數を定義してやりuse ExMachina.Ectoとしてやると、build(:some)insert(:some)と云ふ函數が使へる樣に成る。

さてMnemonicsではこれが出來ない。test毎に一意なdataを生成してやるのだが、readonlyなので環境に書き込めない。

出來なかった。mockする手も在っただらうとは思ふものの、ETSをまるごとmockするのはダルいので、Mnemonics側に書き込み出來る穴を空けてやった。この穴はtable毎に1つのGenServerでありparallelではないので本番では使ってはならないが、testで使ふには充分速い。

Mnemonics.ExMachina

github.com

こう使ふ。

defmodule Factory do
  use Mnemonics.ExMachina

  def item_factory do
    id = sequence("")
    %Item{id: String.to_integer(id), name: "user" <> id}
  end
end

defmodule UserTest do
  import Factory

  use ExUnit.Case

  test "drop?" do
    user = insert(:item)
    assert Item.drop?(item)
  end
end

use ExMachina.Ectouse Mnemonics.ExMachinaに變はっただけ。一つのfactoryに兩方をuseする事は出來ないので、併用する時は2つfactoryを作ってやり、尚且つimportせずfull qualifiedにmodule名附きで呼んでやれば好い。

ヾ(〃l _ l)ノ゙