-
Notifications
You must be signed in to change notification settings - Fork 71
Turbolinks導入にあたっての問題(2020 04 29)
このドキュメントは2020/04/29に@hasehiro25によって書かれました
TurbolinksをFjord boot campに導入するにあたって、現在解決が難しい問題に直面し、2020/04/29導入を断念いたしました。
将来Turbolinksを導入する方への参考になれば幸いです。
編集中のフォーム(日報、FAQなど)からページ遷移すると確認ダイアログが表示されます。(warning.jsで実装されてる)
ダイアログを表示するためにbeforeunload
でページ遷移や更新イベントを検知し、イベントが発火されればevent.returnValue()
でダイアログが出せる仕組みになっています。
Turbolinksでは仕組み上ページ遷移する時beforeunload
が発火されません。
ページ遷移にダイアログ対応できたものの、history-backに対応できませんでした。
turbolinks:before-visit
とはTurbolinksがページ遷移する前に発火されるイベントです。
before-visitでページ遷移の時にconfirmでメッセージボックスを出すことはできました。
ページの更新とページを閉じるに発火しないので`beforeunload'と併用すると両方対応できる。
以下参考コードです。
const warningForm = document.querySelector('.js-warning-form')
const onUnload = () => {
const message = 'このページを離れると、入力したデータが削除されます。本当に移動しますか?'
window.addEventListener('beforeunload', e => {
if (!submitting && !commentForm) {
const warningForm = document.querySelector('.js-warning-form')
if (!warningForm) { return null }
e.preventDefault()
e.returnValue = message
}
})
window.addEventListener('turbolinks:before-visit', e => {
if (!submitting && !commentForm) {
const warningForm = document.querySelector('.js-warning-form')
if (!warningForm) { return null }
if (!confirm(message)) {
e.preventDefault()
}
}
})
}
warningForm.addEventListener('change', onUnload, false)
how to trigger " window.onbeforeunload " event under turbolinks ? - turbolinks - github
ただし、before-visitではhistory-backには対応してないそうです。
Full List of Events - turbolinks/github
canceling-visits-before-they-start -turbolinks/github
なのでhistory-backの前後でページ遷移の判定と遷移しないようにできないか考えました。
調べた結果、history-backを行うとpopstateイベントが発火され、ページ移行を止める手段がないので、history-backに対応するのは現状難しそうです。
onbeforeunload on back button - prevent user from losing unsaved changes turbolinks/github
参考
WindowEventHandlers.onpopstate - mdn
Window: beforeunload イベント - mdn
Turbolinksの設定にそのページにあるリンクからの遷移はTurbolinksを切るという設定があります。
Disabling Turbolinks on Specific Links turbolinks/github
設定を有効するとページ遷移がbeforeunload
で発火することが可能になり、ページ遷移、更新、閉じるに対応できます。
ただし、こちらも上記と同じ理由でhistory-backに対応できませんでした。
以下は当時発生した問題と解決した方法のメモ書きです
Stripeをheadから読み込んでページを遷移すると
'Failed to execute 'postMessage' on 'DOMWindow': The target origin provided ('https://js.stripe.com') does not match the recipient window's origin ('http://localhost:3000').
というエラーがコンソールに出ます。
このエラーをStripe公式に問い合わせたところ、特に動作には問題のないとうことでした。公式は問題を把握しているものの、どう対応するか未定だそうです。
またruby-jpに確認したところ、動作に影響はないものの、エラーが出てる以上は予期せぬ動作が考えられ、スマートではないものの解決手段は用意されているのでそれを使った方が良いのではと教えていただきました。
最終的に、issueとプルリクを参考にStripeFormがあるページの前後に更新をかけ、フォームのないページではStripeのscriptを読み込まないように実装しました。(未レビュー)
Turbolinks and stripe - turbolinks/github
Add meta tag for opting in to full page reloads - turbolinks/github
Turbolinksを有効にすると、ページ遷移するとGTMのプレビュー画面が表示されません。(計測そのものはしてます)
GTMのiframeが最初のページのbodyに紐づくため、ページ遷移するとプレビューが消えてしまう仕様です。
こちらは根本的な解決はできなかったものの、GTMが必要なのはWELCOME側であり、Turbolinksを使いたいのはログイン後の画面なので、WELCOME側ではTurbolinksを切るという方法で対処しました。
具体的な方法としてWELCOME内のリンクを全部turbolinksを無効にするプロパティを追加しました。
Disabling Turbolinks on Specific Links turbolinks/github
なお、GA側はそのままでは動かないで、ページ遷移を検知するためにコードの修正が必要です。
以上が実装のメモです。
将来誰かが代わりに実装してくれるのを期待しております:pray: