Skip to content
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

Usage with Storybook (Component Story Format) #55

Closed
geromegrignon opened this issue Nov 11, 2019 · 6 comments
Closed

Usage with Storybook (Component Story Format) #55

geromegrignon opened this issue Nov 11, 2019 · 6 comments
Labels
question Further information is requested

Comments

@geromegrignon
Copy link

I'm trying to use new Component Story Format of Storybook with Testing library.

The goal is to import a story as an ES6 module without having to redefine its context.

With this component:

@Component({
  selector: 'app-root',
  template: `<input [type]="type">`
})
export class AppComponent {
  type: string;
}

I create 2 stories with Component Story Format to display two types of input.

export default {
  title: 'AppComponent'
};

export const defaultInput = () => ({
  component: AppComponent,
  props: {
    type: 'text'
  }
});

export const rangeInput = () => ({
  component: AppComponent,
  props: {
    type: 'range'
  }
});

With Testing Library, i would expect to be able to test the type from each story without having to define the type in the test.
I'm aware my issue comes from the way i use render() as i call the component property of the story and at this point no property is defined for this component.
But i can't find a way to render the component and its context just by calling 'defaultInput()' or 'rangeInput()'. Is there a solution?

describe('AppComponent', () => {
  // not working test : the type is not defined
  it('should render a custom title', async () => {
    const component = await render(defaultInput().component);
    expect(component.fixture.componentInstance.type).toBe('text');
  });
  // working example as the property is defined into the test context
  it('should render a custom title', async () => {
    const component = await render(defaultInput().component, {
      componentProperties: {
        type: 'text'
      }
    });
    expect(component.fixture.componentInstance.type).toBe('text');
  });
  // not working test : the type is not defined
  it('should render a custom title', async () => {
    const component = await render(rangeInput().component);
    expect(component.fixture.componentInstance.type).toBe('range');
  });
  // working example as the property is defined into the test context
  it('should render a custom title', async () => {
    const component = await render(rangeInput().component, {
      componentProperties: {
        type: 'range'
      }
    });
    expect(component.fixture.componentInstance.type).toBe('range');
  });
});

Link to the project on Github.

@timdeschryver
Copy link
Member

timdeschryver commented Nov 11, 2019

The problem is that the API is different, right?

I think you will have to do the following, to map the API:

    const input = rangeInput();
    const component = await render(input.component, { componentProperties: input.props });
    expect(component.fixture.componentInstance.type).toBe('range');

@timdeschryver timdeschryver added the question Further information is requested label Nov 11, 2019
@geromegrignon
Copy link
Author

Thanks a lot, i was thinking to use this way too.

@timdeschryver
Copy link
Member

Awesome!

@lkashef
Copy link

lkashef commented Nov 7, 2020

Thanks @timdeschryver! I spent a whole day trying to figure this out!

Another tip in case anyone came across this issue

component.fixture.componentInstance.type this line was throwing a typescript: Property 'type' does not exist on type 'unknown'.ts, so calling render with the actual component under test (render<AppComponent>) will help you overcome this problem and give you static detection to the component properties.


@shilman, sorry to bother you but I was wondering now with v6 (csf), is there a better way to test stories in angular, instead of components.

the motive here is to mainly:

  • to reduce duplications and test efficiently against use cases (stories) instead of just replicating the same story logic in the jest unit test
  • reduce the gap between what we visually see in storybook viewer vs the test cases

@shilman
Copy link

shilman commented Nov 8, 2020

@lkashef Thanks for the mention.

We're currently bridging the gap between storybook and React testing library: storybookjs/storybook#10145

I'm sure some of these utilities (e.g. decorator/parameter/arg composition) can be applied to all frameworks.

As for a more natural way to test stories, we're still figuring that out. Suggestions welcome!

@lkashef
Copy link

lkashef commented Nov 8, 2020

Thanks @shilman, I am glad you folks have that on your radar.

Yes for sure, soon I hope I can contribute to this amazing project and community!

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
question Further information is requested
Projects
None yet
Development

No branches or pull requests

4 participants