How to use React SDK with axios

I have a frontend app using @kinde-oss/kinde-auth-react. When I make requests to my backend API server, I want to use axios (axios-http.com) to make the HTTP calls with my Kinde access token. The most natural way of adding the access token to my axios calls is to configure axios with an interceptor which will attempt to retrieve an access token and, if successful, add it as a header. The problem is that the getToken function is provided by useKindeAuth which is a React Hook. But I create my axios instance outside of any React page (in a plain .tsx file) and simply import it when needed. Since my axios instance is created outside of any React component, I'm not able to use the useKindeAuth hook there and so I'm not able to get a reference to the getToken function. So I can't currently configure Axios with an access token. Has anyone come across this problem? Or does anyone have a different suggestion for how to integrate kinde-auth-react with Axios?
3 Replies
onderay
onderay4mo ago
Great question and thanks for providing a picture of your setup. Never come across Axios before, so the below advice is generalised. I can ask the team next week if we have any other advice for you. Integrating @kinde-oss/kinde-auth-react with Axios while respecting the constraints of using React hooks can be a bit tricky but can be achieved by following a structured approach. Here's a way to do it: 1. Create a function to fetch the token using useKindeAuth: This function will be a custom hook that wraps useKindeAuth and provides a method to get the token. 2. Set up Axios interceptors to use the token: Configure Axios to use an interceptor that fetches the token and adds it to the headers. 3. Create an Axios instance: This instance will be used across your app for making API calls. Here’s how you can do it: Step 1: Create a function to fetch the token Create a custom hook that uses useKindeAuth to get the token.
// src/hooks/useFetchToken.ts
import { useKindeAuth } from '@kinde-oss/kinde-auth-react';

export const useFetchToken = () => {
const { getToken } = useKindeAuth();

const fetchToken = async () => {
try {
const token = await getToken();
return token;
} catch (error) {
console.error('Error fetching token:', error);
throw error;
}
};

return { fetchToken };
};
// src/hooks/useFetchToken.ts
import { useKindeAuth } from '@kinde-oss/kinde-auth-react';

export const useFetchToken = () => {
const { getToken } = useKindeAuth();

const fetchToken = async () => {
try {
const token = await getToken();
return token;
} catch (error) {
console.error('Error fetching token:', error);
throw error;
}
};

return { fetchToken };
};
Step 2: Configure Axios with interceptors Set up an Axios instance and configure it with interceptors to use the token fetched by the custom hook.
// src/api/axiosInstance.ts
import axios from 'axios';

const axiosInstance = axios.create({
baseURL: 'https://your-api-base-url.com',
});

export const setAxiosInterceptors = (fetchToken: () => Promise<string>) => {
axiosInstance.interceptors.request.use(async (config) => {
const token = await fetchToken();
if (token) {
config.headers.Authorization = `Bearer ${token}`;
}
return config;
}, (error) => {
return Promise.reject(error);
});
};

export default axiosInstance;
// src/api/axiosInstance.ts
import axios from 'axios';

const axiosInstance = axios.create({
baseURL: 'https://your-api-base-url.com',
});

export const setAxiosInterceptors = (fetchToken: () => Promise<string>) => {
axiosInstance.interceptors.request.use(async (config) => {
const token = await fetchToken();
if (token) {
config.headers.Authorization = `Bearer ${token}`;
}
return config;
}, (error) => {
return Promise.reject(error);
});
};

export default axiosInstance;
Step 3: Set up Axios interceptors in a React component You need to call the function to set up the Axios interceptors within a React component where you can use the useFetchToken hook. This can be done in a top-level component like App.
// src/App.tsx
import React, { useEffect } from 'react';
import { useFetchToken } from './hooks/useFetchToken';
import { setAxiosInterceptors } from './api/axiosInstance';
import axiosInstance from './api/axiosInstance';

const App: React.FC = () => {
const { fetchToken } = useFetchToken();

useEffect(() => {
setAxiosInterceptors(fetchToken);
}, [fetchToken]);

// Your app's other code here...

return (
<div>
{/* Your app components */}
</div>
);
};

export default App;
// src/App.tsx
import React, { useEffect } from 'react';
import { useFetchToken } from './hooks/useFetchToken';
import { setAxiosInterceptors } from './api/axiosInstance';
import axiosInstance from './api/axiosInstance';

const App: React.FC = () => {
const { fetchToken } = useFetchToken();

useEffect(() => {
setAxiosInterceptors(fetchToken);
}, [fetchToken]);

// Your app's other code here...

return (
<div>
{/* Your app components */}
</div>
);
};

export default App;
Usage Now, you can use axiosInstance throughout your application for making API calls. The token will be automatically added to the headers of each request.
// src/components/SomeComponent.tsx
import React, { useEffect } from 'react';
import axiosInstance from '../api/axiosInstance';

const SomeComponent: React.FC = () => {
useEffect(() => {
const fetchData = async () => {
try {
const response = await axiosInstance.get('/your-endpoint');
console.log(response.data);
} catch (error) {
console.error('Error fetching data:', error);
}
};

fetchData();
}, []);

return (
<div>
{/* Component code */}
</div>
);
};

export default SomeComponent;
// src/components/SomeComponent.tsx
import React, { useEffect } from 'react';
import axiosInstance from '../api/axiosInstance';

const SomeComponent: React.FC = () => {
useEffect(() => {
const fetchData = async () => {
try {
const response = await axiosInstance.get('/your-endpoint');
console.log(response.data);
} catch (error) {
console.error('Error fetching data:', error);
}
};

fetchData();
}, []);

return (
<div>
{/* Component code */}
</div>
);
};

export default SomeComponent;
By following these steps, you ensure that your Axios instance is configured with the appropriate token without violating the rules of React hooks.
Geoff Ferrari
Geoff FerrariOP4mo ago
Thanks @Andre @ Kinde - this approach seems to do the trick! Much appreciated. In case it's helpful to anyone else, I adjusted the first function definition as follows to prevent some inscrutable axios errors: // src/hooks/useFetchToken.ts import { useKindeAuth } from '@kinde-oss/kinde-auth-react'; export const useFetchToken = () => { const { getToken } = useKindeAuth(); const fetchToken = async () => { try { const token = await getToken(); return token; } catch (error) { return null; } }; return { fetchToken }; };
onderay
onderay4mo ago
Yay @Geoff Ferrari so great to hear and thanks for the extra detail.
Want results from more Discord servers?
Add your server