One long-established way of working around this is to deploy such files to the server filesystem, rather than into a specific SharePoint site. Commonly, the ‘_layouts’ folder under SharePoint root directory (i.e. ‘14’ for SharePoint 2010 or ‘15’ for SharePoint 2013) was used for such shared files. A second method involved deploying files as ‘uncustomized’, or ‘GhostableInLibrary’. This works by adding a list item ‘stub’ for the file into each site or library, but since the file is also deployed to the SharePoint server’s filesystem, the file contents are pulled from there. In the content database, the SQL record literally has a pointer to the location of the physical file on the SharePoint server (again, this would be somewhere under SharePoint root directory).
Although not just related to app development, I included this article in my 10 part series on apps:
- SharePoint 2013 apps – architecture, capability and UX considerations
- Getting started – creating lists, content types, fields etc. within a SharePoint app (provisioning)
- Working with data in the app web, and why you should
- Access end-user data (in the host web) from a SharePoint 2013 app
- Rolling out SharePoint 2013 apps to the enterprise - tenant scope and PowerShell installs
- Azure is the new SharePoint ‘_layouts’ directory [this article]
- “Host web apps” – provisioning files (e.g. master pages) to the host web
- “Host web apps” – provisioning fields and content types
- Deploying SP2013 provider-hosted apps/Remote Event Receivers to Azure Websites (for Office 365 apps)
- Working with web parts within a SharePoint app
Cloud says no
Once you start to develop sandboxed solutions or SharePoint 2013 apps, of course the technique above cannot be used. Files cannot be provisioned to the server filesystem, since the servers might not belong to you – in the case of Office 365, the servers are run by Microsoft. So what can we do?
As you can imagine, we now regain the ability to store a single instance of files, even if not on the SharePoint server itself. To illustrate, here’s what the ‘default’ and ‘centralized’ approaches look like in pictures:
Default app/sandboxed development model:
Centralized development model:
When should I be considering this?
I think this broad approach is relevant to the following scenarios:
- Developing sandboxed solutions
- Developing SharePoint-hosted apps
- Developing auto-hosted apps
If you are working in these models and not currently considering this approach, perhaps you should. Yes, it can make the initial development process more complex (since your app is effectively stored in multiple places), but rolling out updates once in production will most likely be much simpler. Even if you don’t like this idea, then at least ensure you’ve considered your update mechanisms for these files.
An interesting observation (if it hadn’t occurred to you already), is that provider-hosted apps are mainly stored outside SharePoint – including their business logic. This means, amongst other things, that the creator has the option of making fairly big changes to the app without requiring the app to be upgraded or resubmitted to the Store. Certainly worth bearing in mind.
I think the following also need to be considered:
- Alternative storage flavors:
- Although I’ve mainly discussed storing files in simple Azure websites, my colleague Salvatore di Fazio has also considered the use of Azure CDN –see his post Sharepoint 2013 – How to share contents between Apps