Beginner question: component vs. reactComponent

First of all, sorry if this is a little basic, but I’m just starting to understand Purescript (though with a Haskell background at least).

I’ve been reading the react-basic-hooks documentation and came across two functions: component and reactComponent. The first one seems to receive a general props type, wheras the latter receives Record props. What’s the difference between props and Record props?

Moreover, reactComponent seems to return a ReactComponent. Clicking on the docs simply gives me data ReactComponent :: Type -> Type as it’s type. When do I use component, when reactComponent?

Welcome! And good question! I’ll give it a go, but take it with a grain of salt, because I’m not 100% confident my answer is right.

We use react-basic-hooks in production, and I just searched our codebase and we don’t use reactComponent a single time anywhere. Looking at the docs, it seems to me that reactComponent exists for when PureScript is definining a component that you intend to use from JavaScript or TypeScript. The regular component function is much more convenient in a PureScript-only codebase, but is probably harder to use from JavaScript.

Record props in the reactComponent just means that your input has to be a record, while props in component is totally generic for any type. More specifically Record is a type constructor that takes a row. In fact, your normal syntax like { x :: Int, y :: String } is just sugar for Record (x :: Int, y :: String). So in the reactComponent, props must be a row, and Record props is a record with those fields (and then it can use the row to do fun stuff like say it’s any record that lacks “key”, “ref”, and “children” as fields in that record).

4 Likes

Looks right to me!

component does two things:

  • pre-applies element (a curried version of React.createElement) so you don’t have to do it everywhere
  • tunnels your props to the underlying react component under the key nested so you don’t have to worry about these JS react edge cases for the more common case of writing components for use in PS:
    • you don’t need to use an object/record – sometimes there’s only one prop, or you have a custom data type with multiple constructors holding different prop shapes
    • key and ref are reserved
    • children sometimes gets unwrapped in JS, which means that prop needs a special type to handle this at runtime (see reactComponentWithChildren and ReactChildren)

The functions that return ReactComponent are helpful for building components you need to consume outside PS or pass to 3rd party libraries. The ReactComponent type itself can also be used to define components imported from JS via the FFI.

7 Likes

Sorry for taking long to answer, but: Thanks! Excellent replies!

2 Likes