Javascript

パラメータをobjectでまとめて渡す【Vue】

フロントエンドをvueで実装しているアプリがあります。

formでいろんなパラメータを渡したり、DOMリストに対してフィルターをかけたりと
複数のパラメータをサーバー側に渡したいケースがあります。
そういう時、$dataでパラメータをまとめてobjectとして持たせる事が多いのですが、
そのまま渡してしまうと未入力のフィルターも渡してしまい、非効率です。

選択されている項目だけ渡したかったので、objectに対してfilterメソッドを使い
未入力のフィルターを除外してGETリクエストのURLにくっつける、という処理を書きました。

フィルターには、チェックボックスとラジオボタンを使用してますが、他のinput属性でもできます。

結論

チェックボックスやラジオボタンが選択されていた場合、
選択したパラメータをURLに付与します。

*URLは localhost:3000/app/filter で固定にしています。
*ハッシュがついてたりする場合はよしなにパースしてください。今回は#hash_sampleをつけています

コード解説

肝になる部分だけ

() => {
  let pathName = 'localhost:3000/app/filter';
  const hash = '#hash_sample';

  const query = Object.entries(vm.$data.selectedFilter).filter(v => {
    return (Array.isArray(v) && v.length > 0) || (!Array.isArray(v) && v === null)
  }).map(v => {
		// キャメルケースの場合はスネークケースに変換する
    v[0] = v[0].split(/(?=[A-Z])/).join('_').toLowerCase();
    return v.join('=');
  }).join('&');
  if (query !== '') pathName += `?${query}`;
  pathName += `${hash}`;

  vm.$data.result = pathName;
}

オブジェクトをfilterしてからmapで配列にして、&で繋いでいます。
filterで、選択されていないinput属性を渡さないようにします。

今回は、チェックボックスとラジオボタンなので以下の条件でfilterしました。

  • チェックボックス
    • 配列 && 長さが0以上
  • ラジオボタン
    • 配列以外 && null以外

使用してるinputによってfilterの条件はよしなに変更します。
ラジオボタンも、0がdefault値として絞り込みなしの条件になっていたら
v === null || v === 0 みたいにしてもOKです。

script部分

let vm = new Vue({
  el: "#app",
  data: {
    checkbox: {
      name: 'checkbox',
      items: [
        {label: 'check_1', value: 1},
        {label: 'check_2', value: 2}
      ],
    },
    radio: {
      name: 'radio',
      items: [
        {label: 'default', value: 0},
        {label: 'radio_1', value: 1},
        {label: 'radio_2', value: 2}
      ],
    },
    selectedFilter: {
	    checkbox: [],
      radio: 0
    },
    result: 'localhost:3000/app#hash_sample',
  },
  methods: {
  	filter: () => {
      let pathName = 'localhost:3000/app/filter';
      const hash = '#hash_sample';

      const query = Object.entries(vm.$data.selectedFilter).filter(v => {
        return (Array.isArray(v) && v.length > 0) || (!Array.isArray(v) && v === null)
      }).map(v => {
        v[0] = v[0].split(/(?=[A-Z])/).join('_').toLowerCase();
        return v.join('=');
      }).join('&');
      if (query !== '') pathName += `?${query}`;
      pathName += `${hash}`;

      vm.$data.result = pathName;
    }
  }
})

HTML部分

<div id="app">
  <h3>絞り込みのフィルター的なもの</h3>
  <p>選択されたitem: {{ selectedFilter }}</p>

  <div class="container">
    <div class="filter">
      <template v-for="item in checkbox.items">
        <label :for="item.label">
          <input
                 v-model="selectedFilter.checkbox"
                 :name="checkbox.name"
                 type="checkbox"
                 :value="item.value"
                 :id="item.label"
                 />
          {{ item.label }}
        </label>
      </template>
    </div>

    <div class="filter">
      <template v-for="item in radio.items">
        <label :for="item.label">
          <input
                 v-model="selectedFilter.radio"
                 :name="radio.name"
                 type="radio"
                 :value="item.value"
                 :id="item.label"
                 />
          {{ item.label }}
        </label>
      </template>
    </div>

    <button @click="filter()">絞り込み</button>
  </div>

  <div>
    <span class="label">result</span>
    <span class="result">{{ result }}</span>
  </div>
</div>

まとめ

objectにまとめたフィルターを、選択されている分だけGETで渡す方法を紹介しました。
もっと効率的なやり方もあるかもしれません。

そもそも、未入力のフィルターを渡しても、サーバー側で除外すれば済む話でもあるので
設計によっては使えない方法かもしれません。

Vue内でフィルター項目を定義できるケースもあれば、サーバーからフィルター項目を取得するケースもあると思います。
どんなケースであっても、とりあえずobjectにまとめて渡せるようにしておきたいなと思ったので、
今回の方法を紹介しました。誰かの役に立てば嬉しいです。

ピックアップ記事

  1. 【Rails】modelを作成する
  2. 【UE4】用語備忘録メモ
  3. 起動時の設定をカスタムする【Blender】
  4. 【Blender】MMDファイルをBlenderにImportするアドオン
  5. 【CSS】おしゃれなラジオボタンを作る

関連記事

 
  1. Javascript

    reverse()は破壊的メソッド【JS】

    配列の逆順ソートには reverse() が使えるが、破壊的…

  2. Javascript

    Object.assignではなく、スプレッド構文を使う【JS】

    Object.assignでパラメータの複製とか追加を実装していたの…

カレンダー

2024年3月
 123
45678910
11121314151617
18192021222324
25262728293031

最近の記事

  1. Blender

    【Blender】レンダリング結果を新規ウィンドウで開かないようにする
  2. Ruby on Rails

    【Rails】findメソッドで連想配列から指定した値を検索する
  3. Blender

    【Blender】zip版のBlenderをBlender Launcherに移…
  4. Ruby on Rails

    【Rails】selectメソッドで特定の条件を満たす要素を取得する
  5. Blender

    起動時の設定をカスタムする【Blender】
PAGE TOP