如何在第一次保存之前编程方式修改项目级别权限?
题
我有一个关于我已经写过自定义表单的列表的严格权限的情况。要求是,在创建时,基于元数据,只有某些用户只能访问读写项目。
我的第一次尝试是将此放在列表中的事件接收器中,以确保在添加项目时更新权限。我将项目放在项目中添加的事件,因为在项目中添加了我没有一种方法来提升权限并获取项目的提升实例(我知道)。这导致了不需要的延迟,虽然短暂,但在项目创建的时间之间以及代码实际运行的时间之间。
我尝试的下一件事是在创建项目后立即放置窗体中的项目权限,因为我将为项目的ID提供ID,所以我可以在提升的上下文中检索它(我希望物品成为在当前用户的上下文中创建。这是有问题的,因为一旦实现这种方法,我们在05%的时间内获得了在项目上运行的工作流程中的错误,因此创建说:“无法启动工作流程。工作流无法访问已应用的项目。“ (可能值得注意这是一个nintex工作流程) - 我假设问题是由于某些竞争条件,在Item.update()中间设置的权限,工作流程试图同时启动。
理想情况下,我希望能够更新第一项更新(创建)或逐项事件期间更新权限,但我不确定如何执行此操作,而无需提升整个过程,然后由此创建该项目系统帐户而不是实际创建该项目的用户。
我可以使用哪些选项?
解决方案
您最初使用其逐项事件的方式是正确的。虽然只有一步一步 - 您可以通过将其更改为同步而不是异步运行来立即运行。
其他提示
您可以尝试的一种方法,可以在该列表中启用内容批准。这将意味着,每当创建一个新项目时,它将保持在等待状态之前,直到它被批准。当一个项目处于挂起状态时,只有当您选择以下设置:谁应该在本文档库中查看草稿项时,只能看到项目的始发者和有权管理列表和库的人员可以看到它? - >只有可以批准项目的用户(以及项目的作者)。 然后,您可以使用逐项命令的事件来更改文件的权限,并放入批准的状态。
我希望这有助于您在您的特定情景中。
您应该能够模拟创建该项目的用户或在您的代码中进行更改。
public override void ItemUpdating(SPItemEventProperties properties)
{
base.ItemUpdating(properties);
SPUserToken objSPUserToken = properties.OriginatingUserToken;
if (objSPUserToken != null)
{
using (SPSite objSPSite = new SPSite(properties.SiteId, objSPUserToken))
{
using (SPWeb objSPWeb = objSPSite.OpenWeb())
{
//You can perform user context specific changes here...
}
}
}
}
.
我完成了解决这个问题的是什么,而不是通过工作流的设置自动启动工作流,我们“手动”在更新权限后通过代码启动工作流程。
string workflowId = "{...}"; //dynamically retrieve workflow id
SPWorkflowManager workflowManager = item.Web.Site.WorkflowManager;
SPWorkflowAssociationCollection workflowCollection = item.ParentList.WorkflowAssociations;
foreach (SPWorkflowAssociation workflow in workflowCollection)
{
if (String.Compare(workflow.BaseId.ToString("B"), workflowId, true) == 0)
{
workflowManager.StartWorkflow(item, workflow, workflow.AssociationData, true);
break;
}
}
.