stimulus について知らないので簡単に調査したというメモ

# はじめに
### 目的
* Rails で stimulus を触れる機会があったため、そもそも何なのか基礎から調べることを目的とした

### 対象者
* 私と同じく Stimulus について全く知らない方

---

# 概要
> Stimulus is a JavaScript framework with modest ambitions. It doesn’t seek to take over your entire front-end—in fact, it’s not concerned with rendering HTML at all.
> 
> 「Stimulus は、控えめな目標を持つ JavaScript フレームワークです。フロントエンド全体を制御しようとするものではなく、HTML のレンダリングにはまったく関係ありません。」 (原文翻訳)
> 
> 引用：https://stimulus.hotwired.dev/
* 最近はやりの React も JS のライブラリということで stimulus の比較対象としてサンプルコードを見比べた<br>→ 「[React のサンプルコード](https://ja.react.dev/)」 v.s. 「[stimulus のサンプルコード](https://stimulus.hotwired.dev/)」
    * サンプルコードを見てみる限り **『HTML が主体になっているか JS が主体になっているか』** の違いと思われる

:::note info
【メモ】
* React は JS でありながら HTML をレンダリングしている
    * JavaScript のチュートリアルで学ぶような「すでにある HTML の要素を JS で DOM 操作する」とは違い"JS 側"が舵を取っているイメージ
* stimulus は HTML の要素に `data-XXX` のような属性を加えることで DOM 操作対象を指定している
    * あくまで HTML があってこその JS というイメージで HTML が主体
        * そのため"modest ambitions"と表現しているのかもしれない
:::

# コードで確かめる
* 公式ドキュメントよりサンプルコードを拝借して以下のようなソースコードを実装した

:::note info
* `data-hello-target="name"` ... stimulus で参照する要素（"ターゲット属性"という）
    * `data-XXX-target` ... 参照するのが"XXX"コントローラであることを意味する
    * `"name"` ... "XXX"コントローラ内で扱うこの要素の識別名
* `data-action="click->hello#greet"` ... stimulus で監視する DOM イベント
    * `click` ... 監視する DOM イベント
        * サンプルコードにおいては `<button>` なので `click` を監視している
    * `hello` ... このイベントを扱う stimulus のコントローラ名
    * `greet` ... イベントを扱うコントローラ内のメソッド名

https://stimulus.hotwired.dev/reference/targets
https://stimulus.hotwired.dev/reference/actions
:::
　
(サンプルコード：公式ドキュメントで紹介されているサンプルコードを HTML ファイル単体で実装する場合)
```html:stimulus_sample.html
<!doctype html>
<html>
<head>
    <meta charset="utf-8">
    <script type="module">
        import { Application, Controller } from "https://unpkg.com/@hotwired/stimulus/dist/stimulus.js"
        window.Stimulus = Application.start()
        
        Stimulus.register("hello", class extends Controller {
        static targets = [ "name", "output" ]
        
            greet() {
                this.outputTarget.textContent =
                `Hello, ${this.nameTarget.value}!`
            }
        });
    </script>
</head>
<body>
    <!--HTML from anywhere-->
    <div data-controller="hello">
        <input data-hello-target="name" type="text">
        
        <button data-action="click->hello#greet">
        Greet
        </button>
        
        <span data-hello-target="output">
        </span>
    </div>
</body>
</html>
```
* 参考1：https://stimulus.hotwired.dev/
* 参考2：https://stimulus.hotwired.dev/handbook/installing#using-without-a-build-system

:::note info
【メモ】
* バニラ JS で id を HTML 要素に付与するように stimulus も `data-XXX` を付与している
    * 違う点は前者のように単に「識別するための id」を付与するのではなく `data-action`、`data-hello-target` というように **「要素の識別 & その要素はどういった役割なのか」** という意味を持たせられる<br>⇒ 『Stimulus のコントローラーを見なくとも、HTML から Stimulus のその要素の役割・振る舞いに察しが付く』
:::

# サンプルコードについての注意点など
## `static targets` はそのままに
* `outputTarget` `nameTarget` という風に参照しているため、冒頭の `static targets` もオリジナルの命名が出来るかと思いきやできない
    * `targets` から変更すると参照できなくなります

```javascript:BAD
// BAD
static nametargets = [ "name", "output" ]

// OK
static targets = [ "name", "output" ]
```

### 参照する際は `XXXTarget` とする
* サンプルコードにある通り、`targets` の `name` を参照するには `nameTarget` とする

---
### 参考資料
https://stimulus.hotwired.dev/

https://github.com/hotwired/stimulus-rails

https://qiita.com/nazomikan/items/4dabc63b883aa71ce83c

https://ja.react.dev/

https://www.infoq.com/jp/news/2021/03/stimulus-2-javascript-framework/

https://qiita.com/nazomikan/items/62cf9ff1b4edfd28c225

https://www.ey-office.com/blog_archive/2023/08/22/i-tried-getting-started-with-stimulus-a-js-framework-for-rails-programmers/