如何从Sharepoint客户端模型中的内容类型中删除站点列引用

时间:2015-02-04 10:57:41

标签: c# sharepoint csom

我正在尝试直接从我的代码中删除sharepoint网站上的网站列。这些站点列目前在某些内容类型下引用。所以当我执行代码时

//Delete the site-column
conFields.DeleteObject();
clientContext.ExecuteQuery();
break;

它抛出异常

  

无法删除内容类型中包含的网站列。删除之前删除对此站点列的所有引用。

任何人都可以建议首先从内容类型中删除该引用,然后删除网站列。

以下是代码:

//availableCT is my content-type
 FieldCollection fieldColl = availableCT.Fields;
clientContext.Load(fieldColl);
clientContext.ExecuteQuery();
foreach (Field field in fieldColl)
{
  //columnFromList is the column taht is to be deleted
  if (field.InternalName.Equals(columnFromList))
  {
    field.DeleteObject();
    clientContext.executeQuery();
  }
}

每当我运行此代码时,它都会抛出异常:

  

其他信息:无法删除内容类型或列表中包含的网站列。请在删除之前删除此站点列的所有实例。

请建议我以编程方式完成此任务的方法。仅供参考,当我尝试从我的Sharepoint网站删除它时,它会被删除而不会出现任何错误。

1 个答案:

答案 0 :(得分:0)

由于在内容类型中引用了站点列,因此会发生指定的错误。

以下示例(实现为Extension methods)演示了在内容类型中引用网站列时如何删除网站列:

public static class FieldExtensions
{
    /// <summary>
    /// Remove column and reference from specific content types
    /// </summary>
    /// <param name="field"></param>
    /// <param name="contentTypeId"></param>
    public static void DeleteObject(this Field field,string contentTypeId)
    {
        var ctx = field.Context as ClientContext;
        if (!field.IsPropertyAvailable("Id"))
        {
            ctx.Load(field, f => f.Id);
            ctx.ExecuteQuery();
        }
        //Firstly, remove site column from content type
        var contentType = ctx.Site.RootWeb.ContentTypes.GetById(contentTypeId);
        var fieldLinks = contentType.FieldLinks;
        var fieldLinkToRemove = fieldLinks.GetById(field.Id);
        fieldLinkToRemove.DeleteObject();
        contentType.Update(true); //push changes
        //Then remove column
        field.DeleteObject();
    }


    /// <summary>
    /// Remove column and references from all content types
    /// </summary>
    /// <param name="field"></param>
    /// <param name="includeContentTypes"></param>
    public static void DeleteObject(this Field field, bool includeContentTypes)
    {
        var ctx = field.Context as ClientContext;
        if (!field.IsPropertyAvailable("Id"))
        {
            ctx.Load(field, f => f.Id);
            ctx.ExecuteQuery();
        }
        //Firstly, remove site column link from all content types
        ctx.Load(ctx.Site.RootWeb.AvailableContentTypes, cts => cts.Include(ct => ct.FieldLinks));
        ctx.ExecuteQuery();
        foreach (var ct in ctx.Site.RootWeb.AvailableContentTypes)
        {
            var containsField = ct.FieldLinks.Any(fl => fl.Id == field.Id);
            if (containsField)
            {
                var fieldLinkToRemove = ct.FieldLinks.GetById(field.Id);
                fieldLinkToRemove.DeleteObject();
                ct.Update(true); //push changes         
            }
        }
        //Then remove site column
        field.DeleteObject();
    }
}

<强>用法

所有内容类型中删除网站列和引用:

using (var ctx = ClientContext(webUri))
{        
    var siteFields = ctx.Site.RootWeb.Fields;
    var fieldToDel = siteFields.GetByInternalNameOrTitle(fieldName);
    fieldToDel.DeleteObject(true);
    ctx.ExecuteQuery();
}

从内容类型中删除网站列和引用:

using (var ctx = ClientContext(webUri))
{        
   //find content type
   var result = ctx.LoadQuery(ctx.Site.RootWeb.AvailableContentTypes.Where(ct => ct.Name == "Order Document"));
   ctx.ExecuteQuery();

   if (result.Any())
   {
       var ctId = result.First().Id.StringValue;
       var siteFields = ctx.Site.RootWeb.Fields;
       var fieldToDel = siteFields.GetByInternalNameOrTitle(fieldName);
       fieldToDel.DeleteObject(ctId);
       ctx.ExecuteQuery();
   }
}