Как очистить унаследованный доступ
В этой статье описывается, как удалить унаследованный доступ для записей при изменении каскадной конфигурации таблицы в Microsoft Dataverse.
Симптомы
После изменения каскадного поведения связи таблицы для действия Reparent или Общего доступа на No Cascade вы будете иметь доступ к связанным записям, которые должны быть удалены.
Как проверить доступ к связанным записям
Пользователи могут сообщить о том, что у них есть непредвиденный доступ к записям. Существует два способа проверки доступа к связанным записям: с помощью функции проверки доступа или RetrieveAccessOrigin
сообщения.
Использование функции проверки доступа
Используйте функцию Check Access в приложениях на основе моделей, чтобы проверить, кто имеет доступ к записи. Администраторы могут использовать эту функцию для проверки отдельных пользователей или всех пользователей, имеющих доступ к записи.
При использовании средства проверки доступа отображается список причин, по которым у пользователя есть доступ. Некоторые из этих причин указывают на то, что общий доступ был предоставлен из-за доступа к связанной записи. Например:
- Запись была предоставлена мне, потому что у меня есть доступ к связанной записи.
- Запись была предоставлена группе, в которой я являюсь членом, так как команда имеет доступ к связанной записи.
Использование сообщения RetrieveAccessOrigin
Разработчики могут использовать RetrieveAccessOrigin
сообщение для обнаружения доступа пользователей к записи. Это сообщение возвращает предложение, описывающее, почему у пользователя есть доступ. Любой из следующих результатов указывает, что доступ был предоставлен из-за общего доступа к связанной записи:
PrincipalId is owner of a parent entity of object (<record ID>)
PrincipalId is member of team (<team ID>) who is owner of a parent entity of object (<record ID>)
PrincipalId is member of organization (<organization ID>) who is owner of a parent entity of object (<record ID>)
PrincipalId has access to (<parent record ID>) through hierarchy security. (<parent record ID>) is owner of a parent entity of object (<record ID>)
Дополнительные сведения см. в разделе "Определение того, почему у пользователя есть доступ к коду".
Причина
При изменении каскадного поведения связи с таблицами Dataverse запускает асинхронное задание для удаления пользователей доступа ранее. Однако это задание может завершиться ошибкой, что приведет к тому, что пользователи сохраняют доступ.
Решение
Первым шагом для устранения этой проблемы является повторное создание системного задания для удаления доступа. Если задание завершается ошибкой, разработчик может использовать ResetInheritedAccess
сообщение для применения изменения к указанному набору записей.
Повторное создание системного задания для удаления доступа
Разработчики могут использовать CreateAsyncJobToRevokeInheritedAccess
сообщение для повторного создания асинхронного задания.
Используйте класс Microsoft.Xrm.Sdk.Messages.CreateAsyncJobToRevokeInheritedAccessRequest.
/// <summary>
/// Creates and executes an asynchronous cleanup job to revoke inherited access granted through cascading inheritance.
/// </summary>
/// <param name="service">The authenticated IOrganizationService instance to use.</param>
/// <param name="relationshipSchemaName">The schema name of the entity relationship.</param>
public static void CreateAsyncJobToRevokeInheritedAccessExample(IOrganizationService service, string relationshipSchemaName)
{
var request = new Microsoft.Xrm.Sdk.Messages.CreateAsyncJobToRevokeInheritedAccessRequest()
{
RelationshipSchema = relationshipSchemaName
};
service.Execute(request);
}
Дополнительные сведения об использовании сообщений с пакетом SDK для .NET.
Действие CreateAsyncJobToRevokeInheritedAccess
создает новое асинхронное задание с именем RevokeInheritedAccess
. Вы можете отслеживать успешное выполнение этого задания, но нет способа предварительного просмотра записей, которые будут затронуты. Дополнительные сведения см. в разделе "Мониторинг системных заданий " или управление заданиями системы с помощью кода.
Сброс унаследованного доступа
Если повторное создание системного задания для удаления доступа завершается сбоем, разработчик с правами системного администратора или настройщика системы может использовать ResetInheritedAccess
сообщение для назначения подмножества соответствующих записей. Для удаления доступа ко всем записям может потребоваться несколько раз использовать это сообщение.
/// <summary>
/// Resets the inherited access for the matching records.
/// </summary>
/// <param name="service">The authenticated IOrganizationService instance to use.</param>
/// <param name="fetchXml">The fetchxml query.</param>
public static void OutputResetInheritedAccess(IOrganizationService service, string fetchXml)
{
var parameters = new ParameterCollection()
{
{ "FetchXml", fetchXml}
};
var request = new OrganizationRequest()
{
RequestName = "ResetInheritedAccess",
Parameters = parameters
};
var response = service.Execute(request);
Console.WriteLine(response.Results["ResetInheritedAccessResponse"]);
}
Дополнительные сведения об использовании сообщений с пакетом SDK для .NET.
Сообщение ResetInheritedAccess
пытается выполнить синхронно, если не существует большого количества соответствующих записей. ResetInheritedAccessResponse
Затем значение заканчиваетсяExecutionMode : Sync
. Если есть много соответствующих записей, операция занимает больше времени, а значение заканчивается ExecutionMode : Async
. Создается системное задание Denormalization_PrincipalObjectAccess_principalobjectaccess:<caller ID>
и вы можете отслеживать успешность этого задания. Дополнительные сведения см. в разделе "Мониторинг системных заданий " или управление заданиями системы с помощью кода.
Сообщение ResetInheritedAccess
требует запроса FetchXml для идентификации записей. Этот запрос должен соответствовать следующим требованиям:
- Используйте таблицу
principalobjectaccess
(POA). - Возвращает только
principalobjectaccessid
столбец. - Не должно включать элементы
link-entity
. Невозможно добавить соединение в другую таблицу. - Фильтруйте только столбцы
principalobjectaccess
таблицы.
Эта таблица доступна веб-API в качестве типа сущности principalobjectaccess. Она не включена в ссылку на таблицу или сущность Dataverse, так как таблица POA не поддерживает операцию прямого изменения данных. Чтобы создать запрос FetchXml, необходимо знать столбцы этой таблицы.
Столбцы таблицы POA
Необходимо создать запрос FetchXml, используя только эти столбцы.
Логическое имя | Type | Описание |
---|---|---|
accessrightsmask |
Целое | Содержит объединенные значения элементов перечисления AccessRights для прав доступа, которые у субъекта есть напрямую. |
changedon |
Дата/время | Последняя дата изменения доступа субъекта к записи. |
inheritedaccessrightsmask |
Целое | Содержит объединенные значения элементов перечисления AccessRights для прав доступа, применяемых из-за наследования. |
objectid |
Уникальный идентификатор | Идентификатор записи, к которому имеет доступ субъект. |
objecttypecode |
Целое | Значение EntityMetadata.ObjectTypeCode , соответствующее таблице. Это значение не обязательно совпадает с различными средами. Для пользовательских таблиц она назначается в зависимости от порядка создания таблицы. Чтобы получить это значение, может потребоваться просмотреть метаданные таблицы. Существует несколько средств сообщества, чтобы найти это. Ниже приведено решение от Корпорации Майкрософт: обзор определений таблиц в вашей среде. |
principalid |
Уникальный идентификатор | Идентификатор пользователя или команды с доступом. |
principalobjectaccessid |
Уникальный идентификатор | Первичный ключ таблицы POA. |
principaltypecode |
Целое | Код типа субъекта. SystemUser = 8, Team = 9. |
Следующие значения элементов перечисления AccessRights применяются к столбцам и inheritedaccessrightsmask
столбцамaccessrightsmask
:
Тип доступа | значение | Описание |
---|---|---|
None |
0 | Нет доступа. |
Read |
1 | Право на чтение записи. |
Write |
2 | Право на обновление записи. |
Append |
4 | Право добавить указанную запись в другую запись. |
AppendTo |
16 | Право добавить другую запись к указанной записи. |
Create |
32 | Право на создание записи. |
Delete |
65 536 | Право на удаление записи. |
Share |
262,144 | Право предоставить общий доступ к записи. |
Assign |
524,288 | Право назначить указанную запись другому пользователю или группе. |
Возможно, inheritedaccessrightsmask
значение обычно равно 135 069 719. Это значение включает все типы доступа, за исключением Create
случаев, когда эти права применяются только к уже созданным записям.
Примеры FetchXml
В этом разделе приведены некоторые примеры запросов FetchXml, которые можно использовать с сообщением ResetInheritedAccess
. Дополнительные сведения см. в разделе "Использование FetchXML для создания запроса".
Сброс унаследованного доступа, предоставленного определенному пользователю для определенной учетной записи
<fetch>
<entity name="principalobjectaccess">
<attribute name="principalobjectaccessid"/>
<filter type="and">
<condition attribute="principalid" operator="eq" value="9b5f621b-584e-423f-99fd-4620bb00bf1f" />
<condition attribute="objectid" operator="eq" value="B52B7A48-EAFB-ED11-884B-00224809B6C7" />
</filter>
</entity>
</fetch>
Сброс унаследованного доступа, предоставленного всем дочерним строкам для указанного типа объекта
<fetch>
<entity name="principalobjectaccess">
<attribute name="principalobjectaccessid"/>
<filter type="and">
<condition attribute="objecttypecode" operator="eq" value="10042" />
</filter>
</entity>
</fetch>
Сброс унаследованного доступа, предоставленного указанному пользователю для всех типов объектов
<fetch>
<entity name="principalobjectaccess">
<attribute name="principalobjectaccessid"/>
<filter type="and">
<condition attribute="principalid" operator="eq" value="9b5f621b-584e-423f-99fd-4620bb00bf1f" />
</filter>
</entity>
</fetch>