Projekt

Obecné

Profil

Stáhnout (2.51 KB) Statistiky
| Větev: | Tag: | Revize:
1
import axios from 'axios'
2
import { Store } from 'redux'
3
import config from '../config/conf'
4
import { AppStore } from '../features/redux/store'
5

    
6
let store: AppStore // this will get injected later
7

    
8
export const injectStore = (_store: Store) => {
9
    store = _store
10
}
11

    
12
// Error
13
export interface ApiError {}
14

    
15
const createBaseInstance = () =>
16
    axios.create({
17
        baseURL: config.baseUrl,
18
    })
19

    
20
const axiosInstance = createBaseInstance()
21

    
22
axiosInstance.interceptors.request.use(
23
    (config) => {
24
        const accessToken = store.getState().user.accessToken // get the access token from the store
25
        if (accessToken) {
26
            // @ts-ignore
27
            // this will always be defined, axios developers are just lazy to provide better Typescript types
28
            config.headers['Authorization'] = accessToken as string
29
        }
30

    
31
        return config
32
    },
33
    (err) => {
34
        Promise.reject(err)
35
    }
36
)
37

    
38
axiosInstance.interceptors.response.use(
39
    (res) => res,
40
    async (err) => {
41

    
42
        const originalConfig = err.config
43

    
44
        // Original URL might be login in which case we don't want to refresh the access token
45
        // Since the user just failed to log in and no token expired
46
        if (originalConfig.url === '/login' || !err.response) {
47
            return Promise.reject(err)
48
        }
49

    
50
        // We need to set the refresh token in the auth header
51
        const oldRefreshToken = store.getState().user.refreshToken
52

    
53
        // If there is no refresh token we simply log the user out
54
        if (!oldRefreshToken) {
55
            store.dispatch({ type: 'user/logout' })
56
            return Promise.reject(err)
57
        }
58

    
59
        // Set this to retry the request that failed
60
        originalConfig.retry = true
61

    
62
        // Try refreshing the JWT
63
        try {
64
            const refreshConfig = createBaseInstance()
65
            // @ts-ignore
66
            refreshConfig.headers['Authorization'] = oldRefreshToken as string
67

    
68
            // Send the request
69
            const { data } = await axiosInstance.get('/refreshToken')
70

    
71
            const { accessToken, refreshToken } = data
72

    
73
            // Set the new tokens
74
            store.dispatch({
75
                type: 'user/refreshTokens',
76
                payload: { accessToken, refreshToken },
77
            })
78

    
79
            return axiosInstance(originalConfig)
80
        } catch (err: any) {
81
            // If the refresh token fails we log the user out
82
            store.dispatch({ type: 'user/logout' })
83
            return Promise.reject(err)
84
        }
85
    }
86
)
87

    
88
export default axiosInstance
    (1-1/1)