Johan Björnfot
Dec 11, 2013
  12151
(3 votes)

Multisite feature in EPiServer 7.5

Even in previous version it was possible to have several EPiServer sites sharing the same database and configuration files (often referred as Enterprise setup). However there was a one to one relationship between IIS instance and EPiServer site meaning each EPiServer site needed to have an own IIS instance configured. So even when using same IIS application pool the sites run in different AppDomains.

One consequence of running in separate AppDomains is that static properties like PageReference.StartPage or Configuration.Settings.Instance will not be shared between sites and hence have different static values in each AppDomain. It also has the consequence that event replication was needed to be configured between the sites to get cache invalidation to work.

 

Multisite in 7.5

In EPiServer 7.5 multi-site handling has been changed so now a running EPiServer instance is multi-tenant meaning a single EPiServer application running in one AppDomain can contain several EPiServer sites.

The take advantage of this the DNS/IIS should be configured so the requests are routed to that IIS application. You can e.g. have a wildcard configuration so all request of *.mydomain.com is routed to the IIS application. Then it will be possible to dynamically create/delete new sites like newcampaign.mydomain.com without doing any IIS/DNS configuration at all.

It is of course still possible to configure to run sites that share database in separate IIS instances. For example it can be good to separate large sites to different machines (to avoid that they share the same resources like memory). When doing so you need to configure remote events though.

 

Configuration changes

Previously site settings (like e.g. SiteUrl, StartPage) where defined in the configuration files. That had the consequence that when a site was added/removed the configuration file had to be updated and hence the applications where restarted. We have removed away site settings (like SiteUrl, StartPage, host mappings etc.) from the configuration files and instead those values are stored in database. This make it possible to add/remove sites dynamically without having to update configuration files and hence application restarts can be avoided

This also simplifies deployment/development scenarios since the configuration files does not need to contain as much environment specific settings.

 

SiteDefinition

To be able to run several sites in the same domain static properties like ContentReference.StartPage and Settings.Instance.SiteUrl must return differently depending on context (in previous versions these properties where “truly” static throughout the application). We have achieved this by letting those properties delegate to SiteDefinition.Current (resides in namespace EPiServer.Web).

SiteDefinition.Current is resolved from the request, meaning a comparison will be done where the host from the request will be matched against all sites from SiteDefintionRepository. The site with a host matching the request will be returned. If no match is found or if the current thread is not executing on a web request the site registered with wildcard host '*' will be returned. If no wildcard site is defined a default SiteDefinition is returned where common settings like e.g. RootPage is set but StartPage will be ContentReference.EmptyReference and SiteUrl will be null.

That means that you can add host '*' to one site if you want that site to be returned from SiteDefintion.Current when there is no web request, this can be useful e.g. when running scheduled jobs. Another possibility for code that is not running on a web request (like scheduled jobs) is to assign SiteDefinition.Current then that assignment will be set for that context.

Also worth noticing is that there is one initialization for the application where all sites are initialized (unlike before where the initialization where for a specific site since each site run in a separate AppDomain). So if you have some custom initialization module that are site dependent you could use SiteDefinitionRepository.List() to get a list of all defined sites.

 

Site Management

Sites are managed in admin mode under “Manage Websites” in admin mode. Here you can create new sites, delete unused sites and configure sites (for example specify language-host mappings). So by default is site handling a task for administrators.

However it is possible to let site creation be done by editors. One way to achieve this is to set up an event handler for IContentEvents.PublishedContent and in the event handler check if the content is of your StartPage type and if so creating a new site by storing a new instance towards SiteDefinitionRepository.

Dec 11, 2013

Comments

Dec 11, 2013 10:30 PM

I'm a little bit curious about what you write about development/deployment scenarios.

Often the staging and test and dev environments have different configuration values and the configuration files are updated during an automated deployment. Now with 7.5 when configuration values are in the database how does that simplify deployments?

Instead of config transforms the databases have to be updated either using some SQL Script or using (if possible) the configuration API through an initialization module - which would read the enviroment specific values from somewhere and updated the configuration settings in the database.

Dec 12, 2013 01:51 AM

Thanks Johan, a great article! I especially like the part where editors can be enabled to create their own sites, such as campaign sites for example which really speaks for agility.

Dec 12, 2013 09:17 AM

The values that are stored in db are e.g. SiteUrl and StartPage, those values are different in the different environments (like, test, dev, production) so normally you should not want that to be part of your deployment.
Or did I misunderstand something? what values where you refering to when saying it needs to be handled through sql script or InitializationModule?

Dec 12, 2013 10:25 AM

Johan, I was thinking about the SiteURL, a common use case might be the staging env. which might have a database which is overwritten frequently by production database to keep things in sync, but then the sitesettings have to be fixed as well.

Or when there might be a need to set up a new dev. env using production data and then the configuration would be need to be updated again.

Dec 12, 2013 10:49 AM

Setting up a dev environment could be solved by setting up a empty database and then import content into the site (that is have the production data available in an .episerverdata package). This is how we do it in our developement.

You could use Export/Import as well to transfer data from production to staging (or mirroring if you want to run it automatically).

However there are also powershell cmdlets Set-EPiSiteDefinition and Add.EPiSiteDefinition in EPiServerInstall.CMS that you can use to either create a new site or update an existing site (e.g. SiteUrl)

Jan 3, 2014 08:42 AM

This is one of the coolest features of 7.5 by far, and will really help with Enterprise scenarios. Fiddling with IIS and deployment just for a campaign site was never much fun!

Apr 15, 2014 10:57 AM

If I have a muilti-site with multiple startpages for different countries each having their own language as default, how do I do this? I have created the sites and they are all default to EN. Do I just create the startpage in the local language and the remaining pages will be default in that language?

May 5, 2014 11:42 AM

I have a single site and I get that ContentReference.StartPage is empty when I run a scheduled job. SiteDefinitionRepository contains just one SiteDefinition, so why does it fall back to empty? And where do I set up a wildcard site, which I shouldn't have to when I only have one site?

David Sandeberg
David Sandeberg Feb 9, 2015 09:59 AM

I agree with you there @Mathias Frodin, if there's only one site definition it should return that instead of empty but maybe there's a good reason for it.
You can add a wildcard for a site in admin mode under System Configuraton -> Manage Websites -> Edit Website by adding * for host name.

Please login to comment.
Latest blogs
I'm running Optimizely CMS on .NET 9!

It works 🎉

Tomas Hensrud Gulla | Nov 12, 2024 | Syndicated blog

Recraft's image generation with AI-Assistant for Optimizely

Recraft V3 model is outperforming all other models in the image generation space and we are happy to share: Recraft's new model is now available fo...

Luc Gosso (MVP) | Nov 8, 2024 | Syndicated blog

ExcludeDeleted(): Prevent Trashed Content from Appearing in Search Results

Introduction In Optimizely CMS, content that is moved to the trash can still appear in search results if it’s not explicitly excluded using the...

Ashish Rasal | Nov 7, 2024

CMS + CMP + Graph integration

We have just released a new package https://nuget.optimizely.com/package/?id=EPiServer.Cms.WelcomeIntegration.Graph which changes the way CMS fetch...

Bartosz Sekula | Nov 5, 2024

Block type selection doesn't work

Imagine you're trying to create a new block in a specific content area. You click the "Create" link, expecting to see a CMS modal with a list of...

Damian Smutek | Nov 4, 2024 | Syndicated blog

.NET 8 FAQ

I have previously written about .NET compatibility in general and .NET 8 in particular, see blog posts here , here and here . With the end of suppo...

Magnus Rahl | Nov 4, 2024