Working with multiple sites in Sitecore

Sitecore is a multisite system, meaning that you can administer multiple websites in the same Sitecore, and that these websites can share common data (like users, templates, masters, items, etc.).

Each website in Sitecore will run in its own context, and this context is managed from the web.config. The context is set up by defining a Site. Each context has its own site definition, and it includes a “shell” site, defining the Sitecore editor context (the shell), “modules_shell” and “modules_website”, defining the context for modules running in either the Sitecore Shell or the default website.

The site called “website” defines a default web context:

<sites>
  <site name="website" language="en" rootPath="/sitecore/content" startItem="/home" cacheHtml="false" virtualFolder="/" physicalFolder="/" database="web" domain="extranet" allowDebug="true" htmlCacheSize="10MB" registryCacheSize="0" viewStateCacheSize="0" xslCacheSize="5MB" filteredItemsCacheSize="2MB" enablePreview="true" enableWebEdit="true" enableDebugger="true" disableClientData="false" />
</sites>

The attributes to pay attention to (regarding multisite solutions) are the following:

  • rootPath: The path to the root of the website. This is not the path to the first page of the website, but simply defines where Sitecore will look for items.
  • startItem: The path relative to the rootPath where the first page (home page) of the website is found.

When defining multiple websites in your Sitecore you take advantage of these 2 attributes, along with a new attribute called “hostName“, which I will explain later. First I will define my multisite structure:

In my multisite solution I will have a shared “Settings” folder, and 2 websites, each with their own “Settings” folder. This is my imaginary Sitecore tree:

/sitecore/
     /content/
          /website1/
               /home/
                    /subitems…/
               /settings/
          /website2/
               /home/
                    /subitems…/
               /settings/
          /settings/

In my web.config I will need to set up 2 new “website” sites. I add these above the existing “website” site (or I can delete the old “website” and replace it with my 2 new ones). Never add your website sites to the top of the list, as Sitecore finds the current context based on first match rather than best match:

<site hostName="site1.mysite.com" name="website_1" language="en" rootPath="/sitecore/content/website1" startItem="/home" cacheHtml="false" virtualFolder="/" physicalFolder="/" database="web" domain="extranet" allowDebug="true" htmlCacheSize="10MB" registryCacheSize="0" viewStateCacheSize="0" xslCacheSize="5MB" filteredItemsCacheSize="2MB" enablePreview="true" enableWebEdit="true" enableDebugger="true" disableClientData="false" />
<site hostName="site2.mysite.com" name="website_2" language="en" rootPath="/sitecore/content/website2" startItem="/home" cacheHtml="false" virtualFolder="/" physicalFolder="/" database="web" domain="extranet" allowDebug="true" htmlCacheSize="10MB" registryCacheSize="0" viewStateCacheSize="0" xslCacheSize="5MB" filteredItemsCacheSize="2MB" enablePreview="true" enableWebEdit="true" enableDebugger="true" disableClientData="false" />

Please notice the hostName attribute. This attribute defines on which URL your site will be hit, and which context sitecore will create when calling this url. The hostName is important in a multisite environment as this is the way Sitecore will determine which item to render.

In my example, the url http://site1.mysite.com/ hits the item at /sitecore/content/website1/home, because I have defined that the rootPath and startItem for the hostName site1.mysite.com is on that path.

Sitecore provides functions to get the root path and start item for the current context. So when working with multisite solutions you should always get a path relative to the Sitecore.Context.Site settings:

Response.Write("Current site: " + Sitecore.Context.Site.Name + "<br/>");
Response.Write("Database: " + Sitecore.Context.Site.Database.Name + "<br/>");
Response.Write("Content start path: " + Sitecore.Context.Site.ContentStartPath + "<br/>");
Response.Write("Home node: " + Sitecore.Context.Site.StartPath + "<br/>");
Response.Write("Language: " + Sitecore.Context.Language.GetDisplayName() + "<br/>");

The code above would give me the following output for the site at site1.mysite.com:

Current site: website_1
Database: web
Content start path: /sitecore/content/website1
Home node: /sitecore/content/website1/home
Language: English : English

So, in order to get the “Settings” folder for the site at hostname site1.mysite.com, I should write the following code:

Sitecore.Data.Items.Item settingsFolder = Sitecore.Context.Database.GetItem(Sitecore.Context.Site.ContentStartPath + "/settings");

In Sitecore 6, the Sitecore LinkManager uses the context to render an URL, as internal links in the Rich Text Editor is stored internally as a GUID, but when rendered, the GUID is replaced with a path relative to the current context of the GUID. So in my case: if a page below website1 links to a page below website2, the LinkManager uses the context of website2 to generate the relative path, even when the calling page is in the context of website1.
The LinkManager uses this little partytrick to allow you to cross-reference different websites and still get the right URL.

About briancaos

Developer at Pentia A/S since 2003. Have developed Web Applications using Sitecore Since Sitecore 4.1.
This entry was posted in .net, c#, Sitecore 6 and tagged , , , , , , , . Bookmark the permalink.

20 Responses to Working with multiple sites in Sitecore

  1. Hi Brian,

    Thanks for sharing. Just wanted to drop a link for more information on multisite solutions in Sitecore: http://learnsitecore.cmsuniverse.net/en/Developers/Articles/2009/10/how-to-multisite-in-sitecore.aspx

    Cheers
    Jens

  2. Pingback: Multiple languages in Sitecore « Brian Pedersen’s Sitecore and .NET Blog

  3. Pingback: Multiple languages in Sitecore | cmsnewstoday.com

  4. Verndale says:

    Great post! We have seen these questions come up a lot and have decided to include them in our FAQ section of our site- here’s the link for more information.

    http://www.verndale.com/sitecore-cms.aspx

  5. Brian, would you be able to provide enlightenment on how to access the top level settings folder?

    I recently just started on a multi-site project and have my structure set up similar to yours (just a few more sites under content), but I still have a shared content item sitting in the top level. I’m stumped as to how to access the shared settings though.

  6. Brian, of course I would spend 45minutes to an hour searching for a solution and then start trying random methods; finding one that works as a solution.

    I’m not sure if there is a better practice of doing so, but I just called the context database and then grabbed the root item. This happened to be ‘sitecore’ — Where I can then grab the global item from there.

  7. briancaos says:

    I do the same. My multisite solutions always has some sort of “Global” or “Shared” folder. I simply hard-code the path to this foder, grabbing it like so: Database.GetItem(“/sitecore/content/global/settings”);
    Just remember not to place any items in the global/shared folder that is used as pages, as the LinkManager will provide you with a strange off-context link.

  8. Thomas says:

    2 Questions:

    1) How does the Media Library play into this? If I want a different media library for each site?
    2) With cloning introduced in 6.4, can I clone one site to another? (I don’t see why not…it seems to have nothing/little to do with the rendering of them on the web.)

  9. briancaos says:

    1) The media library is shared across all websites, as the media library has no context. If you want complete seperation of all aspects of Sitecore within your websites, you should look at Sitecore Foundry instead. If it’s a question of hiding parts of the media library from users, you should create seperate roles for each of your websites, and apply the roles to different media library folders.

    2) Cloning in Sitecore 6.4 is per-item cloning. It is possible to clone a complete website to another, but you’ll have to do it per item, which is quite a tedious task if you have 1000’s of items in one website.

  10. Pingback: Sitecore Language selector – creating a country selector « Brian Pedersen’s Sitecore and .NET Blog

  11. Pingback: Sitecore Language selector – creating a country selector | CMS News Today

  12. clinton says:

    I’ve just been toying with Sitecore 6.4 Cloning, Briancaos and Thomas – for point 2) You can clone an entire site by selecting the Home item and selecting Clone. It will Clone every sub items to a new website. Very awesome, this is exactly what i’ve been looking for.

  13. Pingback: Using Sitecore Jobs « Brian Pedersen’s Sitecore and .NET Blog

  14. Pingback: Using Sitecore Jobs « Brian Pedersen’s Sitecore and .NET Blog

  15. Pingback: Sitecore links in multisite solutions – SiteResolving « Brian Pedersen’s Sitecore and .NET Blog

  16. Pingback: Sitecore cross-site and cross-language links resolved in 6.4.1 release 120113 « Brian Pedersen’s Sitecore and .NET Blog

  17. Pingback: Best way to configure Multi Site in Sitecore | My Website

  18. Pingback: Sitecore Multisite Basics | Sitecore basics!

  19. Pingback: Multisites in Sitecore – A Collection of articles on web development by Nataraj Gandhi Arunachalam

  20. Pingback: Sitecore: Interview questions | Sitecore Tweaks

Leave a Reply

Fill in your details below or click an icon to log in:

WordPress.com Logo

You are commenting using your WordPress.com account. Log Out / Change )

Twitter picture

You are commenting using your Twitter account. Log Out / Change )

Facebook photo

You are commenting using your Facebook account. Log Out / Change )

Google+ photo

You are commenting using your Google+ account. Log Out / Change )

Connecting to %s