Skip to content

Events & callbacks

Two ways to hook in:

NeedUse
Replace the default success/error UIcallback option
Keep the default UI, but add logging, CSRF, or analyticsWindow events

You can use both. callback owns the UI; events still fire.

Callback — you own the UI

When callback is a function, formsub does not run the default handler. You handle success, errors, and field errors. The form is not cleared automatically.

js
formsub.newForm({
  formId: 'contact-form',
  submitButton: '#submit-button',
  ajaxUrl: '/api/contact',
  callback: (response) => {
    if (response.status === 'success') {
      showToast(response.message);
      document.getElementById('contact-form').reset();
    } else if (response.errors) {
      response.errors.forEach((err) => {
        console.log(err.name, err.error);
      });
    } else {
      alert(response.message);
    }
  },
});

formsub:AfterSubmit still fires after your callback.

Events — keep the default UI

All events are dispatched on window.

EventWhenevent.detailCancelable
formsub:BeforeSubmitAfter validation, before fetchFormDataYespreventDefault() aborts
formsub:AfterSubmitAfter response handlingResponse objectYes (usually ignore)
formsub:ResponseSuccessDefault handler sees successResponse objectYes
formsub:ResponseErrorDefault handler sees errorResponse objectYes

ResponseSuccess and ResponseError fire only with the default handler (no callback).

AfterSubmit fires after success, server errors, and network errors. It does not fire when client validation fails or BeforeSubmit is cancelled.

Add fields before submit

js
window.addEventListener('formsub:BeforeSubmit', (event) => {
  event.detail.append('csrf_token', getCsrfToken());
  event.detail.append('timestamp', Date.now());
});

Cancel a submit

js
window.addEventListener('formsub:BeforeSubmit', (event) => {
  if (!confirm('Send this message?')) {
    event.preventDefault();
  }
});

Log every finished submit

js
window.addEventListener('formsub:AfterSubmit', (event) => {
  console.log('Done:', event.detail.status, event.detail.message);
});

Callback + events together

js
formsub.newForm({
  formId: 'contact-form',
  submitButton: '#submit-button',
  ajaxUrl: '/api/contact',
  callback: (response) => myApp.handle(response),
});

window.addEventListener('formsub:AfterSubmit', (event) => {
  analytics.track('form_submit', { status: event.detail.status });
});

Multiple forms

Events are global. The response object includes form_css_id (the form’s id):

js
window.addEventListener('formsub:AfterSubmit', (event) => {
  if (event.detail.form_css_id !== 'contact-form') return;
  // ...
});

Released under the MIT License.