пятница, февраля 27, 2009

PS и WSS 2

Во второй серии балета экспериментов пытаемся сделать при помощи PS-технологии нечто содержательное. Например, достаточно часто требуется для элементов списка (документов библиотеки) оставить доступ только создателю и некоторым группам пользователей, отобрав его у всех остальных. Достаточно легко эта операция проделывается при помощи рабочего процесса с использованием activities из пакета Useful Sharepoint Designer Custom Workflow Activities. Алгоритм достаточно простой:

  1. Убрать наследование разрешений
  2. Установить разрешения для групп
  3. Установить разрешения для создателя.

Для использования в обработчике событий PowerEventReceivers имеет смысл написать функцию, выполняющую нужные действия, и вызывать её из обработчиков ItemAdded и ItemUpdated. Функция получается такая:

function ResetPermissions{
$groupsNames = "Администрация", "ИТ Отдел";
$permissionLevelName = "Полный доступ";
$permissionLevel = $null;
$mustSave=$false;
if( -not $item.HasUniqueRoleAssignments){
try{ $item.BreakRoleInheritance($false); }
catch{
# у пользователя нет нужных разрешений
return;
}
}
if($item.HasUniqueRoleAssignments){
try{
$permissionLevel = $web.RoleDefinitions[$permissionLevelName];
}catch{
# у пользователя нет разрешений или неверно задан уровень
}
if($permissionLevel -ne $null){
try{
foreach ($groupName in $groupsNames) {
$group = $null;
try{$group = $web.Groups[$groupName];}catch{} #on web
if($group -eq $null) {try{$group = $web.Site.Rootweb.Groups[$groupName];}catch{}} #on site
if($group -eq $null) {continue;} #wrong group
$role = New-Object -TypeName Microsoft.SharePoint.SPRoleAssignment -ArgumentList $group;
$role.RoleDefinitionBindings.Add($permissionLevel);
$item.RoleAssignments.Add($role);
$mustSave=$true;
}
}catch{
if(-not $mustSave){
return;
}
}
#Creator
try{
$user = (($item.Fields[[Microsoft.SharePoint.SPBuiltInFieldId]::Author] `
-as [Microsoft.SharePoint.SPFieldUser]).GetFieldValue($item[[Microsoft.SharePoint.SPBuiltInFieldId]::Author].ToString()) `
-as [Microsoft.SharePoint.SPFieldUserValue]).User;
$userRole = New-Object -TypeName Microsoft.SharePoint.SPRoleAssignment -ArgumentList $user; #SPRoleAssignment
$userRole.RoleDefinitionBindings.Add($permissionLevel);
$item.RoleAssignments.Add($userRole);
$mustSave=$true;
}catch{
if(-not $mustSave){
return;
}
}
}
if($mustSave){ # сохранить изменения
$item.SystemUpdate();
}
}
## End of ResetPermissions ##
}

Такая функция исполняется ожидаемым образом только когда изменения списка проводит пользователь, имеющий права на изменение разрешений. У пользователя, не имеющего таких прав, дело заканчивается неудачей и разрешения на элемент списка наследуются от списка. Внутри скрипта дело поправить не удаётся (нужно выполнить код с системными привилегиями), поэтому следует искать другие выходы.

Выходов, как обычно, находится два: заставить изменить элемент пользователя с нужными правами или применить другие средства. Можно, например, в списке настроить обязательное утверждение элементов, и в момент утверждения все необходимые действия будут выполнены.

Из “других” средств можно применить SharePoint Designer PowerActivity того же автора. В рабочем процессе, основанном на этой “активности”, можно применить тот же самый скрипт, что и в обработчике событий. С учётом того, что рабочие процессы выполняются в контексте системной учётной записи, изменения проходят у любого пользователя, имеющего разрешения на добавление и/или редактирование элементов списков. Платой за это служит необходимость иметь SPD.

Тексты скриптов для обработчика (RecieverScript.ps1) и для PowerActivity (WFScript.ps1) можно взять здесь.


Technorati Tags: ,

Комментариев нет: