-
-
Notifications
You must be signed in to change notification settings - Fork 9.4k
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
Template.bind on imported variable results in variable name as string literal rather than variable value #12635
Comments
It doesn't have to be a complex object, the prop just needs to reference an object. |
I changed import React from 'react';
import { A } from './someconsts';
const B = 'B'
const C = 'C' + 'c';
const D = B + 'D';
const E = { inner: 'e' };
const F = parseInt('123');
const G = 'G' + parseInt('123');
const onetwothree = '123';
const J = 'J' + parseInt(onetwothree);
export const Component = ({ a,b,c,d,e,f,g,h,i,j }) =>
<div>{a} | {b} | {c} | {d} | {e} | {f} | {g} | {h} | {i} | {j}</div>;
Component.defaultProps = {
a: A,
b: B,
c: C,
d: D,
e: E.inner,
f: F,
g: G,
h: 'H' + 'h',
i: B + 'i',
j: J,
}; (where A === 'Hello') And import React from 'react';
import { Component } from './Component';
export default {
title: 'Component',
component: Component,
};
const Template = (args) => <Component {...args} />;
export const DefaultBind = Template.bind({});
DefaultBind.args = {};
export const DefaultClosure = () => <Component />; And this is what gets rendered in each of the stories now:
Thus, it does not appear to have any problems with an object, but, rather, any computation involving variables. Interestingly, computation involving expressions without variables are executed without issue, even parsing an int. So there is javascript being executed. |
@Multihuntr that's a pretty intense example 🙈 Here's what's going on:
So I think Storybook is doing the eval, succeeding in some cases and producing the actual value, and failing in some cases and falling back to the string produced by static analysis. @jonniebigodes I'm not sure how to document this. I don't know how much better we can do than what we have now |
@Multihuntr sorry you ran into the issue, but glad that you supplied us with some context on this. @shilman going over this i have to agree with you and keep the documentation as is as to avoid introducing a bit of entropy. |
If storybook just
|
@Multihuntr you can always override the output of autogeneration if it's not producing what you want: AFAIK RDT is the best thing out there right now for generating this kind of info. |
Thanks. Although, the controls aren't that important to me. I only use Storybook as a way of rendering test cases in a browser. I was surprised to get a string literal, since I didn't know that RDT was being used. I don't need any help with anything; I'm just going to use I don't use all the features of Storybook, but I'm not clear what is being autogenerated from RDT that can't be read after-the-fact, once the component is loaded. |
Storybook consumes the following information about component props from RDT:
|
@shilman shouldn't we do it by default? |
@Hypnosphi what about typescript |
@shilman I though you can have |
I thought typically people specify the default values by: const Foo: FC<FooProps> = ({ bar='bar', baz=2 }) => <>whatever</> I guess we can spread in |
It's a common pattern in JS as well. Does |
Unfortunately, it breaks automatic actions configured with |
@shilman Maybe we should just resolve to |
I followed your solution, and here is what I did as a quick fix : const Template = (args) => <Button {...args} />
export const Primary = Template.bind({})
Primary.args = {
...Button.defaultProps,
children: 'Primary'
} Not really sexy cause it forced me to take default values out of destructuring props in my functional component, and to add a line on each story. Is there a better way ? PS: In response to last Hypnosphi post, I am not sure about what I am talking about, but why Storybook would fall into a catch if I have a value in my default value constant : //constant.js
export const color = {
PRIMARY: 'primary'
}
//comp.js
export const comp({color: color.red}) {...} color.red should not be undefined there Update: Okay I think I understood, the issue comes from the bind({}) function and not from the import |
This is a serious problem. And from our tests its not the export interface ISelectableListProp<T = string> {
rowRender?: (
item: T,
selected: boolean,
onClick: (item: T) => void
) => ReactElement
(...)
}
const SelectableList = <T extends any = string>({
rowRender = (item, selected, onClick) => (
<StandardStringListItem
selected={selected}
onClick={() => onClick?.(item)}
value={`${item}`}
/>
),
(...) The Hack we are using, forces the default value to be undefined in the stories that dont defines a value: const Template = <T extends {}>(): Story<ISelectableListProp<T>> => args => {
// HACK: Storybook (v6.0.26) can't correctly handle default-prop values that returns virtual dom.
// force undefined in the actual story element + add "disable: true" for its control.
console.log(args.rowRender) // <- This is a string (the functions toString / maybe from docgen...)
args.rowRender = undefined
return <SelectableList<T> {...args} />
} |
Hi everyone! Seems like there hasn't been much going on in this issue lately. If there are still questions, comments, or bugs, please feel free to continue the discussion. Unfortunately, we don't have time to get to every issue. We are always open to contributions so please send us a pull request if you would like to help. Inactive issues will be closed after 30 days. Thanks! |
Shiver me timbers!! I just released https://github.com/storybookjs/storybook/releases/tag/v6.2.0-alpha.30 containing PR #13919 that references this issue. Upgrade today to the
Closing this issue. Please re-open if you think there's still more to do. |
Describe the bug
When using the
Template.bind({})
method of creating stories, if a default value of the component is a variable which resolves to a value which is imported, then the value which is passed is a string literal of the variable name, rather than the variable value.This only appears to happen when you use
Template.bind({})
.To Reproduce
Here is a MWE.
Use
create-react-app
. Installstorybook
. Create these files:Component.js
someconsts.js
Component.stories.jsx
The rendered text in each case is:
VAL, world
Hello, world
Salutations, exile
Salutations, exile
Additionally, in the Storybook web interface, it shows this for both closure stories:
Expected behavior
Screenshots
See above
Code snippets
See above
System
Additional context
I am running this in a Docker container based on
mhart/alpine-node:12
, where the only difference is that I map my user from the host machine as the default user inside the container.Is this related to #12455 ? I initially thought it was, but now I'm not so sure.
The text was updated successfully, but these errors were encountered: