[3] [DFN[[RUBYB[セッション[RUBY[履][り]][RUBY[歴][れき]]]@en[session history]]]]は、
ある[[閲覧文脈]]中の[[文書]]の列です [SRC[>>2]]。

* 仕様書

[REFS[
- [1] [CITE@en-GB-x-hixie[HTML Standard]] ([TIME[2015-04-25 04:40:19 +09:00]] 版) <https://html.spec.whatwg.org/#browsing-context>
- [2] '''[CITE@en-GB-x-hixie[HTML Standard]] ([TIME[2015-04-25 04:40:19 +09:00]] 版) <https://html.spec.whatwg.org/#session-history>'''
- [28] [CITE@en-GB-x-hixie[HTML Standard]] ([TIME[2015-04-25 04:40:19 +09:00]] 版) <https://html.spec.whatwg.org/#dom-history-pushstate>
- [20] [CITE@en-GB-x-hixie[HTML Standard]] ([TIME[2015-04-25 04:40:19 +09:00]] 版) <https://html.spec.whatwg.org/#update-the-session-history-with-the-new-page>
- [19] [CITE@en-GB-x-hixie[HTML Standard]] ([TIME[2015-04-25 04:40:19 +09:00]] 版) <https://html.spec.whatwg.org/#scroll-to-fragid>
- [10] [CITE@en[RFC 7234 - Hypertext Transfer Protocol (HTTP/1.1): Caching]] ([TIME[2014-09-11 10:19:59 +09:00]] 版) <https://tools.ietf.org/html/rfc7234#section-6>
]REFS]

* 閲覧文脈とセッション履歴

[8] 各[[閲覧文脈]]は、
[F[セッション履歴]]を持ちます [SRC[>>1, >>2]]。
[[閲覧文脈]]の[F[セッション履歴]]は、
その[[閲覧文脈]]で過去、現在、未来に於いて[RUBYB[提示される]@en[presented]]
[CODE(DOMi)@en[[[Document]]]] [[オブジェクト]]の[[リスト]]です [SRC[>>1]]。
[[閲覧文脈]]の[F[セッション履歴]]は、
[[閲覧文脈の作成]]と同時に作成されます。

;; [4] [[最上位閲覧文脈]]も[[子供閲覧文脈]]も、
それぞれ1つずつ[F[セッション履歴]]を持ちます。

[5] [[セッション履歴]]は、[[セッション履歴エントリー]]の平坦なリストです [SRC[>>2]]。

[7] [[セッション履歴]]に含まれる[[セッション履歴エントリー]]のいずれか丁度1つは、
[[現在エントリー]]となります。

[21] [[セッション履歴]]は、必ず1つ以上の[[セッション履歴エントリー]]を持ちます。
空の[[セッション履歴]]は存在しません。[[閲覧文脈の作成]]時には、
[[初期「[CODE(URI)@en[about:blank]]」文書]]が自動的に作成されます。

[17] [[セッション履歴エントリー]]には[[文書]]が関連付けられています。
複数の[[セッション履歴エントリー]]が同じ[[文書]]を共有する場合があり、
そのような[[エントリー]]は[[セッション履歴]]上で連続しています。

;; [[セッション履歴エントリー]]を参照。

[18] 同じ[[文書]]を共有する[[セッション履歴エントリー]]が複数ある場合、
最後のものが[[文書]]の[[最新エントリー]]となります。
同じ[[文書]]を共有する[[セッション履歴エントリー]]の個数には、
[[利用者エージェント]]依存の上限が設定されていることがあります。

;; [CODE(DOMm)@en[[[pushState]]]] を参照。

[6] [CODE(DOMi)@en[[[History]]]] [[オブジェクト]]は、[[セッション履歴]]を表しています。
[CODE(DOMi)@en[[[History]]]] [[オブジェクト]]は [CODE(DOMi)@en[[[Document]]]]
ごとに存在しています。

;; [CODE(DOMi)@en[[[History]]]] を参照。

[12] 次の場面で[[セッション履歴]]の操作が行われます。
[FIG(short list)[
- [[navigate]]
- [CODE(DOMm)@en[[[pushState]]]]
- [CODE(DOMm)@en[[[replaceState]]]]
- [[履歴の探索]]
- [CODE(JS)@en[[[document.open]]]]
]FIG]

* セッション履歴エントリーの挿入

