This post is about why it took me so long to get the updated LCM version on CodePlex ;)
- Redesign, redesign and redesign. Well.. as in all applications that you built there is always a point where you decide to redesign and refactor your code and during the development of the LCM, I’ve had a lot of new insights. Mainly due the fact I was building this thing was in my spare time so I was taking all my experience from the ‘daily work’ into the project. So here are some examples of finding new stuff to reuse straight out of the SharePoint toolbox.
- (SPPersistedObject) One of the first things I was trying to do was using the PropertyBag of Central Administration webapplication to store settings in. Now this all went fine for the gathering of sitecollections on all webapplications if the timerjob was being set to the Central Admin webapp itself. But it didn’t work for getting the configuration of the SiteCapture Deletion settings when a site or a web got deleted.
Why not? Well it is good practice that every web application should have it’s own application pool account. So while running with elevated privileges you will be impersonated to the application pool account of the particular web application where the site or webs get deleted. And since that account is different then the one from the Central Admin webapp, the propertybag does not meet the requirement. So what does then? As you might have guessed.. it’s the SPPersistedObject Class. Why? Well, using this class you can save properties to the given Web Application you are configuring and therefore the application pool account has access to it. Next to this, it’s very easy using this object to have different settings per Web Application ;)
- (WebApplicationSelector) Since the stapling of the SiteDeletion Capture is only stapled to new sites and not the existing sites I created a simple function to enable the feature on all the webs and sitecollections on a given web application. To select a web application I used a standard .NET dropdownlist that featured all the webapplications of the current farm. And while looking at out-of-the-box application (like the Site Collection List page) I noticed Microsoft used a control called the WebApplicationSelector which does everything for you. One of the most useful features is that it keeps the context of the selected Web Application consistent in every page where the control is being used.
- (SchedulePicker) To schedule the timerjobs I first used two standard .NET dropdownlists. One had all the all the days of the week and the other had every hour from a day. But I didn’t find it very ideal and I started browsing the SharePoint pages again to see what MS uses to set schedules. And from there I found the SchedulePicker class in the ControlTemplates folder (it’s actually being used in the page where you define the schedule of the WSS search). I explicitly didn’t use any MOSS specific controls to ensure that the solution can be used in every SharePoint environment (though that control is much better looking ;)
- I also wanted to check on MOSS Usage Details.. Was I in for a surprise when I found out that simple things just as checking if the Usage Analysis Processing was enabled in the SSP was just not available using the OM! I still don’t really understand why the SharedResourceProvider class is internal and sealed. It makes things very complicated when you want to do something with the SSP (like determining the default SSP.. )
Using Reflector I found out that the usage reports that you see, when you enable the MOSS Usage Reporting functionality, that the report is generated using Stored Procedures that are stored in the SSP Database. Using the GUID of each sitecollection as a parameter for the stored procedure I’m able to retrieve all the processed usage data.
But(!) since it’s very unsupported to access stored procedures/tables/etc directly from the SharePoint databases I decided not to implement/hack my way around to get it.. (yet…;)
- Testing, testing a tool like the LCM is very difficult. I don’t know how your VPC looks like but mine hasn’t got a lot of sitecollections and webs that are ‘used’ as in a typical SharePoint production environment. Nor the fact that my VPC is up and running 24/7 in order to let the Usage Analysis Process to be processing.. But when you test things out, you come across some interesting things like when you change or set a lockissue on a sitecollection you are also updating the ‘lastcontentmodifieddate’. And one of the things I check whether or not a sitecollection is being used is by checking that property! ;)
- Changing my mind all the time.. I think this was the largest time consumer of them all to be honest ;)
One example : “ Should I only check sitecollections or should I also check for webs.. If I also check on webs, how do I deal with the whole locking mechanism then? And where to store the data.. Should I use two lists, working out a master detail relationship? Or should I store in a SPPersistedObject ? What is the limit of the SPPersistedObject ? “
So there you have my excuse that I took my almost a year to get it out there..