iOS Safariにおいて同一ページ内でブラウザバックwindow.alert/dialogが表示されなくなる問題

今携わっているプロジェクトは、Vue.jsによるアプリ制作の短期プロジェクト。必要なページ数(正確にいうと、ページのもとになるコンポーネント数)は少ないのでUIフレームワークは使わず、CSSによるレイアウトは独自で実装。
仕様のひとつとして、確認ダイアログをだして「OK」を押したら次のページへ進むというものがあったのだけど、独自に実装するのは面倒だし、デザイン指定があるわけでもないので、標準のwindow.confirmを利用。
一通り完成した後、いろいろなブラウザや端末(iPhoneやAndroidやiPad)でテストしてみると、特に問題なし。
今回は順調に終わったなぁ。なんて思っていたら、たまにiPadで確認ダイアログが表示されなくなることに気づいた。エラーがでたらエラーログを出力するようになっているのだけど、エラーログは出力されておらず。調べようと思って画面を更新したら動いた。
何だこれ? と思ってしばらく調べて分かった。ブラウザの戻る機能を使うと、ダイアログが表示されなくなる。

というわけで、試しに簡単なサンプルを作ってiPod touch(iOS 15.2.1)で試してみました(サンプルページ)。
作ったサンプルページは、単純にボタンをクリックすると、確認ダイアログ(window.confirm)が表示され、「OK」を押下するとURLのハッシュが変化するというもの。

最初に表示した時はこんな感じ。

「ここをクリック」というボタンを押すと、確認ダイアログが表示された。

「OK」を押すと、URLの後ろに「#hash1」とつく。

ここでブラウザバックしてURLを一つ前に戻す(URLの後ろに「#hash1」がつかなくなる)。

「ここをクリック」というボタンを押すと、確認ダイアログが表示されず、キャンセルを押したのと同じ扱いになる。

もちろん、PCやAndroidで行うとちゃんと確認ダイアログが表示される。

Safariのバグかと思ったのだけど、どうも昔からそういう動きのようです(一つ目のリンク先は2016年6月に投稿された質問)。
javascript – Alert, confirm, and prompt not working after using History API on Safari, iOS – Stack Overflow
javascript – IOS Safari window.alert, window.confirm not working after onpopstate triggered – Stack Overflow
iPhoneでページ内リンクからブラウザバックした後にalertが動かない現象 – Qiita

こんなに前から放置してしているということは、Safariの仕様なのだろうか。
対策の一つとして、window.location.reload()と実行して再読み込みすると書いている人もいるのだけど、さすがにそれはやりたくないので(起動時にAPI呼び出しするアプリのため)、独自で確認モーダルを実装するのがよさそうです。

ちなみに、alertとかの標準ダイアログ系は、昨年Google Chromeでも、クロスオリジンのiframe内で急に動かなくなるという問題があったようです(参考:クロスオリジンのiframeでのalert()やconfirm()やpromptが使えなくなった問題【GAS】 – ポンコツエンジニアのごじゃっぺ開発日記。)。今後も使えなくなるということはありそうですし、いろいろ問題もありそうなので、使わないほうがいいのかもしれないです。

コメント

タイトルとURLをコピーしました