This blog is about SharePoint, Office365 and Office Development

Popular Posts

SharePoint Online: Use SPO as headless CMS for Public Facing websites

Yes, the title is correct. It's not a typo. SharePoint online and public facing websites in the same sentence.
Some of you would wonder, is that an old concept, old post, we are in 2020 and SharePoint online doesn't offer the public facing site collection anymore. Have I gone mad !?

I was planning to write down this blog post for over four years now and every single time I really pass the buck on that one.
If you are/were a SharePointer part of your work experience was somehow focused towards customer experience not employee experience.  For me it was  the main focus as I used to to work more on building public facing solutions/experiences using On-premises versions of SharePoint 2010/2013 rather than intranets and extranets.

Note:  if you are looking for a rich experience this wouldn't definitely be the right path, also the intention of this post is just to go through a recent personal experience for an idea I had for almost over 5 years ago.

Don't get me wrong , Intranets/extranets were always integral part of our offerings back then but as more spent was poured towards brand identity and public facing experiences we get more public facing websites.

Implementing a complex and innovative designs on top of SharePoint was always challenging , the amount of time spent to make a SharePoint public facing sites using custom Master pages is enormous.  Moreover, it was hard to maintain and the most challenging task used to fit the custom UI on top of SharePoint as the poor UI developer tries to get a fully working standalone HTML/CSS works fine within the SharePoint realm !

To avoid some of these complications, we always tried to separate the concerns and use SharePoint site collection for publishing and use cross site publishing features to leverage content from multiple authors. 
But when it comes to the UI  concern separations and loose coupling wasn't that obvious. We have always used a customer master page. I remember in rare occasions building ASP.NET web applications that uses SharePoint APIs to get the required content and it had worked very well for us but it comes with the following caveats :
  • Maintenance overhead  : Additional Website, where to host, make sure it's redundant and can scale up etc...
  • losing WYSIWYG aspect or in some cases making WYSIWYG more difficult as content editors need to lunch the standalone web app to view what the site will look like instead of just clikcing on a publish button. 
  • Can't use OTB components, which is very useful specially in search scenarios.
  • Missing out on some SharePoint features specially around analytics (but most of our public facing websites were using a different analytics solution)
This is not a the first time I blog about the loosely coupled approach. I've shared almost the same approach but for a loosely coupled intranet back in 2016 and I've built it even using NodeJS and present it in Perth Office 365 Saturday back in May 2016.

So the approach is pretty the same but we would use application permission to allow anonymous users to use the APIs without promot them to be challenged via login page and get id and access token in the same manner that we would do in an intranet scenario, in a nutshell it will look the below:

Couple of things to note here:
  1. Application permission is not enabled for every single endpoint
  2. API access to SharePoint would be via Site.Read.All and Site.ReadWrite.All scopes which still in preview and doesn't allow you to limit access to a particular site collection.
  3. Performance is not going to be great that's why I highly recommend using any kind of caching to make it less expensive for the API to return the content required by your client (SPA, web application or mobile native client)

It would be interesting to see if scopes can be limited to specific site collection also you can use this in conjunction with other delegated permission to fulfill different scenarios for your proxy API