Updating content types using SharePoint Web Services (SPServices)

When you deploy an updated content type which is created from code and have new fields, your changes won’t automatically be pushed to children that inherit from your content type. This is only the case when you have created your content type using code. In the sandbox solution, I’m using the SharePoint Web Services to add new fields to content types that inherit from the updated content type.

Why the web services? With the push from Microsoft to go more and more client side, I found it a challenge to not do something with simply a farm solution or a server-side script. During the development of the web part, I’ve found 2 annoyances by using the SPServices library and jQuery/SharePoint:

  1. SPServices says every method name is unique. This is not true. There’s a method “UpdateContentType” for both the Lists.asmx and the Webs.asmx. Due to this overlooked bug, the call will always be directed to the Webs.asmx web service. I’ve modified the SPServices js file to comment out the WSops.UpdateContentType method for Webs.
  2. jQuery will always put your generated attributes to lower case. The web services are case-sensitive as you can see from the following screenshot (taken from STSSOAP.DLL, decompiled with ILSpy)
    caseSensitive

The web part itself is pretty straight forward. You’ll get a list of content types with update links.

content type updater webpart

When using firebug or another web dev tool, you can track all the calls that are made to the Webs.asmx & Lists.asmx

content type updater console window

I’ve deployed a custom content type to my site, created a list with that content type and then made an update to the site content type. As you can see there’s a column missing from the list content type:

site content type

list content type

After I click on “Update” next to “CustomContentType”, the script will detect a difference between these two and update accordingly:

soap call new fields

And the updated list content type:

updated list content type

All in all I’m pretty happy with the result. You can do a lot with just the web services from SharePoint, but they take some time to get used to. Also the documentation isn’t always great as for instance they mention to use <FieldRefs> while in the source code of the web service itself there’s only a parse of the <Fields> tag.

For the full source, or if you want to download and test the web part itself, you can go to CodePlex.

Advertisements

Deep dive into SharePoint Timer Jobs and Health Rules

In a previous post, I raised an issue regarding a SQL stored procedure not being created upon the creation of the ASP.NET Session State Service Application. This stored procedure takes care of the deletion of the expired sessions. When we check our timer jobs, we also see we have a definition which is called “State Service Delete Expired Sessions”. This obviously is connected to the regular State Service, but let’s take a closer look on how this timer job works.

Before we go deeper into the fundamentals, you’ll need a tool, which is free, called ILSpy. It’s a .NET decompiler, so if you already have one, you’re good to go. When you’ve downloaded ILSpy, extract it somewhere and you can fire it up. The main screen looks like this:

ilspy main window

Select any open libraries and remove them. This gives us a clean start:

ilspy remove standard libs

Next, we’re gonna look at the timer job itself. We need to know in which library it’s located so we can decompile it with ILSpy. Leave ILSpy open and fire up the SharePoint 2010 Management Shell. Type in the following command:

Get-SPTimerJob | ?{$_.Title -eq "State Service Delete Expired Sessions"} | Select TypeName

This will give you the following output:

Microsoft.Office.Server.Administration.StateServiceExpiredSessionJobDefinition

Great! Let’s go back to ILSpy and open the Microsoft.Office.Server library from the GAC:

ilspy open from gac

Next select the Microsoft.Office.Server library and click “Open”:

ilspy open microsoft office server from gac

Expand the library to view all the namespaces. Expand the Administration namespace and scroll down until you find the StateServiceExpiredSessionJobDefinition class. When you decompile this class, you can expand any of the methods and properties. We’re interested in the Execute method, cause that’s what fires when the timer job is executed:

ilspy decompile class

So all it does is call the static DeleteExpiredSessions(current) method on the StateSqlSession class. When we go deeper and click on the method, we can see what happens behind the scene:

ilspy click on method

Seems that all that happens is call a SQL Stored Procedure “proc_DeleteExpiredItems” from this Timer Job:

ilspy deep into method

Deep diving into Timer Jobs can give you a lot of insight into the engine of SharePoint. The following PowerShell command lists all the Titles and TypeNames from the registered Timer Job Definitions so you can go even deeper:

Get-SPTimerJob | Select Title, TypeName | fl

You’ll notice that health rule jobs are registered differently. Getting their TypeName is also a bit different. You have to use the local SPHealthRulesList:

[Microsoft.SharePoint.Administration.Health.SPHealthRulesList]::Local.Items | Select Title, @{ Label="HealthRuleType"; Expression= { $_["HealthRuleType"] } } | fl