WARNING: not maintained, feel free to fork and use in any way
npm i axios use-axios-react
- Hooks for ✅ data fetching ✅ CRUD ✅ Batch operations
- ✅ Request cancellation
- ✅ Retry/reload callbacks
- ✅ Zero-configuration, yet fully configurable when needed
- ✅ No app architecture commitments, drop in into your React and Axios project and start using hooks in your new components
- No extra-dependencies (React and Axios are peer dependencies), thus minimum overhead if your project already uses axios
- All axios features
npm i use-axios-react
Make sure axios itself is installed
npm i axios
And make sure you use React v16.8.0 or newer.
Basic data fetching (GET)
import React from "react";
import { useGetData } from "use-axios-react";
const KanyeQuote = () => {
  const [data, loading] = useGetData("https://api.kanye.rest/");
  if (loading) return <div>Loading...</div>;
  return <blockquote>{data.quote}</blockquote>;
};Cancellable fetching (GET) with reload and retry
import React from "react";
import { useGetData } from "use-axios-react";
const KanyeQuote = () => {
  const [data, loading, { error, retry }] = useGetData("https://api.kanye.rest/", { cancelable: true });
  if (loading) return <Spinner />;
  if (error) return <Button onClick={retry} label="RETRY" />;
  return (
    <div>
      <Quote>{data.quote}</Quote>
      <Button onClick={retry} label="RELOAD" />
    </Fragment>
  );
};Basic POST example
import React from "react";
import { usePostCallback } from "use-axios-react";
function userToRequest({ name, job }) {
  return {
    url: "https://reqres.in/api/users",
    data: { name, job }
  };
}
const CreateUser = () => {
  const [create, sending, { error, data }] = usePostCallback(userToRequest);
  const neo = { name: "Neo", job: "The One" };
  const morpheus = { name: "Morpheus", job: "Leader" };
  return (
    <Layout>
      <Button onClick={() => create(neo)}>Neo</Button>
      <Button onClick={() => create(morpheus)}>Morpheus</Button>
      <StatusBar sending={sending} error={error} lastUser={data} />
    </Layout>
  );
};Pagination
import React, { useState } from "react";
import { useGetData } from "use-axios-react";
const PaginatedKanyeQuotes = () => {
  const [page, setPage] = useState(1);
  const [data, loading] = useGetData(
    { url: "https://api.kanye.rest/", params: { page } },
    { cancelable: true }
  );
  if (loading) return <Spinner />;
  const prev = () => setPage(page - 1);
  const next = () => setPage(page + 1);
  return (
    <div>
      <Quote>{data.quote}</Quote>
      <div>
        <Button onClick={prev} disabled={page <= 1} label="← Prev" />
        <span className="mx-5">Page {page}</span>
        <Button onClick={next} disabled={page >= 9} label="Next →" />
      </div>
    </div>
  );
};Basic TodoMVC CRUD
import React from "react";
import axios from "axios";
import {
  provideAxiosInstance,
  useGetData,
  usePostCallback,
  useDeleteCallback,
  usePatchCallback
} from "use-axios-react";
provideAxiosInstance(
  axios.create({
    baseURL: "https://todo-backend-golang-goa.herokuapp.com"
  })
);
/**
 * Map todos to axios request configs
 */
const todoObjectToAxiosRequest = ({ id, title, order, completed }) => ({
  url: id ? `/todos/${id}` : "/todos",
  data: { title, order, completed }
});
const TodoMvcApp = () => {
  // Reusing the same mapping function for all CRUD requests
  const [create, creating, { error: createError }] = usePostCallback(todoObjectToAxiosRequest);
  const [remove, removing, { error: removeError }] = useDeleteCallback(todoObjectToAxiosRequest);
  const [update, updating, { error: updateError }] = usePatchCallback(todoObjectToAxiosRequest);
  // Re-fetch after any of actions is completed
  const allRequestsDone = !creating && !removing && !updating;
  const [todos = [], fetching, { error: fetchError }] = useGetData("/todos", {
    // The hook will re-run every time `depends` changes
    depends: [creating, removing, updating],
    // Actual request will be performed only if this is true
    willRun: allRequestsDone
  });
  if (createError || removeError || updateError || fetchError) {
    return <div>Error occurred, please reload</div>;
  }
  return (
    <Layout>
      <Header loading={creating || removing || updating || fetching}>
        <NewTodo create={create} />
      </Header>
      <TodoList todos={todos} remove={remove} update={update} loading={fetching} />
    </Layout>
  );
};Common state GET & POST
import React, { useEffect } from "react";
import { useGetData, usePostCallback } from "use-axios-react";
const CreateUser = () => {
  
  // Do an initial load
  const [users = [], loading, { error: loadError, setData: setUsers }] = useGetData("https://reqres.in/api/users");
  // We're particularly interested in the create() callback and the response data (new user data)
  const [create, creating, { error: createError, data: newUser }] = usePostCallback("https://reqres.in/api/users");
  // Update users state evey time the newUser changes
  useEffect(
    () => {
      newUser && setUsers([...users, newUser]);
    },
    [newUser]
  );
  return (
    <Layout>
      <Button onClick={() => create({})}>Create dummy user</Button>
      <span>{(loading || creating) && "Loading..."}</span>
      <span>{(loadError || createError) && "Error occurred"}</span>
      <UserList users={users} />
    </Layout>
  );
};Using custom axios instance
import React from "react";
import ReactDOM from "react-dom";
import axios from "axios";
import { provideAxiosInstance, useGetData } from "use-axios-react";
const customAxiosInstance = axios.create({
  baseURL: "https://reqres.in/api",
  transformResponse: axios.defaults.transformResponse.concat(data => {
    return data.data;
  })
});
provideAxiosInstance(customAxiosInstance);
function App() {
  const [users, loading] = useGetData("/users");
  if (loading) return "Loading...";
  return (
    <div>
      <h1>Users:</h1>
      <code>{JSON.stringify(users)}</code>
    </div>
  );
}| useGetData() | Use this one if you need to fetch data depending on some state (e.g. to fetch search results depending on search term) | 
| usePostCallback()usePutCallback()usePatchCallback()useDeleteCallback()useGetCallback() | Use this if you need to create callbacks to trigger a request programmatically | 
| useParallelPostCallback()useParallelPutCallback()useParallelPatchCallback()useParallelDeleteCallback()useParallelGetCallback() | Use this if you need to create callbacks to trigger batch requests | 
| provideAxiosInstance() | Provide a custom axios instance to use with the hooks | 
- url|axiosConfig— Refer to axios request config documentation for details
- options— The- use{...}Datahook options:
| cancelable: bool | Whether the request should be canceled on component unmount | 
| depends: [] | Hook's effect will be re-run only if one of the passed array values changes. Refer to the React useEffect(effect, depends) second argument docs to learn how it works. | 
| willRun: bool | Request will be be executed only if this option is true. This is usually an expression such as willRun: !loading | 
- result array structure is [data, loading, { error, response, retry, retriesCount, setData }]:
Where {Method} is one of the following: Post, Put, Patch, Delete, Get
- url|axiosConfig|factory— Request URL, axios config object or factory, producing an axios config object from callback args
- result array structure is [exec, loading, { error, retry, response, data, execCount, input }]:
Where {Method} is one of the following: Post, Put, Patch, Delete, Get
- axiosConfigFactory— A function producing an axios config object from callback args
- result array structure is [exec, loading, { retry, errors, responses, data, succeed, failed, execCount, input }]