[13] [[セッション履歴]]に[[セッション履歴エントリー]]を挿入する操作は、
[VAR[置換有効]]について、
次のように行わなければ[['''なりません''']] [SRC[>>28, >>19, >>20]]。
[FIG(steps)[
= [30] [VAR[置換有効]]が[[偽]]の場合、
== [14] [[セッション履歴]]の[[エントリー]]のうち、[[現在エントリー]]よりも後のものを
(あれば) 削除します。 ([[現在エントリー]]は含みません。)
= [15] [[セッション履歴]]の[[閲覧文脈]]の[[最上位閲覧文脈]]の[[文書族]]の[[文書]]に関連付けられた[[履歴探索タスク源]]の[[タスク]]を (あれば) [[タスクキュー]]から削除します。
= [16] [[セッション履歴]]の最後に新しい[[エントリー]]を追加します。
]FIG]

;; [22] [[navigate]] で新しい[[文書]]に移動する場合 [SRC[>>20]]
には[[タスクキュー]]からの削除 (>>15) は行われませんが、
直後の[[履歴の探索]]内で結局削除が行われますから、同じこととなります。


[23] 
[DFN[[RUBYB[URLおよび履歴更新手順群]@en[URL and history update steps]]]]は、
[VAR[文書]]、
[VAR[新URL]]、
[VAR[直列化済みデータ]] (省略可能)、
[VAR[題名]] (省略可能)、
[VAR[状態pushフラグ]] (省略可能)
について、次のようにします [SRC[[CITE[HTML Standard]]]]。

[FIG(steps)[
= [38] 
[VAR[閲覧文脈]]を、
[VAR[文書]]の[F[閲覧文脈]]に設定します。
= [39] 
[VAR[状態pushフラグ]]が[[真]]の場合、
== [41] 
[VAR[閲覧文脈]]の[F[セッション履歴]]において、
[[現在エントリー]]''より''も後の[[セッション履歴エントリー]]をすべて削除します。
== [42] 
[VAR[閲覧文脈]]の[F[最上位閲覧文脈]]の[F[文書族]]に属する[[文書]]に関連付けられた[[履歴探索タスク源]]の[[タスク]]をすべて削除します。
== 必要があれば、[[利用者エージェント]]が永続化させたい状態を[[セッション履歴]]の[[現在エントリー]]に反映させます。[[現在エントリー]]は[[持続的利用者状態付きエントリー]]となります。
== [[文脈オブジェクト]]に関連付けられた[[文書]]の[[閲覧文脈]]の[[セッション履歴]]の[[現在エントリー]]直後に新しい[[セッション履歴エントリーを挿入]]します。
[FIG(list members middle)[
[FIGCAPTION[
[86] [[セッション履歴エントリー]]
]FIGCAPTION]
: [F[直列化済み状態]] : [VAR[直列化済みデータ]]
: [F[題名]] : [VAR[題名]]
: [F[URL]] : [VAR[新URL]]
:[F[[[要求メソッド]]]]:[CODE(HTTP)@en[[[GET]]]]
:[F[[[スクロール復元モード]]]]: [[セッション履歴]]の[F[[[現在エントリー]]]]の[F[[[スクロール復元モード]]]]
]FIG]
== 新しい[[セッション履歴エントリー]]を[[現在エントリー]]とします。
== 
@@
[[利用者エージェント]]依存のページごとの[[状態オブジェクト]]数の上限を設ける場合、
同じ[[セッション履歴]]中で[[現在エントリー]]と同じ[[文書]]を共有する[[セッション履歴エントリー]]のうち2番目のもの (= [[状態オブジェクト]]を持つ最古のもの) を削除して構いません。
= [40] それ以外の場合、
== [[現在エントリー]]を次の通り更新します。
[FIG(list members middle)[ 

: [F[直列化済み状態]] : [VAR[直列化済みデータ]] (無指定なら現在の値のまま)
: [F[題名]] : [VAR[題名]] (無指定なら値なし)
: [F[URL]] : [VAR[新URL]]
: [F[要求メソッド]] : [CODE(HTTP)@en[[[GET]]]]

]FIG]
= [77] [VAR[文書]]の[F[URL][文書の番地]]を、[VAR[新しいURL]]に設定します。
]FIG]


;; [37] [[要求メソッド]]を [CODE(HTTP)@en[[[GET]]]] にする時点で、
[[フォームデータ]]など他の [[fetch]] の[[引数]]も無かったことにされるようです。

[43] 
この手順群は、
[CODE[pushState]],
[CODE[replaceState]],
[CODE[document.open]]
から呼び出されます。


* セッション履歴エントリーの削除

[24] 挿入時にある位置から後の[[セッション履歴エントリー]]がすべて削除されることがあります (>>13)。

[26] [[履歴の探索]]である[[セッション履歴エントリー]]が[[セッション履歴]]から削除されることがあります。

