ElixirでPlugの動作を確認してみた

# 概要
ElixirでPlugの動作を確認してみました。以下のページを参考にしました。

https://dev.to/gumi/elixir-plug-40lb

# mixでプロジェクトを作る
以下のコマンドを実行しました。
```
$ mix new my_plug
* creating README.md
* creating .formatter.exs
* creating .gitignore
* creating mix.exs
* creating lib
* creating lib/my_plug.ex
* creating test
* creating test/test_helper.exs
* creating test/my_plug_test.exs

Your Mix project was created successfully.
You can use "mix" to compile it, test it, and more:

    cd my_plug
    mix test

Run "mix help" for more commands.
```

# Plugのインストール
以下のファイルを作成しました。
```mix.exs
defmodule MyPlug.MixProject do
  use Mix.Project

  def project do
    [
      app: :my_plug,
      version: "0.1.0",
      elixir: "~> 1.12",
      start_permanent: Mix.env() == :prod,
      deps: deps()
    ]
  end

  # Run "mix help compile.app" to learn about applications.
  def application do
    [
      extra_applications: [:logger],
      applications: [:plug_cowboy]
    ]
  end

  # Run "mix help deps" to learn about dependencies.
  defp deps do
    [
      # {:dep_from_hexpm, "~> 0.3.0"},
      # {:dep_from_git, git: "https://github.com/elixir-lang/my_dep.git", tag: "0.1.0"}
      {:plug_cowboy, "~> 2.0"}
    ]
  end
end
```
以下のコマンドを実行しました。
```
$ mix deps.get
Resolving Hex dependencies...
Resolution completed in 0.132s
New:
  cowboy 2.10.0
  cowboy_telemetry 0.4.0
  cowlib 2.12.1
  mime 2.0.5
  plug 1.14.2
  plug_cowboy 2.6.1
  plug_crypto 1.2.5
  ranch 1.8.0
  telemetry 1.2.1
* Getting plug_cowboy (Hex package)
* Getting cowboy (Hex package)
* Getting cowboy_telemetry (Hex package)
* Getting plug (Hex package)
* Getting mime (Hex package)
* Getting plug_crypto (Hex package)
* Getting telemetry (Hex package)
* Getting cowlib (Hex package)
* Getting ranch (Hex package)
You have added/upgraded packages you could sponsor, run `mix hex.sponsor` to learn more
```

# サンプルコードを動かす
以下のコマンドを実行しました。
```
$ iex -S mix
Erlang/OTP 24 [erts-12.2.1] [source] [64-bit] [smp:4:4] [ds:4:4:10] [async-threads:1] [jit]

Could not find "rebar3", which is needed to build dependency :ranch
I can install a local copy which is just used by Mix
Shall I install rebar3? (if running non-interactively, use "mix local.rebar --force") [Yn] Y
* creating /home/xxxxxxxx/.mix/rebar
* creating /home/xxxxxxxx/.mix/rebar3
===> Analyzing applications...
===> Compiling ranch
===> Analyzing applications...
===> Compiling telemetry
===> Analyzing applications...
===> Compiling cowlib
===> Analyzing applications...
===> Compiling cowboy
===> Analyzing applications...
===> Compiling cowboy_telemetry
==> mime
Compiling 1 file (.ex)
Generated mime app
==> plug_crypto
Compiling 5 files (.ex)
Generated plug_crypto app
==> plug
Compiling 1 file (.erl)
Compiling 40 files (.ex)
Generated plug app
==> plug_cowboy
Compiling 5 files (.ex)
Generated plug_cowboy app
==> my_plug
Compiling 1 file (.ex)
Generated my_plug app
Interactive Elixir (1.12.2) - press Ctrl+C to exit (type h() ENTER for help)
iex(1)> {:ok, _} = Plug.Cowboy.http MyPlug, []
** (UndefinedFunctionError) function MyPlug.init/1 is undefined or private
    (my_plug 0.1.0) MyPlug.init([])
    (plug_cowboy 2.6.1) lib/plug/cowboy.ex:412: Plug.Cowboy.dispatch_for/2
    (plug_cowboy 2.6.1) lib/plug/cowboy.ex:360: Plug.Cowboy.to_args/5
    (plug_cowboy 2.6.1) lib/plug/cowboy.ex:331: Plug.Cowboy.run/4
iex(1)> defmodule MyPlug do
...(1)> import Plug.Conn
...(1)> def init(options) do
...(1)> options
...(1)> end
...(1)> def call(conn, _opts) do
...(1)> conn
...(1)> |> put_resp_content_type("text/plain")
...(1)> |> send_resp(200, "Hello world")
...(1)> end
...(1)> end
warning: redefining module MyPlug (current version loaded from _build/dev/lib/my_plug/ebin/Elixir.MyPlug.beam)
  iex:1

{:module, MyPlug,
 <<70, 79, 82, 49, 0, 0, 6, 72, 66, 69, 65, 77, 65, 116, 85, 56, 0, 0, 0, 191,
   0, 0, 0, 18, 13, 69, 108, 105, 120, 105, 114, 46, 77, 121, 80, 108, 117, 103,
   8, 95, 95, 105, 110, 102, 111, 95, 95, ...>>, {:call, 2}}
iex(2)> {:ok, _} = Plug.Cowboy.http MyPlug, []
{:ok, #PID<0.881.0>}
```

# ブラウザで動作を確認する
ブラウザでlocalhost:4000を開くと以下の通りに表示されます。
![Screenshot from 2023-07-14 14-05-31.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3192024/8685713b-1475-20d0-f4e5-f9a10c9dd610.png)


# まとめ
何かの役に立てばと。