// Landing "notify me", the enhanced path. The form posts to /notify on its // own with JS off; this submits the same route and the same encoding over // fetch so the visitor keeps their place on the page instead of reloading it. // Posting the form verbatim also means the CSRF token rides along without // being read out and re-attached by hand. function submitNotify(e) { e.preventDefault(); var form = document.getElementById('notify-form'); var status = document.getElementById('notify-status'); var btn = form.querySelector('button'); btn.disabled = true; btn.textContent = 'Sending...'; status.textContent = ''; status.className = 'notify-status'; fetch(form.action, { method: 'POST', headers: {'Accept': 'application/json'}, body: new URLSearchParams(new FormData(form)) }).then(function(r) { // The route answers a redirect to /?notify=ok or /?notify=invalid. // fetch follows it, so the landed URL is what says which happened. if (!r.ok) throw new Error('Something went wrong'); if (r.url.indexOf('notify=invalid') !== -1) { throw new Error('That address didn\'t look right.'); } status.textContent = 'You\'re on the list.'; status.className = 'notify-status success'; form.querySelector('input[name="email"]').value = ''; }).catch(function(err) { status.textContent = err.message; status.className = 'notify-status error'; }).finally(function() { btn.disabled = false; btn.textContent = 'Notify Me'; }); return false; }