---
title: 複雑な画面構成でのページ離脱ガード​_替え玉.web
tags: 
author: [ezakichi](https://image.docswell.com/user/ezakichi_3207)
site: [Docswell](https://www.docswell.com/)
thumbnail: https://bcdn.docswell.com/page/57GLWG94EL.jpg?width=480
description: 複雑な画面構成でのページ離脱ガード​_替え玉.web by ezakichi
published: September 11, 26
canonical: https://image.docswell.com/s/ezakichi_3207/KWRN1J-2026-09-11-173153
---
# Page. 1

![Page Image](https://bcdn.docswell.com/page/57GLWG94EL.jpg)

複雑な画面構成でのページ離脱ガード
2026.09.11 替え玉.web
1


# Page. 2

![Page Image](https://bcdn.docswell.com/page/4EQY3XWRJP.jpg)

自己紹介
江﨑 政堅（えざき しょうけん）
あだ名: えざきち
• サイボウズ株式会社
• kintone開発
• 趣味: カメラ、猫と遊ぶ
• 福岡で美味しかったラーメン→
らぁめん いちむじん
2


# Page. 3

![Page Image](https://bcdn.docswell.com/page/KJ4W16KQ71.jpg)

目次
01
過去の発表
02
Navigation APIとは？
03
プロダクトの仕様
04
実装
05
Navigation APIがあったら？
3


# Page. 4

![Page Image](https://bcdn.docswell.com/page/LE1YGVXL7G.jpg)

過去の発表
4


# Page. 5

![Page Image](https://bcdn.docswell.com/page/GEWGKLNQJ2.jpg)

Navigation APIとは？
ブラウザのナビゲーションアクションやアプリケーションの履歴を管理する機能を
提供するAPIで、History APIの後継として設計されました。
5


# Page. 6

![Page Image](https://bcdn.docswell.com/page/47ZLZM33J3.jpg)

Navigation APIの細かい機能の話はしません
SPAにおける入力中のページ離脱ガードについて話します
6


# Page. 7

![Page Image](https://bcdn.docswell.com/page/YJ6WZNXZJV.jpg)

プロダクトの仕様
7


# Page. 8

![Page Image](https://bcdn.docswell.com/page/GJ5MW5X9J4.jpg)

画面構成
kintone（MPA）
├── 画面A
├── 画面B
├── 画面C
└── SPA
├── 画面D
├── 画面E
└── 画面F
8


# Page. 9

![Page Image](https://bcdn.docswell.com/page/9E29QNX57R.jpg)

ハッシュルーターを使用（react-router）
URL のハッシュ部分 (#) を使ってクライアント側のルーティングを
管理する仕組み
• #以降が変わるとreact-routerがそれを見て画面を切り替える
• aタグを使ってもSPA遷移ができる
例
https://example.com/app #/home
https://example.com/app #/settings
9


# Page. 10

![Page Image](https://bcdn.docswell.com/page/D7Y4WP86EM.jpg)

ヘッダーと SPA は別の React アプリ
ヘッダー
SPA画面
10


# Page. 11

![Page Image](https://bcdn.docswell.com/page/VENY9591J8.jpg)

どう実装する？
11


# Page. 12

![Page Image](https://bcdn.docswell.com/page/Y79P2Y2YE3.jpg)

遷移の種類で分担する
SPAの外への遷移・
リロード・タブ閉じ
beforeunloadでブラウザに止めてもらう
SPA内の画面遷移
useBlockerでreact-routerに止めてもらう
12


# Page. 13

![Page Image](https://bcdn.docswell.com/page/G78D565K7D.jpg)

SPA内の遷移がうまくいかない
SPAの外への遷移・
リロード・タブ閉じ
beforeunloadでブラウザに止めてもらう
SPA内の画面遷移
useBlockerでreact-routerに止めてもらう
useBlocker が止められるのは
・Link / navigate による遷移
・その遷移で作られた履歴への 戻る / 進む
13


# Page. 14

![Page Image](https://bcdn.docswell.com/page/L7LMY9YPJR.jpg)

Link使ってないの？
14


# Page. 15

![Page Image](https://bcdn.docswell.com/page/4EMYNZN2EW.jpg)

aタグでのSPA遷移を避けられないリンクがある
別のReactアプリのため、SPAのRouterを共有できない
投稿に含まれるリンクは HTML の a タグとして保存され、そのまま描画される
Linkに揃えることができないため、aタグに統一する
15


# Page. 16

![Page Image](https://bcdn.docswell.com/page/PER9D6D5J9.jpg)

popstateイベントで検知し、URLを書き戻す
# が変わったあとにブラウザが window に投げるイベント
クリック / 戻る → URL が変わる → popstate → 画面を切り替える
16


# Page. 17

![Page Image](https://bcdn.docswell.com/page/P7XQ1M1XEX.jpg)

URLを書き戻すことの課題
URL を変える操作は、すべて新しい遷移になる
戻る をキャンセル
[A][B*][C] → 戻る →
[A*][B][C]
→ 書き戻し(push) → [A][B&#039;*]
進む先のCが消えた
リンク をキャンセル
[A][B*]
→ a タグ → [A][B][C*]
* : 現在位置
→ 書き戻し(push) → [A][B][C][B&#039;*]
戻ると、断ったCに着く
17


# Page. 18

![Page Image](https://bcdn.docswell.com/page/37K92G297D.jpg)

URLを書き戻さずに位置を戻す
戻る をキャンセル
[A][B*][C] → 戻る →
[A*][B][C]
→ go(+1) → [A][B*][C]
履歴は無傷
リンク をキャンセル
[A][B*]
→ a タグ → [A][B][C*] → go(-1) → [A][B*][C]
* : 現在位置
進む先にCが残るだけ
18


# Page. 19

![Page Image](https://bcdn.docswell.com/page/LJ3W4N49J5.jpg)

deltaを知るために
popstateは遷移を検知してくれるが「何歩動いたか」は教えてくれない
URLも位置の代わりにならない [A][B][A] ← 同じURLが2回並ぶ
そのため、履歴ひとつひとつに番号を書く
pushStateを差し替えて、履歴を積むたびに番号を付ける
aタグで積まれた履歴には、着地時にreplaceStateで番号をつける
着地した番号 − 直前の番号 ＝ delta
履歴は無傷
番号のない履歴に着いたら、フォールバックとしてURLを書き戻す
進む先にCが残るだけ
19


# Page. 20

![Page Image](https://bcdn.docswell.com/page/8JDKQWQ8EG.jpg)

Navigation APIなら
navigate イベントは URL が変わる前に発火し、遷移そのものを止められる
履歴は無傷
URL書き戻し、deltaの算出、履歴への番号付与が不要になる
進む先にCが残るだけ
20


# Page. 21

![Page Image](https://bcdn.docswell.com/page/VEPKL9LW78.jpg)

Navigation APIを使えるようになるまでの道のり
kintoneのフロントエンドは「Baseline Widely Available」を採用している
履歴は無傷
Navigation APIがNewly availableになったのは今年初めのため、kintoneで
使えるのはまだ先の話...
進む先にCが残るだけ
21


# Page. 22

![Page Image](https://bcdn.docswell.com/page/27VVQMQ97Q.jpg)

22


