用 Jest 反应单元测试 - 模拟 localStorage 的问题
Posted
技术标签:
【中文标题】用 Jest 反应单元测试 - 模拟 localStorage 的问题【英文标题】:React unit test with Jest - issue on simulating localStorage 【发布时间】:2018-12-28 13:56:24 【问题描述】:我在对简单组件进行单元测试时遇到了问题(这里更加简化了):
import React, Component from 'react';
import Logout from '../auth/Logout';
import logoutUser from '../../actions/auth';
export default class Navbar extends Component
render()
const dispatch, isAuthenticated = this.props;
if (isAuthenticated)
logStatus = <Logout onLogoutClick=() => dispatch(logoutUser()) />;
else
logStatus = (
<Link to="/login/">
<Button>Login</Button>
</Link>
);
return (
<AppBar>
logStatus
</AppBar>
);
在import logoutUser from '../../actions/auth';
我在localStorage
上有一个函数 removeItem。我不会将它用于我的测试,但这就是我有错误的地方。
我的测试是:
test('Navbar test series', () =>
//Enzyme testing
it('show the login button', () =>
const wrapper = shallow(<Navbar isAuthenticated=true />);
expect(wrapper.find(Login)).to.have.length(1);
);
);
我明白了:
ReferenceError: localStorage is not defined
at Object.<anonymous> (src/axios/axios.js:8:15) [I don't know why this is here...]
at Object.<anonymous> (src/actions/auth.js:89:38) [my logoutUser using localStorage is here ]
at Object.<anonymous> (src/components/UI/Navbar.js:3:13)
at Object.<anonymous> (src/components/UI/Navbar.test.js:2:15)
像这里建议的那样做How do I deal with localStorage in jest tests?:
var localStorageMock = (function () [...])();
Object.defineProperty(window, 'localStorage', value: localStorageMock );
没有帮助。
我不明白的是我什至没有打电话给dispatch(logoutUser())
那么为什么要尝试访问 localStorage 呢?问题是由于 redux through dispatch 引起的吗?
非常感谢您的帮助!
编辑1: 注销组件:
import React from 'react';
import Button from '@material-ui/core/Button';
const Logout = props => (
<Button onClick=() => props.onLogoutClick() color="secondary">LOGOUT</Button>
);
export default Logout;
以及来自 actions/auth.js 和 logoutUser() 的代码:
export function logoutUser()
return dispatch =>
dispatch(requestLogout());
localStorage.removeItem('token');
dispatch(receiveLogout());
;
【问题讨论】:
How do I deal with localStorage in jest tests?的可能重复 我不这么认为,我尝试使用您链接的帖子“模拟”localStorage,但它没有改变。我认为问题更多在于为什么首先调用这个 logoutUser 函数? 你能把Logout
组件的代码贴出来吗?
完成,我添加了注销组件。非常非常简单。
我发现我只是通过导入我的组件就出现了这个错误。即使没有变浅......奇怪,我会挖掘它。
【参考方案1】:
您可以添加测试文件
global.localStorage =
getItem: () => undefined,
;
test('Navbar test series', () =>
//Enzyme testing
it('show the login button', () =>
const wrapper = shallow(<Navbar isAuthenticated=true />);
expect(wrapper.find(Login)).to.have.length(1);
);
);
【讨论】:
再一次,我已经尝试使用这个精确的 sn-p 来模拟 localStorage ***.com/a/32911774/1565738,这不是这里的问题。无论如何谢谢:) 完成,我已经从 auth.js 添加了 logoutUser() 函数【参考方案2】:您是否尝试过完全为该测试模拟 ../../actions/auth
?
jest.setMock('../../actions/auth', () => (
logoutUser: jest.fn()
))
【讨论】:
我刚试过,我仍然被那个 localStorage 错误阻止:) 不过这是个好主意! 有点离题,但你应该试试react-testing-library。浅渲染是一种真正的痛苦。在我的测试中,我用global.localStorage = setItem: jest.fn() ;
模拟localStorage
,它就成功了。希望你能找到解决办法!【参考方案3】:
所以解决方案是:
at Object.<anonymous> (src/axios/axios.js:8:15) [I don't know why this is here...]
我在运行时使用 localstorage 找到了一个 const。只要把它放在一个条件下,它就解决了这个问题。
感谢大家的努力,这是我的错误:-(
【讨论】:
但是为什么没有调用模拟实现呢?您是通过 window.localstorage 还是其他方式引用它? 因为const token = localStorage.get[...]
是在我的 axios/axios.js 的根目录中调用的,因此调用了 import
链。所以在 localStorage 的模拟实现之前。
即使我在第一行使用模拟测试过一次,但我想我做得很糟糕......以上是关于用 Jest 反应单元测试 - 模拟 localStorage 的问题的主要内容,如果未能解决你的问题,请参考以下文章