meteor / react-packages

Meteor packages for a great React developer experience
http://guide.meteor.com/react.html
Other
571 stars 157 forks source link

react-meteor-accounts not working with SSR #364

Open dnish opened 1 year ago

dnish commented 1 year ago

Hey, when adding the useUserId() hook to my component, I get the following error:

Error running template: Error: Meteor.userId can only be invoked in method calls or publications.

We are running the latest Meteor version with React 18.

Grubba27 commented 1 year ago

Hey, @CaptainN, any thoughts on this one? Also, @dnish, can you provide a snippet of code so that anyone who may find this same issue may relate? thx a lot for reporting 🙏

dnish commented 1 year ago

Hey @Grubba27, yeah, we use the standard way for SSR. On our main.js we got this:

import {onPageLoad} from "meteor/server-render";
import { renderToString } from "react-dom/server";

onPageLoad(sink => {
    const htmlString = renderToString(<App sink={sink}/>);
    sink.renderIntoElementById("app-wrapper", htmlString);
});

I guess the main problem is that Meteor.userId() is only callable within the context of a publish or method. In this case, it is not available within the onPageLoad handler. This one gives an error:

onPageLoad(sink => {
    console.log(Meteor.userId());
    const htmlString = renderToString(<App sink={sink}/>);
    sink.renderIntoElementById("app-wrapper", htmlString);
});

I found a fix, because I was wondering why it worked on another application. If you use the FastRender package, it works perfectly.

import {onPageLoad} from "meteor/server-render";
import { renderToString } from "react-dom/server";
import { FastRender } from 'meteor/communitypackages:fast-render';

FastRender.onPageLoad(sink => {
    console.log(Meteor.userId()); // Works
    const htmlString = renderToString(<App sink={sink}/>);
    sink.renderIntoElementById("app-wrapper", htmlString);
});