Cache Dependencies in SharePoint

While writing a data layer based on data stored in a SharePoint list, I implemented the collection as a static singleton that forced refreshes of the data every 15 minutes.

A colleague was doing something similar in a roll-up web part and we started discussing Cache Dependency objects used for the HttpContext. Could this work with SharePoint objects?

No, says "The Kid". But he gave me a good idea.

Therefore, I implemented the SPListItemCacheDependency and SPListCacheDependency objects.

To use the SPListItemCacheDependency:

   1: HttpContext.Current.Cache.Add("YourKey",


   2:     dataToCache,


   3:     new SPListItemCacheDependency(sourceItem),


   4:     Cache.NoAbsoluteExpiration,


   5:     Cache.NoSlidingExpiration,


   6:     CacheItemPriority.Normal,


   7:     null);




To use the SPListCacheDependency:





   1: HttpContext.Current.Cache.Add("YourKey",


   2:     dataToCache,


   3:     new SPListCacheDependency(sourceList),


   4:     Cache.NoAbsoluteExpiration,


   5:     Cache.NoSlidingExpiration,


   6:     CacheItemPriority.Normal,


   7:     null);




To monitor schema changes and property changes as well within the SPList and to decrease the change check poll from 10 seconds to 1 minute:





   1: HttpContext.Current.Cache.Add("YourKey",


   2:     dataToCache,


   3:     new SPListCacheDependency(sourceList, true, true, 60000),


   4:     Cache.NoAbsoluteExpiration,


   5:     Cache.NoSlidingExpiration,


   6:     CacheItemPriority.Normal,


   7:     null);




Download the code and documentation.

SharePoint Testing Base Class

I have created a base class library for testing SharePoint projects using unit tests, regression tests, integration tests and automated browser tests. It uses the two third-party applications TypeMock Isolator for SharePoint and WatIN.

As an example, if a web part calls the SPContext as:

   1: /// <summary>


   2: /// Primitive sample of web part using the <see cref="SPContext"/> object.


   3: /// </summary>


   4: /// <param name="writer">The <see cref="HtmlTextWriter"/> to write the output to.</param>


   5: protected override void Render(HtmlTextWriter writer)


   6: {


   7:     writer.Write("<h1>" + SPContext.Current.Site.RootWeb.Title + "</h1>");


   8: }




We can now mock this either by making the whole SPContext fake or by ensuring that the SPContext talks to a site collection that we have instantiated programmatically.





   1: /// <summary>


   2: /// Ensure that the <see cref="Microsoft.SharePoint.WebPartPages.WebPart"/> can render stand-alone.


   3: /// </summary>


   4: [Test]


   5: [Isolated]


   6: public void TestRenderUnit()


   7: {


   8:     SPContext context = Mock.MockSharePointContext();


   9:     Isolate.WhenCalled(() => context.Site.RootWeb.Title).WillReturn("Fake");


  10:     Assert.IsTrue(RenderToString(webPart).Contains("<h1>Fake</h1>"));


  11: }


  12:  


  13: /// <summary>


  14: /// Ensure that the <see cref="Microsoft.SharePoint.WebPartPages.WebPart"/> can render when attached to SharePoint API.


  15: /// </summary>


  16: [Test]


  17: [Isolated]


  18: public void TestRenderIntegration()


  19: {


  20:     Mock.MockSharePointContext(Web);


  21:     string evidence = "<h1>" + Site.RootWeb.Title + "</h1>";


  22:     Assert.IsTrue(RenderToString(webPart).Contains(evidence));


  23: }




Download the code, documentation and examples.

SharePoint Solution Installer Fix

When using the SharePoint Solution Installer from CodePlex, you frequently receive the error message (as discussed within the discussions on the site)

 "This solution contains resources scoped for a Web application and must be deployed to one or more Web applications"

This can easily be fixed by changing the code within InstallProcessControl.Open

   1: protected internal override void Open(InstallOptions options)


   2: {


   3:   executeCommands = new CommandList();


   4:   rollbackCommands = new CommandList();


   5:   nextCommand = 0;


   6:   SPFeatureScope featureScope = InstallConfiguration.FeatureScope;


   7:   DeactivateSiteCollectionFeatureCommand deactivateSiteCollectionFeatureCommand = null;


   8:  


   9:   switch (Form.Operation)


  10:   {


  11:     case InstallOperation.Install:


  12:       executeCommands.Add(new AddSolutionCommand(this));


  13:       if (options.WebApplicationTargets != null && options.WebApplicationTargets.Count > 0) //Added code


  14:       {


  15:         executeCommands.Add(new CreateDeploymentJobCommand(this, options.WebApplicationTargets));


  16:       }


  17:       else


  18:       {


  19:         // KML TODO - need to get rid of options.Targets? - check with Lars


  20:         executeCommands.Add(new CreateDeploymentJobCommand(this, options.Targets));


  21:       }




Add "options.WebApplicationTargets.Count > 0" on line 13.



Until this is fixed in the CodePlex release, feel free to download the fixed .exe file here.

Extended Lookup - v1.0 (Alpha)

The Extended Lookup Field for SharePoint is now in public alpha release.

The application works but still needs a lot of refactoring and general tidying up before it is suitable to use on public projects.

Known issues:

  • The control does not support multiple lookup values yet

The project is going into testing now and the following will soon be added:

  • Support for multiple lookup values
  • Unit tests released with the source code
  • Refactoring of source code
  • Full documentation of source code
  • Proper installer

You can download the feature and source code (for use in testing only) from http://www.codeplex.com/extendedlookup.