Reputation: 1762
I have this code:
import axios, {AxiosError} from "axios";
try {
some request
} catch(err:AxiosError) {
console.log(error.response) // Doesn't work
console.log(error.response?.data?.message) // Doesn't work
if(error.response?.data?.statusCode === 401) {
logout()
}
}
I can't check the status code inside because of TypeScript. How do I describe the error type correctly without resorting to the any
type?
I couldn't find how people handle this error in TypeScript, maybe I'm missing something.
Upvotes: 29
Views: 39340
Reputation: 3299
This also depends on the axios version, in my case (axios 0.24.0) I could not use e instanceof AxiosError
. So I use AxiosStatic.isAxiosError
.
import AxiosStatic from 'axios';
try {
await onPostingSomething();
} catch (e: unknown) {
if (!AxiosStatic.isAxiosError(e)) {
throw e;
}
if (e.response?.status === 401) {
console.log('errors.unauthorized');
} else {
console.log('errors.otherErrors');
}
}
Upvotes: 2
Reputation: 321
The best way to do this, is to explicitly check for the Error you expect to get. In this case, if you want to check if it's an AxiosError do the following:
import axios, {AxiosError} from "axios";
try {
some request
} catch(err) {
if (err instanceof AxiosError) {
console.log(error.response);
if(error.response?.data?.statusCode === 401) {
logout();
}
} else {
// it was some other kind of error, handle it appropriately
}
By checking if it's an instance of AxiosError, in the if block we narrow the type of the err variable to be AxiosError. In the examples where people are using as
to cast the Error, that could be incorrect because the error might NOT be an AxiosError but some other kind of error, which would result in a runtime error.
Upvotes: 16
Reputation: 5707
I encountered this as well, you can do it and @David-Easley hints at but does not provide the syntax.
If you surround the error variable with brackets, you can then set the type.
Change it from;
.catch(error => {
to;
.catch((error:AxiosError) => {
That gives intellisense on the error object.
Just make be sure that you'll always get that error type passed.
Upvotes: 0
Reputation: 1383
Alternatively, rather than use a regular catch
block, restructure the code to use the Promise.catch(error)
method. You can then quote the type of the parameter as (error: AxiosError)
or just leave TypeScript to infer the type.
e.g., assuming "some request" is a GET request, it might look like this:
import axios from 'axios';
await (async () => {
axios
.get('some-url')
.then((response) => {
// Some handler logic
})
.catch((error) => {
console.log(error.response); // now works
console.log(error.response?.data?.message); // now works
if (error.response?.data?.statusCode === 401) {
logout()
}
});
})();
Upvotes: 0
Reputation: 85201
Typescript has no way to verify which types of values might be thrown by arbitrary code. So up until recently, the error had to be of type any
.
} catch (err: any) {
From version 4.0 onward, typescript also allows unknown
.
} catch (err: unknown) {
Anything else is not supported. If you want something more specific, you will either need to write code to narrow down what type of thing was thrown, or you will need to use a type assertion. Keep in mind that a type assertion is a way to tell typescript "i know more than you do, so don't check my work". If you assert that it's an AxiosError, but it could actually be something else, typescript cannot point out that mistake to you.
catch (err: unknown) {
const error = err as AxiosError;
//...
}
Upvotes: 33