AbortController is an interface which provides a way for terminating one or
more web request as and when desired.
This generally means that a request can be terminated by a user whenever needed,
irrespective of whether the operation is finished or not.
AbortSignal can be implemented in any web platform API which uses
Promise.
The API
AbortController provides a few things for users to implement it effectively in
code. At the time of writing this, the constructor would return an instance which
contains a method AbortController.abort() and a property 
AbortController.signal(read-only).
- 
AbortController.signal- Returns aAbortSignalinstance
- 
AbortController.abort()- Aborts a DOM Request
AbortSignal
AbortController.signal returns an instance of type AbortSignal which 
represents the current state of the AbortController instance.
It has a read-only property AbortSignal.aborted. Type of property aborted
is Boolean.
AbortSignal is also responsible for communicating with DOM as an Event Listener
can be attached to it.
Using AbortController
To use AbortController in a Promise, one must adhere to a few rules.
Source
- Function should accept AbortSignalthrough asignalproperty. For example:
  function abortThis(arg1, { signal }) {
    return new Promise((resolve, reject) => {
      // function body
    })
  }
- When method aborted()is called, reject the Promise with aDOMExceptionAbortError
  throw new DOMException('aborted by user', 'ABORT_ERR');
-  Abort immediately if the abortedflag onAbortSignalis set totrue.
Browser Support
Despite being a relatively new API, browser support for AbortController is
quite awesome! All major browser fully supports it. Following is a chart
from Can I Use.
<div
  class="ciu_embed"
  data-feature="abortcontroller"
  data-periods="future_1,current,past_1,past_2"
  data-accessible-colours="false"
Data on support for the abortcontroller feature across the major
browsers
Examples
Following are a few examples of AbortController API. First one is using fetch
API. On the second example, I will try to implement it in a Promise.
Using Fetch API
const controller = new AbortController();
const signal = controller.signal;
// fetch a URL
fetch('https://jsonplaceholder.typicode.com/todos/1', { signal })
  .then(raw => raw.ok && raw.json())
  .then(console.log)
  .catch(e => console.log(e.message));
// driver code
setTimeout(() => {
  // abort network request if it takes
  // more than a second
  controller.abort();
}, 500);
The above code allows a network request to run for 500ms. If data has been
fetched within that period, it would return JSON representation of the response.
Otherwise, it would abort the request.
Implementing using Promise
In this section, I will try to implement AbortController for a function which
returns Promise. Should be quite easy and straightforward.
/* this function would return a Promise
 * which would resolve with value `hello`
 * after 4s
 */
function abortTask({ signal }) {
  return new Promise((resolve, reject) => {
    // 1. check if it's already aborted
    if (signal && signal.aborted) {
      return reject(new DOMException('`signal` is in `aborted` state', 'ABORT_ERR'));
    }
    // wait for 4s
    setTimeout(() => resolve("hello"), 4000);
    // 2. add a listener to `signal` to check its state
    signal && signal.addEventListener('abort', () => {
      // reject promise when signal.aborted changes to `true`
      return reject(new DOMException('aborted by user', 'ABORT_ERR'));
    })
  })
}
/* DRIVER CODE */
let signal;   // just so that I could re-use it
// when `signal.aborted` is `false`
const abortController_1 = new AbortController();
signal = abortController_1.signal;
abortTask({ signal })
  .then(t => console.log(t)) // hello
  .catch(e => console.error(e.message))
// when `signal.aborted` is `true`
const abortController_2 = new AbortController();
signal = abortController_2.signal;
abortController_2.abort();
abortTask({ signal })
  .then(t => console.log(t))
  .catch(e => console.error(e.message)) // err
// when user calls AbortController.abort()
const abortController_3 = new AbortController();
signal = abortController_3.signal;
// abort task in 2s
setTimeout(() => abortController_3.abort(), 2000);
abortTask({ signal })
  .then(t => console.log(t))
  .catch(e => console.error(e.message)) // err
 
 
              
 
    
Top comments (0)