[25] [CODE(JS)@en[[[document.open]]]] によって同じ[[文書]]を持つ[[セッション履歴エントリー]]がまとめて削除されることがあります。

* 関連

[9] [[結合セッション履歴]]は、複数の[[セッション履歴]]をまとめたものです。

[11] [[HTTPキャッシュ]]においては[[新鮮寿命]]などの規定がありますが、
これは必ずしも[[履歴]]に適用されるものではありません [SRC[>>10]]。
[[履歴]]を戻って[[腐敗応答]]を[[表示]]しても何ら問題ありません。
逆に[[腐敗]]していることを[[利用者]]に[[表示]]したり、
[CODE(HTTP)@en[[[Cache-Control:]] [[no-store]]]] に従ったりしても構いません。

* 歴史

[27] [CITE@en[<iframe> and the History API · Issue #184 · w3c/webcomponents]]
( ([TIME[2016-06-21 11:13:02 +09:00]]))
<https://github.com/w3c/webcomponents/issues/184>

[29] [CITE@en[cbrewster/ServoNavigation: Proposal for Servo Navigation]]
([TIME[2017-05-09 13:02:58 +09:00]])
<https://github.com/cbrewster/ServoNavigation>

[31] [CITE@en[Fragment navigation should use replacement enabled]]
([[annevk]]著, [TIME[2017-08-19 22:16:53 +09:00]])
<https://github.com/whatwg/html/commit/cf02423dc52686d084a3191833d939919b5907fd>

[32] [CITE@en[Bug in hash change algorithm with replace flag · Issue #2796 · whatwg/html]]
([TIME[2017-08-21 23:28:10 +09:00]])
<https://github.com/whatwg/html/issues/2796>

[33] [CITE@en[Fragment navigation should use replacement enabled by annevk · Pull Request #2869 · whatwg/html]]
([TIME[2017-08-21 23:28:19 +09:00]])
<https://github.com/whatwg/html/pull/2869>

[34] [CITE@en[document.open() simplifications, part 2]]
([[TimothyGu]]著, [TIME[2018-08-21 03:57:31 +09:00]])
<https://github.com/whatwg/html/commit/ae7cf0cc1936c6c309d7279c822dffc3af147851>

[35] [CITE@en[document.open() can make a document's URL go out of sync with its history entry · Issue #3885 · whatwg/html]]
([TIME[2018-09-05 22:39:55 +09:00]])
<https://github.com/whatwg/html/issues/3885>

[36] [CITE@en[At least Blink does not support document.open()'s replace parameter · Issue #3564 · whatwg/html]]
([TIME[2018-09-05 22:42:41 +09:00]])
<https://github.com/whatwg/html/issues/3564>

[37] [CITE@en[document.open() simplifications, part 2 by TimothyGu · Pull Request #3946 · whatwg/html]]
([TIME[2018-09-05 22:43:49 +09:00]])
<https://github.com/whatwg/html/pull/3946>

[44] [CITE@en[Editorial: Factor out history.push/replaceState() steps]]
([[TimothyGu]]著, [TIME[2018-08-18 08:04:45 +09:00]])
<https://github.com/whatwg/html/commit/f42dcf0bf2ebf86bc5ca79aecea098a8fed6cf3e>

[45] [CITE@en[Remove overridden reload concept]]
([[TimothyGu]]著, [TIME[2018-08-18 05:31:49 +09:00]])
<https://github.com/whatwg/html/commit/6440ccae7340ea41d3eb5bf8ff0b3b27363eda85>

[46] [CITE@en[556002 - document.open() and write() after parsing is complete breaks reload button - we reload new, not original document]]
([TIME[2018-09-05 23:38:32 +09:00]])
<https://bugzilla.mozilla.org/show_bug.cgi?id=556002>

[47] [CITE@en[Editorial: nested browsing context is a member, not a type]]
([[annevk]], [TIME[2019-11-27 02:46:03 +09:00]], [TIME[2022-01-18T09:44:02.000Z]])
<https://github.com/whatwg/html/commit/6b737bbc428facf34ec3728c0912cf9e172d0ea4>

[48] 
[CITE@ja[Xユーザーのたなさん: 「最近 history API悪用してブラウザバックで離脱しようとするとおすすめ記事ページみたいなのを一度挟むサイト増えてない? 口汚く罵りたいんだけど」 / X]], [TIME[午前8:12 · 2024年3月31日][2024-03-30T23:12:23.000Z]], [TIME[2024-04-01T01:54:45.000Z]] <https://twitter.com/side_tana/status/1774213110511067202>
