
Research
Malicious npm Packages Impersonate Flashbots SDKs, Targeting Ethereum Wallet Credentials
Four npm packages disguised as cryptographic tools steal developer credentials and send them to attacker-controlled Telegram infrastructure.
storybook-addon-module-mock
Advanced tools
[](https://www.npmjs.com/package/storybook-addon-module-mock) [](https://www.npmjs.com/package/storybook-addon-module-mock) ['],
build: {
test: {
disabledAddons: ['@storybook/addon-docs', '@storybook/addon-essentials/docs'],
},
},
addons: [
'@storybook/addon-essentials',
'@storybook/addon-interactions',
{
name: '@storybook/addon-coverage',
options: {
istanbul: {
exclude: ['**/components/**/index.ts'],
},
},
},
{
name: 'storybook-addon-module-mock',
options: {
exclude: ['**/node_modules/@mui/**'],
},
},
],
};
export default config;
import React, { FC, useMemo, useState } from 'react';
interface Props {}
/**
* MockTest
*
* @param {Props} { }
*/
export const MockTest: FC<Props> = ({}) => {
const [, reload] = useState({});
const value = useMemo(() => {
return 'Before';
}, []);
return (
<div>
<button onClick={() => reload({})}>{value}</button>
</div>
);
};
createMock
replaces the target module function with the return value of jest.fn()
.
The mockRestore()
is automatically performed after the Story display is finished.
import { Meta, StoryObj } from '@storybook/react';
import { expect, userEvent, waitFor, within } from '@storybook/test';
import React, { DependencyList } from 'react';
import { createMock, getMock, getOriginal } from 'storybook-addon-module-mock';
import { MockTest } from './MockTest';
const meta: Meta<typeof MockTest> = {
tags: ['autodocs'],
component: MockTest,
};
export default meta;
export const Primary: StoryObj<typeof MockTest> = {
play: async ({ canvasElement }) => {
const canvas = within(canvasElement);
expect(canvas.getByText('Before')).toBeInTheDocument();
},
};
export const Mock: StoryObj<typeof MockTest> = {
parameters: {
moduleMock: {
mock: () => {
const mock = createMock(React, 'useMemo');
mock.mockImplementation((fn: () => unknown, deps: DependencyList) => {
// Call the original useMemo
const value = getOriginal(mock)(fn, deps);
// Change the return value under certain conditions
return value === 'Before' ? 'After' : value;
});
return [mock];
},
},
},
play: async ({ canvasElement, parameters }) => {
const canvas = within(canvasElement);
expect(canvas.getByText('After')).toBeInTheDocument();
const mock = getMock(parameters, React, 'useMemo');
expect(mock).toBeCalled();
},
};
export const Action: StoryObj<typeof MockTest> = {
parameters: {
moduleMock: {
mock: () => {
const useMemo = React.useMemo;
const mock = createMock(React, 'useMemo');
mock.mockImplementation(useMemo);
return [mock];
},
},
},
play: async ({ canvasElement, parameters }) => {
const canvas = within(canvasElement);
const mock = getMock(parameters, React, 'useMemo');
mock.mockImplementation((fn: () => unknown, deps: DependencyList) => {
const value = getOriginal(mock)(fn, deps);
return value === 'Before' ? 'Action' : value;
});
userEvent.click(await canvas.findByRole('button'));
await waitFor(() => {
expect(canvas.getByText('Action')).toBeInTheDocument();
});
},
};
export const getMessage = () => {
return 'Before';
};
import React, { FC, useState } from 'react';
import { getMessage } from './message';
interface Props {}
/**
* LibHook
*
* @param {Props} { }
*/
export const LibHook: FC<Props> = ({}) => {
const [, reload] = useState({});
const value = getMessage();
return (
<div>
<button onClick={() => reload({})}>{value}</button>
</div>
);
};
import { Meta, StoryObj } from '@storybook/react';
import { expect, userEvent, waitFor, within } from '@storybook/test';
import { createMock, getMock } from 'storybook-addon-module-mock';
import { LibHook } from './LibHook';
import * as message from './message';
const meta: Meta<typeof LibHook> = {
tags: ['autodocs'],
component: LibHook,
};
export default meta;
export const Primary: StoryObj<typeof LibHook> = {
play: async ({ canvasElement }) => {
const canvas = within(canvasElement);
expect(canvas.getByText('Before')).toBeInTheDocument();
},
};
export const Mock: StoryObj<typeof LibHook> = {
parameters: {
moduleMock: {
mock: () => {
const mock = createMock(message, 'getMessage');
mock.mockReturnValue('After');
return [mock];
},
},
},
play: async ({ canvasElement, parameters }) => {
const canvas = within(canvasElement);
expect(canvas.getByText('After')).toBeInTheDocument();
const mock = getMock(parameters, message, 'getMessage');
console.log(mock);
expect(mock).toBeCalled();
},
};
export const Action: StoryObj<typeof LibHook> = {
parameters: {
moduleMock: {
mock: () => {
const mock = createMock(message, 'getMessage');
return [mock];
},
},
},
play: async ({ canvasElement, parameters }) => {
const canvas = within(canvasElement);
const mock = getMock(parameters, message, 'getMessage');
mock.mockReturnValue('Action');
userEvent.click(await canvas.findByRole('button'));
await waitFor(() => {
expect(canvas.getByText('Action')).toBeInTheDocument();
});
},
};
import React, { FC, useMemo, useState } from 'react';
interface Props {}
/**
* MockTest
*
* @param {Props} { }
*/
export const MockTest: FC<Props> = ({}) => {
const [, reload] = useState({});
const value = useMemo(() => {
return 'Before';
}, []);
return (
<div>
<button onClick={() => reload({})}>{value}</button>
</div>
);
};
import { Meta, StoryObj } from '@storybook/react';
import { expect, userEvent, waitFor, within } from '@storybook/test';
import React, { DependencyList } from 'react';
import { createMock, getMock, getOriginal } from 'storybook-addon-module-mock';
import { MockTest } from './MockTest';
const meta: Meta<typeof MockTest> = {
tags: ['autodocs'],
component: MockTest,
};
export default meta;
export const Primary: StoryObj<typeof MockTest> = {
play: async ({ canvasElement }) => {
const canvas = within(canvasElement);
expect(canvas.getByText('Before')).toBeInTheDocument();
},
};
export const Mock: StoryObj<typeof MockTest> = {
parameters: {
moduleMock: {
mock: () => {
const mock = createMock(React, 'useMemo');
mock.mockImplementation((fn: () => unknown, deps: DependencyList) => {
// Call the original useMemo
const value = getOriginal(mock)(fn, deps);
// Change the return value under certain conditions
return value === 'Before' ? 'After' : value;
});
return [mock];
},
},
},
play: async ({ canvasElement, parameters }) => {
const canvas = within(canvasElement);
expect(canvas.getByText('After')).toBeInTheDocument();
const mock = getMock(parameters, React, 'useMemo');
expect(mock).toBeCalled();
},
};
export const Action: StoryObj<typeof MockTest> = {
parameters: {
moduleMock: {
mock: () => {
const useMemo = React.useMemo;
const mock = createMock(React, 'useMemo');
mock.mockImplementation(useMemo);
return [mock];
},
},
},
play: async ({ canvasElement, parameters }) => {
const canvas = within(canvasElement);
const mock = getMock(parameters, React, 'useMemo');
mock.mockImplementation((fn: () => unknown, deps: DependencyList) => {
const value = getOriginal(mock)(fn, deps);
return value === 'Before' ? 'Action' : value;
});
userEvent.click(await canvas.findByRole('button'));
await waitFor(() => {
expect(canvas.getByText('Action')).toBeInTheDocument();
});
},
};
import React, { FC } from 'react';
import styled from './ReRenderArgs.module.scss';
interface Props {
value: string;
}
/**
* ReRenderArgs
*
* @param {Props} { value: string }
*/
export const ReRenderArgs: FC<Props> = ({ value }) => {
return <div className={styled.root}>{value}</div>;
};
import { Meta, StoryObj } from '@storybook/react';
import { expect, waitFor, within } from '@storybook/test';
import { createMock, getMock, render } from 'storybook-addon-module-mock';
import * as message from './message';
import { ReRender } from './ReRender';
const meta: Meta<typeof ReRender> = {
tags: ['autodocs'],
component: ReRender,
};
export default meta;
export const Primary: StoryObj<typeof ReRender> = {};
export const ReRenderTest: StoryObj<typeof ReRender> = {
parameters: {
moduleMock: {
mock: () => {
const mock = createMock(message, 'getMessage');
return [mock];
},
},
},
play: async ({ canvasElement, parameters }) => {
const canvas = within(canvasElement);
const mock = getMock(parameters, message, 'getMessage');
mock.mockReturnValue('Test1');
render(parameters);
await waitFor(() => {
expect(canvas.getByText('Test1')).toBeInTheDocument();
});
mock.mockReturnValue('Test2');
render(parameters);
await waitFor(() => {
expect(canvas.getByText('Test2')).toBeInTheDocument();
});
},
};
FAQs
[](https://www.npmjs.com/package/storybook-addon-module-mock) [](https://www.npmjs.com/package/storybook-addon-module-mock) [![](http
The npm package storybook-addon-module-mock receives a total of 39,284 weekly downloads. As such, storybook-addon-module-mock popularity was classified as popular.
We found that storybook-addon-module-mock demonstrated a healthy version release cadence and project activity because the last version was released less than a year ago. It has 1 open source maintainer collaborating on the project.
Did you know?
Socket for GitHub automatically highlights issues in each pull request and monitors the health of all your open source dependencies. Discover the contents of your packages and block harmful activity before you install or update your dependencies.
Research
Four npm packages disguised as cryptographic tools steal developer credentials and send them to attacker-controlled Telegram infrastructure.
Security News
Ruby maintainers from Bundler and rbenv teams are building rv to bring Python uv's speed and unified tooling approach to Ruby development.
Security News
Following last week’s supply chain attack, Nx published findings on the GitHub Actions exploit and moved npm publishing to Trusted Publishers.