Description
With React server components, async React components are now a thing. Async components in this context means that you, on the server, can use an async function (and via that await in the body) as your component function:
let User = async (props) => {
let userData = await getUserData(props.userId)
<div>{userData.name}</div>
}
In ReScript it could look like this:
@react.component
let make = async (~userId) => {
let userData = await getUserData(userId)
<div> {React.string(userData.name)} </div>
}
However, this doesn't work today: https://rescript-lang.org/try?version=v11.0.0-beta.4&code=AIJwpghgxgLgdFA9gWwA6IHZgzAUAGzBgAJkIBrMYgXmIgGcBPDKYgCgD8BXesEASQAmAShoA+YgG9cxYoRI8+AEQgwINOgHcIASxIBzIgFVeIFWraKBImcQA8gnQDcJkgEqRYcejBA6M+pam5hBwGBDIYMIAvvYA9I4uuNG4QA
(I believe it doesn't work because we're loosing the async context in the PPX as the make
function is transformed.)
It is possible to use async components today by not using the PPX, and defining your own wrapping identity function for casting the async component into a regular one:
type userData = {name: string}
let getUserData = async _userId => {name: "test"}
external asyncComponent: ('props => promise<React.element>) => React.component<
'props,
> = "%identity"
module AsyncComponent = {
type props = {userId: string}
let make = asyncComponent(async (props: props) => {
let userData = await getUserData(props.userId)
<div> {React.string(userData.name)} </div>
})
}
let jsx = <AsyncComponent userId="1" />
However, this gives up using the PPX, and requires you to manually wrap the make function in that external. And that doesn't feel very ergonomic.
How can we make this work?
I think this is important to support now that Server Components are becoming a thing, and ReScript supports everything else for them.
Interested in your thoughts here. The way I see it, we need at least 2 things:
- Figure out why the async context isn't propagated as
make
is transformed in the PPX - Have some sort of functionality like the external above that turns an async component into a regular component that React/JSX expects. Maybe have this builtin to the PPX? Or ship that exact external with
rescript-react
?
Cc @mununki @cristianoc . What do you think? Interested in your thoughts of this.