Slide 1

Slide 1 text

© LayerX Inc. Next.jsとNuxtが混在? iframeでなんとかする! ypresto @ JSConf 2024 Sponsor LT (2024/11/23)

Slide 2

Slide 2 text

⾃⼰紹介 ypresto (プレスト) @yuya_presto

Slide 3

Slide 3 text

© LayerX Inc. 5 バクラクのマルチプロダクトとNext.js NuxtとNext.jsを混在させたい話 将来的にNext.jsへの移⾏を検討中 ⼀部Next.jsにしたい 検証やっていき!

Slide 4

Slide 4 text

© LayerX Inc. 7 1プロダクトでNuxtとNext.jsを混ぜる⽅法 Next.js Nuxt Next.js Nuxt ハードナビゲーション (ページ読み込み) が発⽣ JSのグローバル ステートも失われる /foo /bar /foo /bar 埋め込みできれば 回避できる!

Slide 5

Slide 5 text

© LayerX Inc. 8 じゃあ埋め込めばええやん。しかし‧‧‧ 話⻑くなるから省略! ● 要件:アプリ側を変更しないで対応 (⼯数節約) ● Next.jsアプリに、Nuxtアプリを直接埋め込む (e.g. Module Federation) ○ エントリポイントのbundleにNuxtの起動コードがベタ書きなのでそのままでは無理 ● Next.jsアプリから、NuxtアプリのPage Componentなどをimportする ○ Nuxtの機能に依存するコードがNG、dependenciesの問題 ● マイクロフロントエンド系フレームワークを使う (e.g. SAP/luigi、single-spa) ○ やりたいことに対して学習と運⽤のコストが⾼そう ○ Nuxtの機能に依存するコードがNG (なはず) ● iframeで読み込む ○ routerやHistoryがNext.jsとNuxtの2つになることへの対処が⾯倒そう チョット⾯倒なだけ では???

Slide 6

Slide 6 text

© LayerX Inc. 10 提案⼿法 Next.js 内で、Nuxtのiframeを出し分ける iframe Next.js iframe Nuxt app router router 普通のNext.jsアプリ React使⽤可能 条件を満たすURLなら iframeを全画⾯で描画 条件を満たしていない間は 空ページに遷移して隠す

Slide 7

Slide 7 text

© LayerX Inc. 11 提案⼿法 Next.js と Nuxt で URL の同期を取る iframe Next.js iframe Nuxt app router router Next.jsでURLを変える Nuxt側でリンククリックや 戻る進むしたら、 postMessage()

Slide 8

Slide 8 text

© LayerX Inc. 12 提案⼿法 Next.js の URL を Nuxt に反映する iframe Next.js iframe Nuxt app router router Nuxtで router.replace() Next.js側でURLが 変わったら postMessage() Next.jsのrouterを 正にすることで、 戻る‧進むの対応も容易に ※ iframeの中でのrouter.push() は、リロードした後にハードナビゲーションになりました

Slide 9

Slide 9 text

© LayerX Inc. 13 Nuxt の Custom History を実装する https://nuxt.com/docs/guide/recipes/custom-routing#custom-history-advanced window.historyじゃないのを 使える!

Slide 10

Slide 10 text

© LayerX Inc. 14 Nuxt の Custom History を実装する Next.jsに送って、 Next.jsでrouter.push() ※ history.go() は、Nuxt側ではhistory stackの概念を発生させたくないので未対応

Slide 11

Slide 11 text

© LayerX Inc. 15 Nuxt の Custom History を実装する Next.jsに送って、 Next.jsでrouter.push() ※ history.go() は、Nuxt側ではhistory stackの概念を発生させたくないので未対応 Next.jsからmessage来たら listener経由で popstate or pushしたことにする

Slide 12

Slide 12 text

やったか??

Slide 13

Slide 13 text

問題発⽣

Slide 14

Slide 14 text

© LayerX Inc. 24 戻る‧進むされるとき「保存していない変更があります」を表⽰できるNuxtの機能 Next.jsにはそんなものない Navigation Guard

Slide 15

Slide 15 text

© LayerX Inc. 25 Next.jsのページ遷移を全⼒で⽌める!! https://speakerdeck.com/ypresto/hack-to-prevent-page-navigation-in-next-js 5分じゃ無理なので こちらもぜひ! 戻る→URL書き換え next-navigation-guard popstateイベント (キャンセル不可) Next.js側 History API history.go(差分) Next.jsが知らぬ間に URLを元に戻す Nuxt側 Custom History Next.jsのrouterが拾う前に stopImmediatePropagation() で握りつぶす popstateされたよ postMessage() キャンセルされたよ postMessage() ユーザーに 確認

Slide 16

Slide 16 text

© LayerX Inc. 27 iframe内に描画しても無駄無駄ァァ! '@unhead/vue' を上書きし、 titleを親windowに送信 Nuxt内の タグ対応 ReactでいうContextProviderを ネストさせて上書き titleタグを描画せずに postMessage() で送信

Slide 17

Slide 17 text

URL同期できた、ページ遷移⽌められた、同期できた 検証完了! できた!!

Slide 18

Slide 18 text

※ 今はnuxt generateでstatic buildしたものを配信しています NuxtをSSRしたらハードナビゲーションが 爆速になったのでいらんかも

Slide 19

Slide 19 text

制作‧著作:LayerX 終

Slide 20

Slide 20 text

(npm|yarn|pnpm) install next-navigation-guard https://github.com/LayerXcom/next-navigation-guard このとき作った next-navigation-guard が 実際導⼊されたのでヨシ! ※「保存されてない変更があります」表示は、 Next.jsで作る場合も必要なことを見越して作っていた

Slide 21

Slide 21 text

ライブラリ、フレームワーク、APIの仕様を把握しコードを読めば、 だいたいなんでも解決できる! 懇親会でもぜひお話しましょう‧‧! プログラミング超楽しい!!