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

Observable created by fromResource can't be used in computed if it sinks immediately #32

Closed
tekacs opened this issue Jan 3, 2017 · 3 comments
Labels

Comments

@tekacs
Copy link
Contributor

tekacs commented Jan 3, 2017

Observables created using fromResource seem to be impossible to use inside a computed from mainline MobX. Apart from creating derived values, this is also useful for simply wrapping the resulting observables in a familiar interface to be passed to functions that normally received an IComputedValue<T> rather than a {current(): T, dispose(): void, isAlive(): boolean}.

Even a simple computed: computed(() => fromResourceObservable.current()) throws an exception.

The exception thrown is an invariant violation of actions being used inside computed:

Uncaught Error: [mobx] Invariant failed: Computed values or transformers should not invoke actions or trigger other side effects

This happens because it appears that fromResource's sink uses an action in its implementation, here:

subscriber(action("ResourceBasedObservable-sink", (newValue: T) => {
.

Example

You can see an example of the problem here http://www.webpackbin.com/4k5kc14BM. I also made a zip of the project, since WebpackBin doesn't let me make the bin immutable.

In the above project, if you render the React component using obsUser directly, the component works fine. If you render it using computedUser, you trigger the above exception.

I used exactly the code from the example by @mweststrate in the mobx-utils README with a mock dbUserRecord wrapped in a computed.

I ran into this problem myself trying to use MobX to wrap apollo-client as in your comment here. The reason being that Apollo's subscribe immediately calls sink on the stack of its first call, thus tripping this action guard.

All of these problems can be avoided as far as I can tell, by deferring the sink to occur on the 'next tick', so that it's outside the guards of the computed's execution, but this is an unreliable solution that should hopefully not be necessary.

@mweststrate
Copy link
Member

@tekacs confirmed, thanks for reporting!

@mweststrate mweststrate added the bug label Jan 3, 2017
@mweststrate
Copy link
Member

The issue should be fixed now, could you confirm?

@tekacs
Copy link
Contributor Author

tekacs commented Jan 3, 2017

Confirmed fixed, both in my use with apollo-client and in the WebpackBin above, with no changes made other than updating mobx-utils.

Thanks for turning this around so fast! :)

@tekacs tekacs closed this as completed Jan 3, 2017
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
Projects
None yet
Development

No branches or pull requests

2 participants