jQuery ajaxStart Event

Beginner
8 min read
Updated: Oct 2026
5 examples
Live preview

What Is ajaxStart?

ajaxStart is a global AjaxEvent (event since jQuery 1.0; .on() binding since 1.7). jQuery triggers it on document when the first qualifying Ajax request is about to begin — and only if no other global requests are already active.

Remember
$(document).on("ajaxStart", function () {
  // runs when the first global Ajax request begins
});

// Order (batch):
// ajaxStart → ajaxSend → success|error → ajaxComplete → ajaxStop

// Opt out for one call:
$.ajax({ url: "/x", global: false });
NeedUse
Show loading when Ajax begins$(document).on("ajaxStart", fn)
Hide loading when idleajaxStop
Before every requestajaxSend
After every requestajaxComplete
One request only$.ajax(...).always(fn) / beforeSend

How to Use ajaxStart

Bind once on document, then the first global Ajax call can show your loading UI.

  1. Attach the handler to document with .on("ajaxStart", handler).
  2. Make requests with $.ajax(), $.get(), $.post(), or .load().
  3. Show a spinner or status text inside the handler (no jqXHR args).
  4. Pair with ajaxStop to hide the UI when the last request finishes.
  5. Use global: false on requests that must stay silent.
PieceRequired?Role
documentYes (1.9+)Only valid bind target for global Ajax events
handlerYesfunction() — no request args
ajaxStopRecommendedHide loading when no global requests remain
global: falseOptionalSkip all global Ajax events for that call

Pseudocode

Pseudocode
bind ajaxStart on document with handler()

when a jQuery Ajax request is about to send:
    if request.global === false:
        do not count it / do not fire ajaxStart
        return

    if no other global Ajax requests are active:
        fire ajaxStart
            for each registered handler:
                call handler()

    then fire ajaxSend for this request
    ... send and complete ...
    when last active global request finishes:
        fire ajaxStop

Cheat Sheet

Keep these facts handy while wiring a global loading indicator.

TopicDetail
Bind$(document).on("ajaxStart", handler)
Unbind$(document).off("ajaxStart" [, handler])
Signaturefunction() — no jqXHR / settings
WhenFirst global request begins (idle → busy)
SinceEvent 1.0 · .on() form 1.7 · document-only 1.9+
Pair withajaxStop to hide loading UI
vs ajaxSendStart = once per batch · Send = every request
Opt outglobal: false in $.ajax() / $.ajaxSetup()

Live Preview

Run a real $.get() and watch the global ajaxStart handler update the log.

Live demo uses a public JSON API. Needs network access.

Result
Ready — pick an action and click Run.

jQuery Examples

Short, copy-ready snippets. Open DevTools Console, or use Try It Yourself for a live editor.

Example 1 — Document Handler + .load()

Official pattern: log a message when the first Ajax request begins after a click.

jQuery
$(document).on("ajaxStart", function () {
  $(".log").text("Triggered ajaxStart handler.");
});

$(".trigger").on("click", function () {
  $(".result").load("ajax/test.html");
});
Try It Yourself

How It Works

  1. Bind. .on("ajaxStart") on document listens globally.
  2. Click. .load() starts an Ajax request under the hood.
  3. First. Because nothing else is active, ajaxStart fires.
  4. Update. The log text confirms the global event ran.

Example 2 — Show a Loading Message

Official demo: reveal a loading element whenever Ajax activity begins.

jQuery
$(document).on("ajaxStart", function () {
  $("#loading").text("Loading…");
});

$("#go").on("click", function () {
  $.get("https://jsonplaceholder.typicode.com/posts/1");
});
Try It Yourself

How It Works

  1. Handler. On start, write a loading message into #loading.
  2. Trigger. Any qualifying Ajax call can light up the UI.
  3. No args. You do not need jqXHR — this is page-wide UI only.
  4. Next step. Bind ajaxStop to clear the same element when idle.

Example 3 — Parallel Requests Fire Once

Three overlapping calls still produce a single ajaxStart.

jQuery
var startCount = 0;

$(document).on("ajaxStart", function () {
  startCount++;
  $("#log").text("ajaxStart count: " + startCount);
});

$("#go").on("click", function () {
  $.get("https://jsonplaceholder.typicode.com/posts/1");
  $.get("https://jsonplaceholder.typicode.com/posts/2");
  $.get("https://jsonplaceholder.typicode.com/posts/3");
});
Try It Yourself

How It Works

  1. Idle → busy. The first request finds no active globals and fires start.
  2. Already busy. The next two see activity in progress — no extra start.
  3. Count. Your counter increments once per batch, not per call.
  4. Use. Perfect for a single page-wide spinner.

Example 4 — Opt Out with global: false

Private requests skip all global Ajax events, including ajaxStart.

jQuery
$(document).on("ajaxStart", function () {
  $("#log").append(" ajaxStart");
});

// Fires ajaxStart
$.get("/api/public");

