1

I have a Web scoped Feature which provisions a number of Content Types, List Templates & Instances, Custom Actions etc that enables a discrete set of functionality. I also have a number of WebParts which use the Content Types, Lists etc provisioned by this Feature to provide reusable functionality. In SP2010 WebParts can only be deployed through Site scoped Features as they must go into the appropriate gallery so therefore I can't stop them being available even in a Web which doesn't have my Feature activated.

My question then is how to manage the dependency on the Web scoped feature being activated inside the code for the WebParts? Is there a recognised best practice approach to this? Should I just handle exceptions so that the WebPart doesn't 'break' the page it is added to if the required Feature isn't activated? Or is there a neat way to check the dependency at the time the WebPart is added to the page, alert the user and stop it being added if the Feature isn't activated?

2 Answers 2

2

Two solutions comes to mind:

  • Implement some requirements validation logic on your web part. The user will still be able to add the web part, but the web part simply won't work and will instead display an appropiate message.

  • Go the extra mile and implement a custom WebPartGallerySourceBase: this way you can provide custom links in the insert web part window (and hide them when appropiate). Notice that the WebPartGallerySourceBase class is almost undocumented... this blog post provide a good start up if you decide to follow this road. Keep also in mind that the web part could be added in a way that bypass your Web Part Gallery Source extender, so it's best to include some validation logic in the web part as well.


As per user comment the third solution is not applicable.

Basic level: add a dependency on the feature that provision the web part. This will protect you from most basic issues, but depending on your real use-case could prove insufficient. Remember also that a feature dependency can only block activation of the feature but won't provide any protection after that.

5
  • FeatureDependency won't work as the dependency already exists in reverse i.e. the web scoped feature is dependent on the site scoped feature containing the webparts. In fact they are mutually dependent, though for the site scope only with respect to these webparts. +1 because the custom WebPartGallerySourceBase seems like it could be an excellent solution, though I haven't implemented it yet I will let you know if it works. There is another good blog post on the subject from Chris O'Brien here - sharepointnutsandbolts.com/2012/01/… Commented Feb 1, 2012 at 15:03
  • Sorry - didn't saw you already have the reverse dependence. I suppose that means that a custom WebPartGallerySourceBase is your best source. Anyway, like I said, the dependency would only have protected you agains first activation of the feature... an user could delete a list after the feature has been activated. I will update the answer to incorporate your notice. Commented Feb 1, 2012 at 15:18
  • 1
    +1. WebPartGallerySourceBase is a very good option in most cases, and actually it is not very hard to implement. I used this approach and I can assure that it is lightweight, flexible and powerful. However, cannot resist mentioning that an advanced user can get around this limitation and add the webpart to any other site within farm, for example by using EcmaScript Client Object Model. Commented Feb 1, 2012 at 23:09
  • @omlin: good point. Maybe it wasn't clear from my original answer, so I have edited it to include your suggestion. Thank you. Commented Feb 2, 2012 at 8:02
  • I implemented the WebPartGallerySourceBase this morning and put the feature dependency logic into a gallery source base which a derived gallery source class can instantiate with 1-n dependencies. As you recommended, omlin, I added the check inside the web part as well to scupper those pesky advanced users! Thank you both for contributing to an elegant solution. Commented Feb 2, 2012 at 13:27
2

In the webpart, you can add something like following:

void Page_Load (object sender, EventArgs e) 
{

    if(SPContext.Current.Web.Features[MyFeatures.MyFeatureGuid] == null)
       throw new Exception("This webpart is not allowed here!");

    // ...
}

, where MyFeatures.MyFeatureGuid represents your feature guid.

Or you can render the error inside the webpart, because throwing the exception will obviously break the whole page.

P.S. Btw, the following CodePlex project can help you to generate MyFeatures class automatically: http://t4sharepoint.codeplex.com/

1
  • Thanks omlin. This is the sort of solution I envisaged but was wondering if there was a WebPart.OnAdding or similar event I could override to do the check. I know I could use a custom WebPartManager and override OnWebPartAdding but I want to keep this contained to the WebPart itself so it will apply on any page. +1 for the link to the T4 just because I am a big T4 fan and can think of lots of other applications of something similar. Commented Feb 1, 2012 at 14:59

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Not the answer you're looking for? Browse other questions tagged or ask your own question.