在JWT过期时调度'userLogoutAction'会在'Menu.js'中抛出错误

问题描述 投票:0回答:1

为了在JWT到期后立即从我的react-admin应用程序(react-admin版本2.8.3)执行自动注销(由react应用程序触发,没有用户交互和没有API调用)。我定期检查并发送我从userLogout导入的ra-core/authActions动作,就像Logout按钮(ra-ui-materialui/auth/Logout)一样。

不幸的是ra-ui-materialui/esm/layout/Menu.js在第116行抛出错误抱怨一个未定义的属性:TypeError:无法读取null的属性'pathname'

return {
  114 |     open: state.admin.ui.sidebarOpen,
  115 |     resources: getResources(state),
> 116 |     pathname: state.router.location.pathname
  117 |   };

使用Chrome redux工具,我可以看到redux-store router的属性location为null。

在JWT过期后有更好的方法来注销用户吗?如果没有,我需要做些什么来使userLogout行动起作用?

也许有人可以解释为什么Menu.js似乎与userLogout行动紧密耦合。

我的组件的源代码如下所示:

import React from 'react'
import { connect } from 'react-redux'
import { userLogout } from 'react-admin'
import { hasValidJWT } from '../authProvider'

class PeriodicAuthCheck extends React.Component {
    constructor(props) {
        super(props)
        // interval in seconds
        this.interval = 60
    }

    authCheck(loginPath, dispatchAction) {
        if (!hasValidJWT()) {
            if (window.location.hash !== `#${loginPath}`) {
                console.log(`JWT has expired, redirecting to ${loginPath}`)
                /*
                  this is my workaround:
                  window.location.replace(`/#${loginPath}`)
                */
                dispatchAction(loginPath)
            }
        }
    }

    componentDidMount() {
        this.authCheck(this.props.loginPath, this.props.logout)
        this.interval = setInterval(this.authCheck, this.interval * 1000, this.props.loginPath, this.props.logout)
    }

    componentWillUnmount() {
        if (this.interval) {
            clearInterval(this.interval)
            this.interval = undefined
        }
    }

    render() {
        return null
    }
}

const mapDispatchToProps = dispatch => {
    return {
        logout: (loginPath) => dispatch(userLogout(loginPath))
    }
}

export default connect(null, mapDispatchToProps)(PeriodicAuthCheck)

先感谢您!托马斯

react-admin
1个回答
0
投票

您可以更新dataProvider的httpClient。对我而言,只有在我明确删除了令牌并将浏览器转发到登录表单时才有效。

if (401 === responseStatusCode) {
    localStorage.removeItem('token');
    window.location = '/#/login';
}

它不是最好的解决方案,但它可以完成工作。很想看到这个问题的其他解决方案。

© www.soinside.com 2019 - 2024. All rights reserved.