如何通过CSOM C#修改SharePoint的Created By字段?遇只读字段报错
嘿,我来帮你搞定这个问题!你碰到的Invalid data has been used to update the list item. The field you are trying to update may be read only报错,主要是因为Created By是SharePoint的系统只读字段,而且你的代码还有几个关键细节没做对,下面我给你梳理清楚解决方案:
为什么你的代码会报错?
你的代码有两个核心问题:
- 字段名称错误:你用了显示名"Created by",但SharePoint内部识别的字段名是
Author,用显示名赋值肯定会出问题 - 字段类型与修改方式错误:Created By是用户类型字段,不能直接赋值字符串;而且它是系统只读字段,普通的
Update()方法没有权限修改,得用专门的方法
修改单个列表项(ID=13)的正确代码
下面是修正后的代码,注释里标清楚了关键步骤:
using (ClientContext cc = new ClientContext("http://sharepoint-site-url")) { // 根据你的环境设置凭据:On-Prem用NetworkCredential,SPO用SharePointOnlineCredentials // 示例(On-Prem): // cc.Credentials = new NetworkCredential("你的用户名", "你的密码", "域名"); // 示例(SPO): // var securePassword = new SecureString(); // foreach (char c in "你的密码") securePassword.AppendChar(c); // cc.Credentials = new SharePointOnlineCredentials("你的账号@租户.onmicrosoft.com", securePassword); // 获取目标列表 List list = cc.Web.Lists.GetByTitle("sharepointlistname"); cc.Load(list); cc.ExecuteQuery(); // 获取要设置为Created By的用户(必须通过SharePoint的User对象,不能直接写字符串) User targetUser = cc.Web.EnsureUser(@"domain\Dinesh"); // 替换成你的用户账号格式 cc.Load(targetUser); cc.ExecuteQuery(); // 获取要修改的列表项(ID=13) ListItem item = list.GetItemById(13); cc.Load(item); cc.ExecuteQuery(); // 设置Created By字段(内部名称是Author) item["Author"] = targetUser.Id; // 使用SystemUpdate(false)修改系统字段,false表示不更新Modified/Modified By字段 item.SystemUpdate(false); cc.ExecuteQuery(); Console.WriteLine("单个列表项修改成功!"); }
修改所有列表项的代码
如果要批量修改所有项,记得要分页处理(避免触发列表视图阈值),代码如下:
using (ClientContext cc = new ClientContext("http://sharepoint-site-url")) { // 设置凭据(同上) // cc.Credentials = ...; List list = cc.Web.Lists.GetByTitle("sharepointlistname"); cc.Load(list); cc.ExecuteQuery(); // 获取目标用户 User targetUser = cc.Web.EnsureUser(@"domain\Dinesh"); cc.Load(targetUser); cc.ExecuteQuery(); // 分页获取列表项,每次取500条(可根据阈值调整) CamlQuery query = CamlQuery.CreateAllItemsQuery(500); ListItemCollectionPosition position = null; do { query.ListItemCollectionPosition = position; ListItemCollection items = list.GetItems(query); cc.Load(items); cc.ExecuteQuery(); // 批量修改当前页的项 foreach (ListItem item in items) { item["Author"] = targetUser.Id; item.SystemUpdate(false); } // 提交当前页的修改 cc.ExecuteQuery(); // 获取下一页的位置 position = items.ListItemCollectionPosition; } while (position != null); // 直到所有页处理完成 Console.WriteLine("所有列表项修改成功!"); }
关键注意事项
- 权限要求:必须拥有网站集管理员权限,或者列表的完全控制权限,才能修改系统字段;如果是SPO,也可以用AppOnly权限来实现
- 字段内部名称:所有系统字段都要用内部名称,比如Created对应
Created,Created By对应Author,Modified对应Modified,Modified By对应Editor - SystemUpdate方法:
SystemUpdate(false)不会修改Modified和Modified By字段,如果需要同步更新这些字段,可以传true
内容的提问来源于stack exchange,提问作者Dinesh
相关产品推荐
相关产品推荐

