Skip to content

Masterbar: async-load launch button to prevent Explat warnings#109841

Merged
zaguiini merged 1 commit intotrunkfrom
update/async-load-masterbar-launch-button
Apr 6, 2026
Merged

Masterbar: async-load launch button to prevent Explat warnings#109841
zaguiini merged 1 commit intotrunkfrom
update/async-load-masterbar-launch-button

Conversation

@zaguiini
Copy link
Copy Markdown
Contributor

@zaguiini zaguiini commented Apr 6, 2026

Proposed Changes

  • Load MasterbarLaunchButton with AsyncLoad in the logged-in masterbar instead of a static import.
  • Switch masterbar-launch-button.tsx to a default export so the async chunk resolves correctly.

Why are these changes being made?

The masterbar is loaded in SSR contexts and because the Launch Button contains experiment setup code and the explat code should only be run in the browser, it was giving us

ERROR calypso: 
    message: Trying to initialize anonId outside of a browser context.
    --
    properties: {
      "context": "explat",
      "explat_client": "calypso",
      "message": "Trying to initialize anonId outside of a browser context."
    }

Testing Instructions

  1. Log in to Calypso with a site that is not launched yet.
  2. Confirm the launch button still appears and works (launch flow / navigation as before).
  3. Check you don't see the error in the server logs.

Load MasterbarLaunchButton via AsyncLoad so its chunk is not in the
initial masterbar bundle. Export default for AsyncLoad require().

Made-with: Cursor
@zaguiini zaguiini self-assigned this Apr 6, 2026
@zaguiini zaguiini changed the title Masterbar: async-load launch button Masterbar: async-load launch button to prevent Explat warnings Apr 6, 2026
@zaguiini zaguiini marked this pull request as ready for review April 6, 2026 20:02
@matticbot
Copy link
Copy Markdown
Contributor

This PR modifies the release build for the following Calypso Apps:

For info about this notification, see here: PCYsg-OT6-p2

  • help-center

To test WordPress.com changes, run install-plugin.sh $pluginSlug update/async-load-masterbar-launch-button on your sandbox.

@zaguiini zaguiini requested review from a team April 6, 2026 20:14
@matticbot matticbot added [Status] Needs Review The PR is ready for review. This also triggers e2e canary tests and wp-desktop tests automatically. labels Apr 6, 2026
@zaguiini zaguiini merged commit 2f4e1be into trunk Apr 6, 2026
18 of 20 checks passed
@zaguiini zaguiini deleted the update/async-load-masterbar-launch-button branch April 6, 2026 23:29
@github-actions github-actions bot removed the [Status] Needs Review The PR is ready for review. This also triggers e2e canary tests and wp-desktop tests automatically. label Apr 6, 2026
Copy link
Copy Markdown
Member

@p-jackson p-jackson left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

@aaronyan when calypso/lib/explat is imported on the server we get this error message.

https://github.com/Automattic/wp-calypso/blob/c234565488018d2672be95943e4bf19a79e52e8e/client/lib/explat/internals/anon-id.ts#L45

It makes sense that we skip initialising this on the server, but we safely skip it by returning null. So what's the purpose of the error message? Afaict nothing bad happens, and in fact I would think skipping this is expected behaviour? If a React component uses explat, then it makes sense to skip this on the server and then when the component is hydrated client side is when the anonID is set up.

Can't we remove this line or at least downgrade it from an error to just an info message?

}

return <MasterbarLaunchButton siteId={ siteId } />;
return <AsyncLoad require="./masterbar-launch-button" placeholder={ null } siteId={ siteId } />;
Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The problem is that AsyncLoad can't be server rendered, it's internal <Suspense> element can't be serialised by vanilla React. I merged #109543 to work around this issue for the help centre icon, but I think we could maybe do a "simpler" solution for the MasterbarLaunchButton?

The issue is that master-bar-launch-button.tsx imports lib/explat, which then sets up the anonId at the module level. No way of avoiding it once you've imported lib/explat.

This is some untested code. We could switch the useExperiment call in master-bar-launch-button.tsx out for a hook like this.

function useAsyncExperiment( experimentName: string ) {
	const [ result, setResult ] = useState( [ true, null ] );

	useEffect( () => {
		let isSubscribed = true;
		import ('calypso/lib/explat').then( ( { loadExperimentAssignment } ) => {
			if ( isSubscribed ) {
				loadExperimentAssignment( experimentName ).then( ( data ) => {
					if ( isSubscribed ) {
						setResult( [ false, data ] );
					}
				} );
			}
		} );
		return () => {
			isSubscribed = false;
		};
	}, [ experimentName ] );

	return result;
}

But even this might be more complicated than necessary. See question in the comment above.

@p-jackson
Copy link
Copy Markdown
Member

I'm reverting this (#109845) because AsyncLoad is going to introduce other SSR issues. Will hopefully hear from @aaronyan about whether we can simply silence the error.

@p-jackson
Copy link
Copy Markdown
Member

Follow up #109849

@aaronyan
Copy link
Copy Markdown
Member

aaronyan commented Apr 9, 2026

Thanks @p-jackson! I'll share some thoughts on your PR. Thanks for fixing this at the ExPlat level.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

4 participants