In this tutorial, you will learn how to create a working page-preview when you are building a SPA using Episerver and the content delivery API. Traditionally when you worked with Episerver, you could use the PropertyFor()
helper. The PropertyFor()
helper renders everything Episerver needs to render a property correctly. For example, it will render additional specific attributes so inline-editing will work.
When you are building a SPA using Episerver, it is up to you to replicate all of this logic yourself within your web-head. As of writing, there is no official dedicated Episerver Javascript client-side library to do these types of tasks. You may decide to use the foundation sample site, however, this is a very opinionated architecture. It will be up to your team to decide if the sample site fits your needs. Want to statically generate your site to follow JAMStack? Think again. This means that it is very likely that you will be responsible for getting the page preview to work yourself. In this tutorial, you will get an overview of what you will need to do in order to achieve this.
First, let us examine what a content delivery API request looks like. Imagine that you had some Javascript using Axios to call the API, similar to this:
This request will take a content reference ID and return all the related published content from the CMS. As the API only returns the published content this poses a preview dilemma. How do you get the preview content from the API? Using Dotpeek and looking within EPiServer.ContentApi.Core
you will find the ContentLoaderService
. As the name implies this class is responsible for loading the content for any API requests. Within here you will find ShouldContentBeExposed()
:
The code in this method will only return data when the page is published and the content is not expired. If you want to view the website in preview mode then this will not work. Content editors will not be able to see the unpublished changes. Instead, you will need to override this default behavior whenever a request is made in editor preview mode. To override this default behavior you will need to hook into the Episerver rendering pipeline and inject a custom content loader. The code to do this can be seen below:
This modified content loader will bypass the default rules and will allow a request to continue as long as a query-string parameter of epieditmode
is present. If true
then the request is in edit mode. If false then the request is in preview mode. If the query string is not present, the request will be treated as a normal request and the default rendering rules should be applied. In order to get the preview to work, you will also need to customize the URL resolver. The URL resolver needs to be updated to ensure that the links are resolving correctly and pointing to the preview URL rather than the standard one. This is done by creating a URL resolver:
The code above is taken from the Episerver foundation code. Within GetContextMode()
the content of the request is determined. Again this class needs to use the same logic as the custom content loader. When no query string is present, the code should work as normal. If the query string epieditmode
is present and set, the request is in edit mode. If the epieditmode
is present and set to false, the request is within preview mode. After this check is made, the context is then passed into the default URL resolver so Episerver generates the correct URL. To configure the rendering pipeline to use these new classes, you will need to update StructureMap. This can be done like this:
Lastly, you will need to enable preview mode:
With these three things in place, the page preview should now work! One thing you should be aware of when you start testing the page preview is that any blocks contained within content areas on the page will only render the published versions. The content area loader will only render published blocks. I will cover how to get around this limitation in a future post. Until then, Happy Coding!