orphic-cypress
Version:
Set of utilities and typescript transformers to cover storybook stories with cypress component tests
114 lines • 5.09 kB
JavaScript
Object.defineProperty(exports, "__esModule", { value: true });
exports.stubStoryActions = void 0;
/** Quick util to stub or spy and alias, which isn't consistent in cypress API */
const mockAs = (alias, toSpy) => {
if (toSpy)
return cy.spy(toSpy).as(alias);
const stub = cy.stub();
stub.as(alias);
return stub;
};
const addAlias = (stubOrSpy, alias) => {
stubOrSpy.as(alias);
return stubOrSpy;
};
/**
* Wrap argTypes in cy.stubs. Unit test framework from storybook at this point doesn't do
* anything with these argTypes, nor does it add props/stubs for actions.argTypesRegex.
* As such, its recommended to manually specify crucial argTypes, or write `.cy` tests
* which provide mocks.
*
* In executeCyTests will operate on `export default { argTypes: { some: { action: 'some' } } }`
* and combine that with any action argTypes defined on the story level.
* Will be available at `cy.get("@actions")` or `this.actions` within tests.
*
* @private
*/
const stubArgTypeActions = (args, argTypes, seed) => Object.entries(argTypes !== null && argTypes !== void 0 ? argTypes : {}).reduce((acc, [key, value]) => {
if (value && value.action) {
// alias the stub with the name given to the action. shows up really well in cypress
// as a stub with call count and in assertion names etc.
return {
...acc,
[key]: acc[key]
? addAlias(acc[key], value.action)
: mockAs(value.action, args === null || args === void 0 ? void 0 : args[key]),
};
}
return acc;
}, seed !== null && seed !== void 0 ? seed : {});
/**
* Get argTypes from both the default export and the individual story.
* Useful for a per-component beforeEach or top-of-test declaration.
* Note that you'll want to return undefined from `beforeEach`
*
* ```ts
* describe("SomeComponent", () => {
* beforeEach(() => {
* stubStoryActions(SomeComponent, stories);
* });
*
* it("should render ok and call someAction on init", () => {
* cy.mount(<SomeComponent {...this.actions} />);
* cy.get("@actions").its("someAction").should("be.calledWith", "");
* });
* });
* ```
*
* ```ts
* it("should do something", () => {
* // could just be `const actions = { someAction: cy.stub(), ... }`
* const actions = stubStoryActions(SomeStory, stories);
* cy.mount(<SomeStory {...actions} />);
* cy.dataCy("something").click().then(() => {
* expect(actions.someAction).to.have.callCount(1);
* });
* // or without the promise
* cy.dataCy("something").click();
* cy.get("@actions").its("someAction").should("have.callCount", 2);
* });
* ```
*
* Mostly an internal detail: precedence order, 3 through end will have essentially the same effect
* 1) explicitly provided args/props for story which will become spies
* 2) explicitly provided args at default export which will become spies
* 3) local argTypes action definition
* 4) global argTypes action definition
* 5) local argTypes regex definition
* 6) global argTypes regex definition
*/
const stubStoryActions = (composedStory, stories, seed) => {
var _a, _b, _c, _d, _e, _f, _g, _h, _j;
const { argTypes, storyName, parameters, args } = composedStory;
const argTypesRegex = (_a = parameters === null || parameters === void 0 ? void 0 : parameters.actions) === null || _a === void 0 ? void 0 : _a.argTypesRegex;
const docgenInfo = (_c = (_b = stories.default) === null || _b === void 0 ? void 0 : _b.component) === null || _c === void 0 ? void 0 : _c.__docgenInfo;
const asRegex = new RegExp(argTypesRegex);
// start with args and props, unique
const argKeys = [
...new Set([
...Object.keys(args !== null && args !== void 0 ? args : {}),
...Object.keys((_d = docgenInfo === null || docgenInfo === void 0 ? void 0 : docgenInfo.props) !== null && _d !== void 0 ? _d : {}),
]),
];
const toAutoMock = argTypesRegex
? Object.fromEntries(argKeys.flatMap((key) => asRegex.test(key)
? [[key, mockAs(`argTypesRegex.${key}`, args === null || args === void 0 ? void 0 : args[key])]]
: []))
: {};
const argTypesFromStoryObj = storyName
? (_e = stories[storyName]) === null || _e === void 0 ? void 0 : _e.argTypes
: null;
const actions = stubArgTypeActions({ ...((_g = (_f = stories.default) === null || _f === void 0 ? void 0 : _f.args) !== null && _g !== void 0 ? _g : {}), ...composedStory.args }, {
...((_j = (_h = stories.default) === null || _h === void 0 ? void 0 : _h.argTypes) !== null && _j !== void 0 ? _j : {}),
...(argTypes !== null && argTypes !== void 0 ? argTypes : {}),
...(argTypesFromStoryObj !== null && argTypesFromStoryObj !== void 0 ? argTypesFromStoryObj : {}),
}, {
...toAutoMock,
...(seed !== null && seed !== void 0 ? seed : {}),
});
cy.wrap(actions).as("actions");
return actions;
};
exports.stubStoryActions = stubStoryActions;
//# sourceMappingURL=actions.js.map
;