Elixir scaffold生成.html.heexの<.link href={～}>追加

こんにちは！
プログラミング未経験文系出身、Elixirの国に迷い込んだ？！見習いアルケミストのaliceと申します。
今回はscaffold生成した後でhtml.heexの「<.link href={～}>」部分を追加する方法をまとめます。

# 目的
mixコマンド(今回は`mix phx.gen.live`を使用)を使用してscaffoldした後、html.heexファイル内の「<.link href={～}>」部分を追加／改修する方法を理解する。

## 実行環境
Windows 11 ＋ WSL2 ＋ Ubuntu 22.04
Elixir v1.17.3
Erlang v27.0
Phoenix 1.7.14


# html.heexファイル内の「<.link href={～}>」部分とは
`<.link href={～}>`は、Elixirで書かれたリンクをテンプレートファイル(=heexファイル)に補間するためのものです。

https://hexdocs.pm/phoenix/components.html#heex

`<.link href={～}>`はページ全体をリロードします。
部分リロードしたい場合は`<.link navigate={～}>`または`<.link patch={～}>`を使用します。

https://hexdocs.pm/phoenix_live_view/live-navigation.html

# 前提
## Phoenixプロジェクト作成
`hello`という名前でPhoenixプロジェクトを作成
```bash:bash
mix phx.new hello
cd hello
mix ecto.create
```
## scaffold実行
```bash:bash
mix phx.gen.live Accounts Users users name:string age:integer
```

```diff_elixir:lib/hello_web/router.ex
 scope "/", HelloWeb do
     pipe_through :browser

     get "/", PageController, :home
     
+    live "/users", UsersLive.Index, :index
+    live "/users/new", UsersLive.Index, :new
+    live "/users/:id/edit", UsersLive.Index, :edit
+
+    live "/users/:id", UsersLive.Show, :show
+    live "/users/:id/show/edit", UsersLive.Show, :edit
   end
```

```bash:bash
mix ecto.migrate
```

## scaffoldされたheexファイルの確認
```diff_elixir:lib/hello_web/live/users_live/index.html.heex
<.header>
  Listing Users
  <:actions>
    <.link patch={~p"/users/new"}>
      <.button>New Users</.button>
    </.link>
  </:actions>
</.header>

<.table
  id="users"
  rows={@streams.users_collection}
  row_click={fn {_id, users} -> JS.navigate(~p"/users/#{users}") end}
>
  <:col :let={{_id, users}} label="Name"><%= users.name %></:col>
  <:col :let={{_id, users}} label="Age"><%= users.age %></:col>
  <:action :let={{_id, users}}>
    <div class="sr-only">
      <.link navigate={~p"/users/#{users}"}>Show</.link>
    </div>
    <.link patch={~p"/users/#{users}/edit"}>Edit</.link>
  </:action>
  <:action :let={{id, users}}>
    <.link
      phx-click={JS.push("delete", value: %{id: users.id}) |> hide("##{id}")}
      data-confirm="Are you sure?"
    >
      Delete
    </.link>
  </:action>
</.table>

<.modal :if={@live_action in [:new, :edit]} id="users-modal" show on_cancel={JS.patch(~p"/users")}>
  <.live_component
    module={HelloWeb.UsersLive.FormComponent}
    id={@users.id || :new}
    title={@page_title}
    action={@live_action}
    users={@users}
    patch={~p"/users"}
  />
</.modal>
```
画面上ではこんな感じです↓
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/677280/940965b4-8a2c-680f-e74e-0dd53821ccb1.png)

# 追加してみる
## `/users`から`/`へ遷移するリンクの追加
先ほどのheexファイルの先頭行に`/`へ遷移するリンクを追加します。


テストを追加します。
※ `~s`はエスケープや埋め込みを含む文字列を生成するシギルです。[^1]
```diff_elixir:test/hello_web/live/users_live_test.exs
 describe "Index" do
     setup [:create_users]
 
+   test "renders the Welcome Page link", %{conn: conn} do
+     {:ok, _view, html} = live(conn, ~p"/users")
+
+     assert html =~ "Welcome Page!"
+     assert html =~ ~s(href="/")
+   end
# 以下略
```

テストが通る実装を追加します。
```diff_elixir:lib/hello_web/live/users_live/index.html.heex
+ <p><.link href={~p"/"}>Welcome Page!</.link></p>
+
 <.header>
   Listing Users
   <:actions>
# 以下略
```

画面上ではこんな感じです↓
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/677280/df96ae62-3da3-cb93-a7d3-761cd4eaa3e7.png)

クリックすると`/`に遷移することが確認できます↓
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/677280/3cbf72b5-b5df-2dfa-e9c7-f71e3480fa4d.png)






# ～Elixirの国のご案内～
↓Elixirって何ぞや？と思ったらこちらもどぞ。Elixirは先端のアレコレをだいたい全部できちゃいます:laughing::sparkles::sparkles:

https://qiita.com/piacerex/items/09876caa1e17169ec5e1

↓ゼロからElixirを始めるなら「エリクサーチ」がおすすめ！私もエンジニア未経験から学習中です。

https://elixir-lang.info/topics/entry_column


↓[We Are The Alchemists, my friends!:bouquet:](https://qiita.com/torifukukaiou/items/6bcd5bbb80df9e594e9e "Awesome-san's Awesome article")[^10]
Elixirコミュニティは本当に優しくて温かい人たちばかり！
私が挫折せずにいられるのもこの恵まれた環境のおかげです。
まずは気軽にコミュニティを訪れてみてください。[^11]


https://speakerdeck.com/elijo/elixirkomiyunitei-falsebu-kifang-guo-nei-onrainbian


[^1]:https://elixirschool.com/ja/lessons/basics/sigils

[^10]: @torifukukaiouさんのAwesomeな名言をお借りしました。Elixirコミュニティを一言で表すと、これに尽きます。


[^11]: @kn339264さんの素敵なスライドをお借りしました。Elixirコミュニティはいろんな形で活動中！