// Does NOT fire ajaxStart
$.ajax({ url: "/api/silent", global: false });
Try It Yourself

How It Works

  1. Default. Ajax calls participate in global events.
  2. Opt out. global: false skips ajaxStart (and the other globals).
  3. Local still works. .done() / .fail() / .always() still run.
  4. When. Use for silent prefetch, polling, or third-party widgets.

Example 5 — ajaxStart + ajaxStop Pair

Show loading when the first request begins; hide it when the last request finishes.

jQuery
$(document).on("ajaxStart", function () {
  $("#loading").text("Loading…");
});

$(document).on("ajaxStop", function () {
  $("#loading").text("");
});

$("#go").on("click", function () {
  $.get("https://jsonplaceholder.typicode.com/posts/1")
    .done(function (post) {
      $("#out").text(post.title);
    });
});
Try It Yourself

How It Works

  1. Start. First global request → show the loading message.
  2. Work. The request runs; parallel calls keep the spinner text visible.
  3. Stop. Last global request finishes → ajaxStop clears it.
  4. Result. One spinner covers the whole active batch.

Edge Cases & Pitfalls

Check these before relying on a global loading spinner.

target

Bind on document only (1.9+)

Handlers on window or other elements will not receive global Ajax events.

once

Not per request

ajaxStart fires once per busy batch. Use ajaxSend when you need every request.

global

global: false stays silent

Those requests never trigger ajaxStart and do not count toward the active total.

args

No jqXHR in the handler

Unlike ajaxSend / ajaxComplete, the start handler has no settings object — keep it for UI only.

Browser Support

ajaxStart has been part of jQuery since 1.0. Prefer $(document).on("ajaxStart", …) (1.7+). Since 1.9, handlers must attach to document.

✓ Stable · jQuery 1.0+

jQuery ajaxStart

Works in every browser that runs your loaded jQuery version. Prefer a current jQuery 3.x build for modern projects.

100% jQuery Ajax event
Google Chrome All versions · Desktop & Mobile
Full support
Mozilla Firefox All versions · Desktop & Mobile
Full support
Apple Safari All versions · macOS & iOS
Full support
Microsoft Edge All versions · Chromium & Legacy
Full support
Internet Explorer IE 6+ · Legacy environments
Full support
Opera All modern versions
Full support
ajaxStart Universal

Bottom line: Safe for everyday apps. Bind on document, pair with ajaxStop for loading UI, and use global: false for silent background calls.

Performance Notes

ApproachCostBest for
One ajaxStart + ajaxStopCheapPage-wide loading spinner
ajaxSend every requestCheapPer-request logging / headers
Heavy DOM work on every startExpensiveAvoid — keep the handler tiny

Global start handlers are fine when they only toggle a spinner or short status text. Leave per-request work to ajaxSend or beforeSend.

Key Takeaways

  • Role: global “Ajax just became busy” hook — first request only.
  • Bind: $(document).on("ajaxStart", fn) — document only since 1.9.
  • Pair: use ajaxStop to hide the same loading UI.
  • Per request: prefer ajaxSend when you need settings or jqXHR.

One line: ajaxStart is jQuery’s global first-request-began event — bind it on document and pair it with ajaxStop.

Frequently Asked Questions

ajaxStart is a global AjaxEvent that fires when the first qualifying jQuery Ajax request is about to be sent — and only when no other global Ajax requests are already in progress. Bind it with $(document).on("ajaxStart", handler) (since 1.7).
Since jQuery 1.9, all global Ajax event handlers must be bound to document — not window or other elements. Use $(document).on("ajaxStart", fn) and remove with $(document).off("ajaxStart", fn).
No. It fires once when the first active global request begins. Three parallel $.ajax() calls still trigger ajaxStart only once. Pair it with ajaxStop, which fires when the last active global request finishes.
ajaxStart fires once at the start of a batch (no active requests yet). ajaxSend fires before every individual qualifying request and receives event, jqXHR, and settings. Use ajaxStart for page-wide loading UI; use ajaxSend for per-request work.
When $.ajax() or $.ajaxSetup() sets global: false, that request opts out of all global Ajax events. ajaxStart will not fire for it, and it does not count toward the active global request total used by ajaxStart/ajaxStop.
None that matter for typical use — function() { … }. Unlike ajaxSend or ajaxComplete, you do not get jqXHR or settings. Use those events when you need per-request details.
The shorthand method .ajaxStart(handler) is deprecated as of jQuery 3.5. Prefer $(document).on("ajaxStart", handler) — the event API this page teaches.

Next: .ajaxStart() method

See the deprecated shorthand and how to migrate to .on("ajaxStart").

.ajaxStart() tutorial →

About the author

Mari Selvan M P
Mari Selvan M P 🔗

Developer, cloud engineer, and technical writer

  • Experience 12 years building web and cloud systems
  • Focus Full Stack Development, AWS, and Developer Education

I write practical tutorials so students and working developers can learn by doing—from databases and APIs to deployment on AWS.

9 people found this page helpful