在Jest测试中,我一直得到“localStorage is not defined”,这是有意义的,但我的选项是什么?碰壁。


当前回答

如果使用create-react-app,文档中解释了一个更简单和直接的解决方案。

创建src/setupTests.js,并把这个放在里面:

const localStorageMock = {
  getItem: jest.fn(),
  setItem: jest.fn(),
  clear: jest.fn()
};
global.localStorage = localStorageMock;

Tom Mertz的评论如下:

然后,您可以通过执行以下操作来测试localStorageMock的函数是否被使用

expect(localStorage.getItem).toBeCalledWith('token')
// or
expect(localStorage.getItem.mock.calls.length).toBe(1)

在你的测试中,如果你想确保它被调用。查看https://facebook.github.io/jest/docs/en/mock-functions.html

其他回答

这对我很有效,

delete global.localStorage;
global.localStorage = {
getItem: () => 
 }

2021年,打印稿

class LocalStorageMock {
  store: { [k: string]: string };
  length: number;

  constructor() {
    this.store = {};
    this.length = 0;
  }

  /**
   * @see https://developer.mozilla.org/en-US/docs/Web/API/Storage/key
   * @returns
   */
  key = (idx: number): string => {
    const values = Object.values(this.store);
    return values[idx];
  };

  clear() {
    this.store = {};
  }

  getItem(key: string) {
    return this.store[key] || null;
  }

  setItem(key: string, value: string) {
    this.store[key] = String(value);
  }

  removeItem(key: string) {
    delete this.store[key];
  }
}

export default LocalStorageMock;

然后你可以用它

global.localStorage = new LocalStorageMock();

在这个网站的帮助下,我们找到了答案:https://groups.google.com/forum/#!主题/ jestjs / 9 ephunwvytg

设置一个包含以下内容的文件:

var localStorageMock = (function() {
  var store = {};
  return {
    getItem: function(key) {
      return store[key];
    },
    setItem: function(key, value) {
      store[key] = value.toString();
    },
    clear: function() {
      store = {};
    },
    removeItem: function(key) {
      delete store[key];
    }
  };
})();
Object.defineProperty(window, 'localStorage', { value: localStorageMock });

然后将以下行添加到包中。json在你的Jest配置

:“setupTestFrameworkScriptFile PATH_TO_YOUR_FILE”,

答:

目前(7月22日)localStorage不能像你通常会被嘲笑或监视,并在创建-反应-应用程序文档中概述。这是由于jsdom中所做的更改。你可以在jest和jsdom问题跟踪器中读到它。

作为一种变通方法,你可以监视原型:

// does not work:
jest.spyOn(localStorage, "setItem");
localStorage.setItem = jest.fn();

// either of these lines will work, different syntax that does the same thing:
jest.spyOn(Storage.prototype, 'setItem');
Storage.prototype.setItem = jest.fn();

// assertions as usual:
expect(localStorage.setItem).toHaveBeenCalled();

关于监视原型机的注意事项:

监视实例使您能够观察和模拟特定对象的行为。

另一方面,监视原型,将同时观察/操作该类的每个实例。除非您有一个特殊的用例,否则这可能不是您想要的。

但是,在本例中没有区别,因为localStorage只存在一个实例。

不幸的是,我在这里找到的解决方案对我不起作用。

所以我在看Jest GitHub的问题,发现了这个帖子

得到最多好评的解决方案是:

const spy = jest.spyOn(Storage.prototype, 'setItem');

// or

Storage.prototype.getItem = jest.fn(() => 'bla');