Accessing the Sitecore Context data in a React component
JSS ships with a React higher-order component (HOC) that can inject the Sitecore context - in other words, route-level data, as opposed to component-level data - into any component.
Common examples of needing context data might be to get at page title or meta keyword fields stored on the route level or to conditionally alter rendering when using the app with advanced Sitecore editors. The following is an abbreviated example of using the HOC:
import { withSitecoreContext } from '@sitecore-jss/sitecore-jss-react';
const MyComponent = (props) => <div>Page editing: {props.sitecoreContext.pageEditing}</div>;
// wrap MyComponent in the HOC (note the double function invocation - important)
export default withSitecoreContext()(MyComponent);
To use the withSitecoreContext()
HOC, you must wrap any component using it in a SitecoreContext
component that maintains a context state. For example, in the root component of the application:
import React from 'react';
import { SitecoreContext } from '@sitecore-jss/sitecore-jss-react';
import { componentFactory } from './temp/componentBuilder';
export default class extends React.Component {
constructor(props) {
super(props);
// Set default sitecoreContext
if (props.ssrState) {
this.sitecoreContext = props.ssrState.sitecore && props.ssrState.sitecore.route
? {
route: props.ssrState.sitecore.route,
itemId: props.ssrState.sitecore.route.itemId,
...props.ssrState.sitecore.context,
}
: props.ssrState.sitecore.context
} else {
this.sitecoreContext = null;
}
}
render() {
return (
<SitecoreContext context={this.sitecoreContext}>
<YourAppsComponentsHere />
</SitecoreContext>
)
}
}
The final piece of using the withSitecoreContext()
HOC is to ensure that the data in the props.sitecoreContext
property is updated when the Sitecore context changes. To get access to props.updateSitecoreContext
and update props.sitecoreContext
inside the nested component, you can wrap the component with withSitecoreContext({ updatable: true })
. This could be when the route changes in your app, or when server-side rendering passes down a state object - any time new layout data is pulled from Sitecore and rendered. For example:
import React from 'react';
import { withSitecoreContext } from '@sitecore-jss/sitecore-jss-react';
class RouteHandler extends React.Component {
getContext = () => this.props.sitecoreContext
async updateRouteData() {
const routeData = await getRouteData("/"); // makes a request for new route data, for example
this.props.updateSitecoreContext(routeData.sitecore.context);
}
}
export default withSitecoreContext({ updatable: true })(RouteHandler)
We do not recommend that you store the global variable ssrInitialState
and use it across the application. Instead, you must pass ssrInitialState
into the AppRoot
, store all required data inside SitecoreContext
, and access it using withSitecoreContext()
.