よくわからん機能
Chrome 132では、非アクティブなドキュメント内のポップオーバーやダイアログに対してshowPopover()やshowModal()を呼び出すと、InvalidStateErrorがスローされるように変更されました。以前は、これらのメソッドを非アクティブなドキュメントで実行してもエラーは発生せず、単に表示されないだけでした。この変更は、開発者が意図しない動作を早期に検出できるようにするためのものです。
この機能はChrome 132から新たに導入される変更です。既存のシステムでshowPopover()やshowModal()を使用している場合、非アクティブなドキュメントでこれらのメソッドを呼び出すとエラーが発生する可能性があります。そのため、システム全体のソースコードを確認し、これらのメソッドの使用箇所を特定することが重要です。
ソースコード内でshowPopover()やshowModal()を使用している箇所を特定するには、以下の文字列を検索してください。
showPopover(
showModal(
これらのメソッドが使用されている箇所を確認し、非アクティブなドキュメントで呼び出されていないかを検討することで、今回の変更による影響を評価できます。
showModal(を使用しているコードが影響を受けるかどうかを切り分けるには、以下の手順を取ると良いでしょう。
手順 1: 該当箇所の特定
ソースコード内でshowModal(を検索し、該当する箇所をリストアップします。
使用箇所の周囲のコードを確認し、以下の条件に該当するかを確認します。
ダイアログが「非アクティブなドキュメント」で操作されている可能性があるか?
手順 2: 「非アクティブなドキュメント」の確認方法
以下を確認します。
対象のドキュメントが現在アクティブか?
ドキュメントのdocument.visibilityStateを確認します。これがhiddenである場合、そのドキュメントは非アクティブです。
例えば、console.log(document.visibilityState)で状態を確認します。
iframeなど別のコンテキスト内で操作されているか?
iframe内で操作されている可能性を考慮してください。例えば、iframeのcontentDocumentやcontentWindowを介して操作している場合、非アクティブな状態である可能性があります。
ページ遷移やバックグラウンドタブ時に呼び出されていないか?
ページのフォーカスが失われた際に実行されるスクリプトの中にshowModal(が含まれている場合、問題となる可能性があります。
手順 3: 影響がある場合の対応方法
非アクティブな状態で実行しないようガードを追加
document.visibilityStateをチェックし、非アクティブな場合はshowModal()を実行しないようにします。
javascript
コードをコピーする
if (document.visibilityState === 'visible') {
dialog.showModal();
} else {
console.warn("Dialog cannot be shown in a non-active document");
}
例外処理を追加
万が一エラーが発生した場合でもアプリが停止しないように、try-catchブロックでエラー処理を行います。
javascript
コードをコピーする
try {
dialog.showModal();
} catch (e) {
if (e.name === 'InvalidStateError') {
console.error("Dialog cannot be shown because the document is inactive:", e);
} else {
throw e; // 他のエラーはそのまま再スロー
}
}
設計を見直す
ダイアログを非アクティブなドキュメントで表示する設計そのものを避けるべきです。アクティブな状態を必要とする動作がある場合は、UI設計を見直します。
まとめ
Grepで検出する文言: showModal(
非アクティブ状態をチェックする条件:
document.visibilityStateの値がhiddenでないか。
iframeやバックグラウンド実行ではないか。
影響がある場合の対応策:
ガード条件を追加する。
try-catchで例外処理を行う。
非アクティブドキュメントでの操作を回避する設計を採用する。
これにより、Chrome 132の変更の影響を適切に切り分け、対応できます。
あなた:
document.visibilityState でGrep していなければ言いとういうものでもない?
ChatGPT:
ChatGPT
おっしゃる通り、document.visibilityStateを使用していないからといって、安全であるとは限りません。その理由と補足を以下に説明します。
理由: document.visibilityStateで切り分けできないケース
visibilityStateチェックがなくても問題がないケースもある
showModal()が呼び出されるコードが、必ずアクティブなドキュメント内で実行される設計になっていれば、visibilityStateを使う必要がない場合があります。
例: メインのUIイベント(クリックやボタン操作)から直接呼び出される場合。
設計ミスで非アクティブなドキュメントで呼び出される可能性
例えば、バックグラウンドで動作する非同期処理やタイマーなどでshowModal()が呼び出されている場合、visibilityStateが使われていなくても非アクティブな状態で動作してしまう可能性があります。
非アクティブかどうかの確認方法が別途ある可能性
document.hasFocus()などの他のAPIを使ってアクティブ状態をチェックしている場合、visibilityStateだけでは検出できません。
安全性を保証するための追加確認
コード内でdocument.visibilityStateのチェックがない場合、以下の追加調査が必要です。
1. 呼び出し元の確認
showModal()の呼び出し箇所で、明示的に「アクティブな状態を前提にしている」かどうかを調査します。
クリックイベントやユーザー操作イベントの中でのみ実行されている場合は安全性が高いです。
2. 非同期処理の中での呼び出し
タイマーや非同期処理(例: setTimeoutやPromiseの.then()内)でshowModal()が使われていないか確認します。非同期処理では、実行時にドキュメントが非アクティブになっている可能性があります。
3. iframeやバックグラウンド実行の確認
showModal()が他のiframeやウィンドウコンテキストで動作するコードで使われていないかを確認します。
特にwindow.frames[]やiframe.contentWindowを利用している箇所があれば要注意です。
Grepに追加すべき検索対象
単純にdocument.visibilityStateだけでは不足する可能性があるため、以下のキーワードも併せて検索することを推奨します。
showModal(
直接該当する箇所を調査。
非同期処理の指標
setTimeout
.then(
async / await
iframe操作
iframe.contentWindow
iframe.contentDocument
まとめ
Grepだけで完全に切り分けるのは難しい: document.visibilityStateのチェック有無だけでなく、非同期処理や他のドキュメント操作の有無も確認が必要。
より詳細な影響調査: 呼び出し元のコードフローを確認し、非アクティブな状態で実行される可能性を排除する設計であるかを確認する必要があります。
適切な調査を通じて、Chrome 132の変更による影響を確実に排除できます。
showPopover(についても、showModal(と同様に、非アクティブなドキュメントで呼び出された場合にInvalidStateErrorがスローされる可能性があります。そのため、showPopover(を使用しているコードが影響を受けるかどうかを切り分ける手順を以下にまとめます。
手順: showPopover(の影響切り分け
showPopover(はHTML要素(ポップオーバー)を表示するためのAPIで、非アクティブなドキュメントで実行されるとエラーになる可能性があります。これを確認するための具体的な手順を以下に記載します。
1. 使用箇所の特定
ソースコード内でshowPopover(を検索し、すべての使用箇所をリストアップします。
2. 非アクティブなドキュメントで動作する可能性の確認
以下の点を確認します。
アクティブな状態で動作しているか?
document.visibilityStateをチェックしているか、またはdocument.hasFocus()を使用しているかを確認します。
これらがない場合、非アクティブな状態で呼び出される可能性があります。
呼び出しのトリガーがユーザーイベントか?
例えば、クリックやキーボード入力などの直接的なユーザーイベントでshowPopover()が呼び出されている場合は、通常アクティブなドキュメント内で動作しているはずです。
非同期処理内での実行
setTimeoutやasync関数内で実行されている場合、非アクティブなドキュメントで呼び出される可能性があります。
iframeや別のコンテキストからの操作
iframe.contentDocumentやcontentWindowを介してポップオーバーを操作している場合、非アクティブな状態になる可能性があります。
3. 必要に応じた修正
該当箇所が非アクティブなドキュメントで動作する可能性がある場合、以下の対策を取ります。
状態チェックを追加
document.visibilityStateやdocument.hasFocus()を用いて、非アクティブな状態ではshowPopover()を実行しないようにします。
javascript
コードをコピーする
if (document.visibilityState === 'visible') {
element.showPopover();
} else {
console.warn("Popover cannot be shown in a non-active document");
}
例外処理を追加
try-catchでエラーを処理し、非アクティブなドキュメントでエラーが発生してもアプリが停止しないようにします。
javascript
コードをコピーする
try {
element.showPopover();
} catch (e) {
if (e.name === 'InvalidStateError') {
console.error("Popover cannot be shown in the current state:", e);
} else {
throw e; // 他のエラーは再スロー
}
}
設計の見直し
非アクティブなドキュメントでポップオーバーを操作しないよう、UIや処理フローを設計し直します。
Grep対象と調査方法
Grep対象
showPopover(
追加調査が必要な場合
非同期実行の可能性がある箇所:
setTimeout, .then(, async/await
iframe経由の操作:
iframe.contentDocument, iframe.contentWindow
結論
showPopover(もshowModal(と同じく、非アクティブな状態で呼び出される可能性がある箇所に注意が必要です。ただし、呼び出しが明確にアクティブなドキュメントで行われている場合、特別な対策は不要です。影響を正確に切り分けるためには、呼び出し元や非同期処理の使用を確認することが重要です。