🤦‍♂️

VueRouterでパスの一部として定義されていないParamsを渡すと、値が消失する

2023/03/05に公開

VueRouter でパスの一部として定義されていない Params を渡すと、値が消失する

事象

Vue Router でパスの一部として定義されていない params を渡そうとしたとき、
以下の警告が発生して、受け渡した Params の値がundefinedになっていました。

エラーが発生したコード

受渡元

router.push({ name: "somewhere", params: { hoge: "i am params" } });

router.ts

{
  path: "/somewhere/",
  name: "somewhere",
  component: somewhere,
  props: (route: RouteLocationNormalized) => ({ id: route.params.hoge }),
},

受渡先

import { useRoute } from "vue-router";
const route = useRoute();
const q = route.params.id;

エラー内容

[Vue Router warn]: Discarded invalid param(s) "q" when navigating. See https://github.com/vuejs/router/blob/main/packages/router/CHANGELOG.md#414-2022-08-22 for more details.

エラー要約

結論

Vue Router v4.1.4 から[パスの一部として定義されていないパラメータを渡す]ことは廃止になりました。
代替手段としては以下を使ってくださいとのこと。

  1. ストアにデータを保持する
  2. ルートのパスにデータを定義するか、クエリパラメータとして渡す
  3. History API state にデータを保存する
  4. ナビゲーションガードのなかで to.meta プロパティにデータを渡す

背景

参考文献内容

This change will break your app. This behavior has worked in some scenarios but has been advised against for years as it's an anti-pattern in routing for many reasons, one of them being reloading the page lose the params.

要約

この変更によってアプリが壊れる可能性があります。この振る舞いは一部のシナリオで機能していましたが、ルーティングにおいて反パターンとされており、ページの再読み込みによりパラメータが失われるため、多くの理由から長年にわたって推奨されていませんでした。

代替手段

ストアにデータを保持させる

Pinia などの状態管理ライブラリを使いましょう。

ルートのパスにデータを定義するか、クエリパラメータとして渡す

router.ts を以下のように変える

router.ts

{
  path: "/somewhere/:id",
  name: "somewhere",
  component: somewhere,
  props: (route: RouteLocationNormalized) => ({ id: route.params.hoge }),
},

History API state にデータを保存する

文献によると、以下のように書けば渡せる(動作未確認)

state to save it to the History API state

<router-link :to="{ name: 'somewhere', state: { myData } }">...</router-link>
<button
  @click="$router.push({ name: 'somewhere', state: { myData } })"
>...</button>

ナビゲーションガードのなかで to.meta プロパティにデータを渡す

参考文献の以下コードのようにする

router.beforeEach(async (to) => {
  if (to.meta.shouldFetch) {
    // name `data` whatever you want
    to.meta.data = await fetchSomething();
  }
});

参考文献

https://qiita.com/Engineer_Grotle/items/66d181309a779ce8a34a

https://github.com/vuejs/router/blob/main/packages/router/CHANGELOG.md#414-2022-08-22

GitHubで編集を提案

Discussion