Roll your own Provider and connect with recompose

The Provider and connect concepts provided by higher-order components in many state management libraries are one of my favorite conveniences of React. I haven’t come across a bad version of any of these, and I don’t really see the need to write another one. That being said I think the subject provides a good opportunity to demonstrate utilizing context with the withContext and getContext higher-order components from recompose.

Now we have a simple Provider with an accompanying connect. We’re obviously lacking some of the magic of the react-redux connect higher-order component, but all the basics are there. Let’s look at how we’d use this.

That’s simple enough. The context will contain the props of the Provider, and a component wrapped in connect will receive those props in the form of the stores prop.

That’s cool, but what about the react-redux connect's mapStateToProps concept? That’s easily accomplished with the mapProps higher-order-component.

Here, with mapProps, we spread the props of the parent component, and merge them with the props returned by our mapStateToProps function. It’s not perfect as it currently requires a mapStateToProps argument to prevent undefined is not a function, but I think the basic idea is clear.

Conclusion

I don’t think there is really any reason to replace the Provider and connect higher-order components provided by whatever state management library you use, but as an exercise in how recompose can simplify complex topics such as context I think these concepts are a great learning tool.

There is always the possibility you use some form of state management that doesn’t provide these higher-order components, and in that case recompose can be really helpful.

If you like what you see here, check out my previous story to learn about the withState and withHandlers higher-order-components from recompose.

Thanks for reading!

Edit: I had a major error in my code in the original version of this article, it’s important to note that the component wrapped by withContext should render it’s children, sorry about that!