-
-
Notifications
You must be signed in to change notification settings - Fork 1.2k
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Unable to mock React.useReducer because of module already loaded. (in i18next react) #4970
Comments
Finally I managed reproduce problem - https://stackblitz.com/~/github.com/hadson172/vitest-err?startScript=test |
Your link doesn't seem to work for me. Is it a private repository? |
@sheremet-va Its public. You can get it here - https://github.com/hadson172/vitest-err |
@hadson172 Hello mate. Any luck with this issue? |
I think the reproduction showing an error is an intended behavior of Vitest with the rational described in the error message, so that doesn't necessary serve as a bug report reproduction. My understanding is that such use case of We expect such usage of It would help if someone can provide a reproduction with something like having |
@hi-ogawa Its not hard to imagine situation where user has to mock one of the function from module loaded in setup.js (like in my case mock useReducer to unit testing some components). Currently we found workaround for this. In each of our test files (and there is 10+ of them) we have this few lines on the top of file:
It works fine, it adds some overhead for these few tests. So instead of above sniped we would have
When it comes to current solution. We tried to make some reusable function to not to copy-pase 10 lines of code in each to the tests, something like this:
then in each of 10 tests files where we have to resetAllmodules and setup them again to mock react
But when calling mockUseReducer we are getting exception with some "import_v9" in the name or something like this. It would be really appreciated if there would be some simpler/easier solusion for this case which does not put overhead of execution of setup.js again. |
@hadson172 Thanks for providing the context. I wasn't aware that this issue is motivated by the migration from jest. I cannot give quick suggestions to help your scenario right now but I see that there are some pain points and I appreciate your feedback on current limitation of mocking. |
@hadson172 To follow up what Vitest can improve (or to find simpler workaround), it would be still helpful if you can provide a "reproduction" to illustrate your current workaround. From the pseudo code with |
I would like to add a similar context. In our case we want to mock the
This worked fine so far. Unfortunately, we now also get this "Cannot mock "react-router-dom" because it is already loaded by" message since we have some utility files also importing "react-router-dom". Like a Router wrapping utility:
or the In my opinion, these utility methods/hooks are not comparable to setup files so I'm now quite clueless how to approach this scenario. |
We had a similar problem after updating vitest. The only way that worked for me to work around this was to move many of the // setupTest file
vi.mock("react-router-dom", async () => {
const actual = await vi.importActual<typeof import("react-router-dom")>(
"react-router-dom"
);
return {
...actual,
useHistory: vi.fn().mockImplementation(actual.useHistory),
};
}); And then in the test files I can import // unit test file
import { useHistory } from "react-router-dom";
import { Mock } from "vitest";
const mockHistoryPush = vi.fn();
(useHistory as Mock).mockReturnValue({
push: mockHistoryPush,
}); But this also meant that I was forced to change the vitest config settings, because if either "mockReset" or "restoreMocks" are set to true, the tests were broken again. |
If it worked before and doesn't work anymore, then it's a bug. |
Since we just stumbled upon this by accidentally updating vitest I just decided to roll back the vitest version and keep the older one running. But of course, that's not a solution. I'm confused by the motivation to introduce this new error. From the corresponding issue report I get that mocking was silently just not applied if that module to mock was already loaded. But wouldn't that mean that this setup here:
would result in a failure of a test which |
It's not enough to say yes or no, this is not a sufficient reproduction. The only way this would've worked when the module was already loaded is if it was imported again by modules in the test file that were not evaluated yet, but it is impossible to know when mocking because it is executed before all imports. |
I just gave another approach a try. That worked out for me. |
Describe the bug
Hi.
Our setup for vitest looks like this:
vitest.setup.ts
<- here we are loadining translations using i18next reactWe have code which tests for components which are using
React.useReducer
.We want to mock "react" module and provide implementation for
React.useReducer(...)
(for rest importOriginal)Then we are getting this error - https://vitest.dev/guide/common-errors#cannot-mock-mocked-file-js-because-it-is-already-loaded
Using 'react' inside setup make it impossible to mock react modules inside any of the tests.
We can
vi.resetModules()
in config file orvi.hoisted(() => vi.resetModules())
inside test file, but then config loaded by i18next (all translations) are reset as well. I triedvi.domock('react')
as well but does not work.Is there any solution for this?
Reproduction
From some unknown reason this issue is not reproducible with clean repo all the time (sometimes it work sometimes this exception is thrown). I would be happy to provide more details or try to reproduce this with someone's help.
Edit: https://stackblitz.com/~/github.com/hadson172/vitest-err?startScript=test
System Info
Used Package Manager
npm
Validations
The text was updated successfully, but these errors were encountered: