I ended up ditching the default export:

// UniqueIdGenerator.js
export const uniqueIdGenerator = () => Math.random().toString(36).substring(2, 8);

And then I could use and spy it like this:

import * as UniqueIdGenerator from './UniqueIdGenerator';
// ...
const spy = jest.spyOn(UniqueIdGenerator, 'uniqueIdGenerator');

Some recommend wrapping them in a const object, and exporting that. I suppose you can also use a class for wrapping.

However, if you can't modify the class there's still a (not-so-nice) solution:

import * as UniqueIdGenerator from './UniqueIdGenerator';
// ...
const spy = jest.spyOn(UniqueIdGenerator, 'default');
Answer from thisismydesign on Stack Overflow
🌐
Chakshunyu
chakshunyu.com › blog › how-to-spy-on-a-named-import-in-jest
How To Spy On An Exported Function In Jest | A technical blog by Chak Shun Yu
September 3, 2021 - import * as moduleApi from '@module/api'; // Somewhere in your test case or test suite jest.spyOn(moduleApi, 'functionToMock').mockReturnValue({ someObjectProperty: 42 }); One caveat to this approach is that there’s the chance that you will run across a TypeError: Cannot redefine property: functionToMock at Function.defineProperty (<anonymous>). In that case, you can’t use the spyOn function to mock the exported function.
Discussions

spy on pure functions exported as const
Whether or not you can spy on these functions depends on what module type your app is targeting. If it is ES6, you do a default export in your helper file and spy on the functions via spyOn(defaultImport, ‘helperFn’). You cannot just spy on the function itself, since ES6 modules export read-only references to their exposed values (i.e., you can’t overwrite the reference with a spy). If you target commonjs, you can get away with it because the references are not actually read-only at runtime. You need to spy on the reference before your component/service that you’re testing is initialized, so before the TestBed calls for example. At least, this is what my app has experienced recently. More on reddit.com
🌐 r/Angular2
11
2
March 12, 2021
Use `jest.spyOn` on an exported function from a Node module
const childProcess = require('child_process'); const spySpawnSync = jest.spyOn(childProcess, 'spawnSync').mockImplementation(); This allows us to use spySpawnSync to check what arguments it was last called with, like so: ... However, this is not possible with Node modules that export a function, ... More on stackoverflow.com
🌐 stackoverflow.com
node.js - Use `jest.spyOn` on an exported function from a ...
const childProcess = require('child_process'); const spySpawnSync = jest.spyOn(childProcess, 'spawnSync').mockImplementation(); This allows us to use spySpawnSync to check what arguments it was last called with, like so: ... However, this is not possible with Node modules that export a function, ... More on stackoverflow.com
🌐 stackoverflow.com
Cannot spy on individual functions that are individually exported
Having done a lot of research I cannot find a way to mock functions that are exported with no parent object. For example I'm trying to mock functions exported the following way: module.exports ... More on github.com
🌐 github.com
69
August 22, 2017
🌐
Medium
medium.com › @DavideRama › mock-spy-exported-functions-within-a-single-module-in-jest-cdf2b61af642
Mock/Spy exported functions within a single module in Jest | by Davide Ramaglietta | Medium
February 14, 2020 - } export function bar () { foo() } You want to assert that when executing bar() , it will also fire the execution of foo(). This would seem to be a classic situation for using Jest functionalities spyOn or mock.
🌐
JavaScript in Plain English
javascript.plainenglish.io › jest-spy-on-an-exported-function-d8fc91793876
Jest Spy on an Exported Function. The spyOn utility in Jest is incredibly… | by Shaurya Kalia | JavaScript in Plain English
April 2, 2024 - Jest Spy on an Exported Function The spyOn utility in Jest is incredibly versatile, enabling you to monitor, track, and even replace the behavior of functions. However, applying this to a named …
🌐
DEV Community
dev.to › tylerlwsmith › override-functions-in-individual-tests-using-jest-dp5
Mock functions in individual tests using Jest - DEV Community
August 5, 2024 - The jest.spyOn() method allows Jest to record calls to a method on an object and provide its own replacement. This only works on objects, and we can use it because our module is exporting an object that contains our function.
🌐
Reddit
reddit.com › r/angular2 › spy on pure functions exported as const
r/Angular2 on Reddit: spy on pure functions exported as const
March 12, 2021 -

Lately I've been writing pure functions more and more in my code, they convey meaning very well, are easy to write and test

Now that most of my logic is in pure function I tend to write them outside of components because they don't depend on the state of the component.

Example getUsername is pure and not used in the template and as such doesn't really need to be a method of the component.

@Component({selector: ..., templateUrl: ..., styleUrls: ...})
export class UserComponent implements OnInit {
    @Input() user: User;
    username: string

    ngOnInit() {
        this.username = getUsername(this.user);
    }
}

export const getUsername = (user: User): string => `${user.firstname} ${user.lastname}`;

When I have too many of these pure functions I sometimes move them to a helper file.

Everything works perfectly, except when I try to spy on them for unit testing. At this point jasmine refuses to spy on them (relevant github issue)

What do you guys think I should do ? Move my pure functions to method of components ? Change my helper files into services eventhough they don't use any state ?

I feel like I have to remove relevant information from my code (purity of the functions) for the sole reason of unit testing and I don't like it

Edit: spying on an exported function used to work but stopped working with Angular 9, cf this github issue

🌐
DhiWise
dhiwise.com › post › grow-testing-efficiency-with-jest-spyon-for-default-exports
A Deep Dive into Jest spyOn for Default Exports
April 30, 2025 - It returns a Jest mock function that can be used to inspect calls to the function. Spying on a default export in Jest can be a bit tricky since you need to account for the way the default export is handled within the module system.
🌐
Stack Overflow
stackoverflow.com › questions › 57620224
Use `jest.spyOn` on an exported function from a Node module
const childProcess = require('child_process'); const spySpawnSync = jest.spyOn(childProcess, 'spawnSync').mockImplementation(); This allows us to use spySpawnSync to check what arguments it was last called with, like so: ... However, this is not possible with Node modules that export a function, such as with the execa package.
Find elsewhere
🌐
kaliaverse
shauryakalia.com › jest-spy-on-an-exported-function-d8fc91793876
Jest Spy on an Exported Function - Shaurya Kalia
February 10, 2025 - You might wonder how to correctly use jest.spyOn to monitor this function, especially what argument to pass first. Jest’s spyOn expects an object or module as the first parameter, and the name of the method to spy on as the second. The trick to effectively monitoring a named export is to import the entire module’s contents as an object, then pass this object into jest.spyOn.
🌐
Stack Overflow
stackoverflow.com › questions › 57619182 › use-jest-spyon-on-an-exported-function-from-a-node-module
node.js - Use `jest.spyOn` on an exported function from a ...
const childProcess = require('child_process'); const spySpawnSync = jest.spyOn(childProcess, 'spawnSync').mockImplementation(); This allows us to use spySpawnSync to check what arguments it was last called with, like so: expect(spySpawnSync).lastCalledWith('ls'); However, this is not possible with Node modules that export a function, such as with the execa package.
🌐
Mercedes Bernard
mercedesbernard.com › blog › jest-mocking-strategies
Jest Mocking Strategies | Mercedes Bernard
July 12, 2020 - For true mocking, we use mockImplementation to provide the mock function to overwrite the original implementation. import example from "../defaultObject"; const mockExpected = "mock value"; jest.spyOn(example, "getValue").mockImplementation(jest.fn(() => mockExpected)); it("returns the expected value", () => { const actual = example.getValue(); expect(actual).toEqual(mockExpected); }); In this example, the library exports a named object that has a property for the function we want to mock.
🌐
Developright
developright.co.uk › posts › mocking-functions-or-methods-with-jest.html
Mocking & Spying with Jest SpyOn | DevelopRight.co.uk
December 30, 2022 - // import package import randomLibrary from './libraries/random'; // inside test (shortened for brevity) jest.spyOn(randomLibrary, 'functionOrMethod'); The following will mock all of randomLibrary's exports with the default jest.fn() implementation.
🌐
GitHub
github.com › jasmine › jasmine › issues › 1414
Cannot spy on individual functions that are individually exported · Issue #1414 · jasmine/jasmine
August 22, 2017 - export function thing(event) {}; When importing these into a test file I try importing like this: import {thing} from 'emvio-util-responses; //call some function that calls thing() spyOn(???, 'thing').and.returnValue({}); expect(???.thing)....
Author   jasmine
🌐
Erikmartinjordan
erikmartinjordan.com › spy-non-default-function-react
Spy on non-default function using Jest's spyOn() — Erik Martín Jordán
February 21, 2022 - import * as Math from './Math.js' test('Mocking up default and non-default', async() => { // Spying on a non default exported function jest.spyOn(Math, 'sub').mockUpImplementation(() => 5) // Spying on the default exported function jest.spyOn(Math, 'default').mockImplementation(() => 5) }) Hi, I'm Erik, an engineer from Barcelona.
🌐
Jest
jestjs.io › mock functions
Mock Functions · Jest
May 7, 2026 - the return type of jest.spyOn()). __utils__/setDateNow.ts · import {jest} from '@jest/globals'; export function setDateNow(now: number): jest.Spied<typeof Date.now> { return jest.spyOn(Date, 'now').mockReturnValue(now); } import {afterEach, expect, type jest, test} from '@jest/globals'; import {setDateNow} from './__utils__/setDateNow'; let spiedDateNow: jest.Spied<typeof Date.now> | undefined = undefined; afterEach(() => { spiedDateNow?.mockReset(); }); test('renders correctly with a given date', () => { spiedDateNow = setDateNow(1_482_363_367_071); // ...
🌐
GitHub
github.com › swc-project › swc-node › issues › 610
Can't use jest spies for functions in same file · Issue #610 · swc-project/swc-node
September 21, 2021 - // myFile.ts export const addOne = (x: number): string => `${x + 1}` export const someFunc = (x: number): string => `The answer is : ${addOne(x)}` And I want to test the two functions separately and therefore mock addOne: import * as myFile from './myFile' describe('someFunc', () => { const expected = '2'; const addOneSpy = jest.spyOn(myFile, 'addOne').mockResolvedValue(expected); it('should call addOne', () => { expect(addOneSpy).toHaveBeenCalledWith(1); }); }); with ts-jest, this code snippet provided works.
Author   swc-project
🌐
Code with Hugo
codewithhugo.com › jest-mock-spy-module-import
Jest Full and Partial Mock/Spy of CommonJS and ES6 Module Imports · Code with Hugo
October 15, 2019 - import * as db from './db'; const keyPrefix = 'todos'; const makeKey = key => `${keyPrefix}:${key}`; let autoId = 1; export function addTodo(todo) { const id = autoId++; const insertable = { ...todo, id }; return db.set(makeKey(id), insertable); } export function getTodo(id) { return db.get(makeKey(id)); } The calls to db.set and db.get can be spied/mocked using the following approach (full code test file at examples/spy-module-esm-named/lib.jest-test.js): import * as db from './db'; import {addTodo, getTodo} from './lib'; beforeEach(() => jest.clearAllMocks()); test('ESM named export > addTod
🌐
GitHub
github.com › jestjs › jest › issues › 11019
Issue using "export { } from" syntax · Issue #11019 · jestjs/jest
January 19, 2021 - When trying to stub a function from a file that is re-exporting a function, Jest exits with the following error message: TypeError: Cannot redefine property: log at Function.defineProperty (<anonymous>) Try to spy on a re-exported function. # lib/index.js export { log } from './log' # index.test.js import * as Lib from './lib' test('spyOn export from', () => { const log = jest.spyOn(Lib, 'log') }) Jest correctly spys on log function.
Author   jestjs