SharePoint: Calling SPList.Update Causes “Save Conflict” SPException


I’m working on a feature which creates List instances, the feature has a receiver which makes configuration changes to the created Lists. When activating the feature for the first time (when the list instance is created) the receiver executes and an SPException is thrown when the code calls the SPList.Update method.

The information in the exceptions is;

Microsoft.SharePoint.SPException: Save Conflict
Your changes conflict with those made concurrently by another user. If you want your changes to be applied, click Back in your Web browser, refresh the page, and resubmit your changes.

If  I try activating the feature again (now that the list instance is created) it works just fine. I’m assuming that the configuration changes made in the receiver code somehow conflict with the list instance creation itself.

Now, I’ve come across this quite a few times while working with List items in Event Receivers and Workflow, but never with List’s.

The original code looked as shown below, the only noteworthy thing about it was that I was using the SPWeb object from the feature receiver properties to get the SPList reference and therefore to do the list configuration update.

public override void FeatureActivated(SPFeatureReceiverProperties properties)
{
	if (!(properties.Feature.Parent is SPWeb))
		return;
	var web = properties.Feature.Parent as SPWeb;

	var fProp = properties.Definition.Properties["config"];
	if (fProp == null)
		return;
	var configFile = fProp.Value;
	if (string.IsNullOrEmpty(configFile))
		return;

	var doc = XDocument.Load(Path.Combine(properties.Definition.RootDirectory, configFile));
	foreach( var xList in doc.Descendants("list"))
	{
		var att = xList.Attribute("name");
		if (att == null) continue;

		// change list configuration
		// .....

		var theList = web.Lists[att.Value];

		// now update list changes
		theList.Update();
	}
}

Didn’t really find anthing useful after Googling about it, except this post by Eric Stallworth, so based on that I changed my code as follows and that solved the problem.

public override void FeatureActivated(SPFeatureReceiverProperties properties)
{
	var featWeb = (properties.Feature.Parent as SPWeb);
	if (featWeb == null)
		return;
	var featSite = featWeb.Site;

	var fProp = properties.Definition.Properties["config"];
	if (fProp == null)
		return;
	var configFile = fProp.Value;
	if (string.IsNullOrEmpty(configFile))
		return;

	var doc = XDocument.Load(Path.Combine(properties.Definition.RootDirectory, configFile));
	foreach( var xList in doc.Descendants("list"))
	{
		var att = xList.Attribute("name");
		if (att == null) continue;

		// create a new SPWeb object for each list modification otherwise we'll get Save Conflict exceptions
		using (var thisWeb = featSite.OpenWeb(featWeb.ID))
		{
			try
			{
				var listUpdate = false;
				var theList = thisWeb.Lists[att.Value];

				// change list configuration
				// .....

				// commit List modifications
				if (listUpate)
					theList.Update();
			}
			catch
			{
				// log the event and rethrow
				throw;
			}
		}
	}
}

Published by

Phil Harding

SharePoint Consultant, Developer, Father, Husband and Climber.

6 thoughts on “SharePoint: Calling SPList.Update Causes “Save Conflict” SPException

  1. Hi Phil Thank you for your great hel , how ever I am still facing lot of problem to get this work in my project,

    Please help me with it.

    Scenario : I have a data sheet type list – around 10 columns in it. In that I have two columns say – Status (Text Type) and Last Modified (Date type).

    Now I would love to update my Last Modified field for a row/ Item when ever I changes the status field in that column (Only for status field and not for other fields).

    I created the following Event Reciever …

    public override void ItemUpdating(SPItemEventProperties properties)
    {
    var featWeb = (properties.List.ParentWeb as SPWeb);
    if (featWeb == null)
    return;
    var featSite = featWeb.Site;
    using (var thisweb = featSite.OpenWeb(featWeb.ID))
    {
    this.EventFiringEnabled = false;

    if ((properties.ListItem[“Status”] == null) || (properties.AfterProperties[“Status”] == null))
    {
    return;
    }
    else
    {
    string currentStatus = properties.ListItem[“Status”].ToString();
    string newStatus = properties.AfterProperties[“Status”].ToString();

    if (currentStatus != newStatus)
    {
    SPListItem oItem = properties.ListItem;

    oItem[“Last Modified”] = DateTime.Now;
    oItem.UpdateOverwriteVersion();

    }

    }

    this.EventFiringEnabled = true;
    base.ItemUpdating(properties);
    }

    }

    Now the problem is while changing the value manually (need manual entry) by any user, the system is encountering a conflict. “Rows you changed where previously changed by (Same user name) on ….. Your changes conflicted with that user changes”

    and it forces me to discard my changes!! I believe this is because of the following update in the receiver.

    oItem[“Last Modified”] = DateTime.Now;
    oItem.UpdateOverwriteVersion();
    Now how can I get rid of this, or How to update both date and my changes now.

  2. The LastModified column is read only, you can’t change it yourself, it’s updated by SharePoint.

    Since you are overriding the ItemUpdating method you shouldn’t call the SPListItem UpdateXXX() methods, instead you should use the Before and After Properties properties of the SPItemEventProperties method parameter
    Remember that ItemUpdating is called before ItemUpdated and so the SPListItem has not been saved yet

Leave a Reply

Fill in your details below or click an icon to log in:

WordPress.com Logo

You are commenting using your WordPress.com account. Log Out / Change )

Twitter picture

You are commenting using your Twitter account. Log Out / Change )

Facebook photo

You are commenting using your Facebook account. Log Out / Change )

Google+ photo

You are commenting using your Google+ account. Log Out / Change )

Connecting to %s