When using Jest for unit testing, there are several common approaches to handle localStorage. Since localStorage is a browser API and Jest runs in a Node.js environment, localStorage is not available by default. Here are several approaches to handle this situation:
1. Using Mock
The most common approach is to use Jest's mocking feature to create a fake localStorage. This allows you to simulate localStorage behavior without relying on a real browser environment. This approach is simple and provides strong control, making it easy to test various edge cases and error handling.
Example code:
javascript// Set up the mock in your test file beforeAll(() => { global.localStorage = { getItem: jest.fn(), setItem: jest.fn(), removeItem: jest.fn(), clear: jest.fn() }; }); // Test example test('should set item in localStorage', () => { const key = 'user'; const value = 'John Doe'; localStorage.setItem(key, value); expect(localStorage.setItem).toHaveBeenCalledWith(key, value); });
2. Using Third-Party Libraries
Some third-party libraries like jest-localstorage-mock can automatically handle localStorage mocking for you. These libraries typically provide a complete localStorage mock, correctly handling stored data and responding to method calls.
How to use:
First, you need to install this library:
bashnpm install --save-dev jest-localstorage-mock
Then, add it to your Jest configuration file (e.g., jest.config.js):
javascriptsetupFiles: ["jest-localstorage-mock"]
Example code:
javascript// No need to manually mock; you can use it directly test('should store the correct value in localStorage', () => { localStorage.setItem('info', 'test'); expect(localStorage.setItem).toHaveBeenCalledWith('info', 'test'); expect(localStorage.__STORE__['info']).toBe('test'); });
3. Rewriting the Global Object
If you don't want to use other libraries, you can simulate it by simply adding localStorage to the global object.
Example code:
javascriptglobal.localStorage = { getItem: function(key) { return this.store[key] || null; }, setItem: function(key, value) { this.store[key] = value.toString(); }, removeItem: function(key) { delete this.store[key]; }, clear: function() { this.store = {}; }, store: {} }; // Use the rewritten localStorage for testing test('should retrieve the correct item from localStorage', () => { localStorage.setItem('theme', 'dark'); expect(localStorage.getItem('theme')).toBe('dark'); });
Summary
The above describes three approaches to handle localStorage. You can choose the most suitable method based on your needs and the complexity of your testing environment. Mocking is the most flexible approach, while using third-party libraries can make the code more concise and maintainable.