Skip to content

Instantly share code, notes, and snippets.

@eric1234
Last active December 12, 2015 01:10
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save eric1234/77720eb0da524a049c2b to your computer and use it in GitHub Desktop.
Save eric1234/77720eb0da524a049c2b to your computer and use it in GitHub Desktop.
Protect data from being lost in form edit on navigation

Based on http://stackoverflow.com/a/11844403/120067 but with the following enhancements:

  • It is coffeescript which IMHO automatically makes it better. :)
  • It is entirely based on event bubbling so dynamic content is automatically handled (@AlphaMale's update also has this).
  • It only operates on POST forms as GET forms do not have data we typically want to avoid loosing (i.e. GET forms tend to be search boxes and filtering criteria).
  • It doesn't need to be bound to a specific button for carrying out the save. Anytime the form is submitted we assume that submission is saving.
  • It is Turbolinks compatible. If you don't need that just drop the two page: event bindings.
  • It is designed so that you can just include it with the rest of your JS and your entire site will be protected.

Install with gist-dep with:

gist-dep add -p app/assets/javascripts/unsaved-alert.js.coffee 77720eb0da524a049c2b
# Message displayed to user. Depending on browser and if it is a turbolink,
# regular link or user-driven navigation this may or may not display.
msg = "This page is asking you to confirm that you want to leave - data you have entered may not be saved."
# Default state
unsaved = false
# Mark the page as having unsaved content
$(document).on 'change', 'form[method=post]:not([data-remote]):not(.no-alert) :input', -> unsaved = true
# A new page was loaded via Turbolinks, reset state
$(document).on 'page:change', -> setTimeout (-> unsaved = false), 250
# The user submitted the form (to save) so no need to ask them.
$(document).on 'submit', 'form[method=post]', ->
unsaved = false
return
# Confirm with user if they try to go elsewhere
$(window).bind 'beforeunload', -> return msg if unsaved
# If page about to change via Turbolinks also confirm with user
$(document).on 'page:before-change', (event) ->
event.preventDefault() if unsaved && !confirm msg
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment