role-edit · diff

git:20261002.261364e to git:20261013.179d77a

52 added, 21 removed. Audit A to A.

---
name: role-edit
description: Типизированно изменить права существующей роли 1С по логическому адресу, сохранив RLS, шаблоны и остальные права.
argument-hint: <at> <operations>
allowed-tools:
- Read
- Glob
---
# /unica:role-edit — точечное редактирование прав роли
## MCP routing
- - Preferred path: use MCP `unica` tool `unica.apply` с операцией `right.set`.
- - Роль называет адрес: `args.at` вида `<набор>:Role.<Имя>`. Физический
- `Rights.xml` — внутренняя деталь; наружу путь отдаёт только аварийный
- `unica.resolve`, и в обычном ходе работы он не нужен.
+ - Preferred path: use MCP `unica` tool `unica.apply` с операциями
+ `right.set` и `right.add`.
+ - Права одного объекта — запись роли со своим адресом
+ `<набор>:Role.<Роль>.Right.<Вид>_<Имя>`, например
+ `main:Role.Демо.Right.Catalog_Демо`. Записи роли видны в ветви
+ `<набор>:Role.<Роль>.Right`. Физический `Rights.xml` — внутренняя деталь;
+ наружу путь отдаёт только аварийный `unica.resolve`, и в обычном ходе
+ работы он не нужен.
- Имя набора даёт `unica.view {}`, адрес роли по имени —
`unica.search {corpus: "names", kind: "Role"}`. `"main"` ниже только пример.
- Сначала вызови `unica.apply` с `at` и `ops`: это план без записи.
Когда пользователь поручил внести эту правку, вызови `unica.apply` только
с `executionToken` из `data.executionToken` успешного плана.
+ - Точную форму аргументов даёт контракт операции по её адресу:
+ `<набор>:Role.<Роль>.Can.right.add` и
+ `<набор>:Role.<Роль>.Right.<Вид>_<Имя>.Can.right.set`.
- Читай из ответа `changed`, `effects` по порядку операций и диагностики.
Физический путь и diff контрактом результата не являются.
## Операция `right.set`
- `args.values` принимает `object`, `right` и хотя бы одно из `value` и `rls`:
+ Меняет одно право существующей записи. Адрес — сама запись, `args.values`
+ принимает `right` и хотя бы одно из `value` и `rls`:
| Поле | Что задаёт |
|---|---|
- | `object` | Объект метаданных, например `Catalog.Демо` |
| `right` | Имя права, например `Delete` |
| `value` | Булево значение права |
| `rls` | Условие ограничения записей |
- Операции выполняются по порядку и публикуются одной транзакцией: либо все,
- либо ни одной. Повтор эквивалентной операции даёт `changed: false` без записи.
+ `right.set` не создаёт запись: адрес объекта, которого в роли нет, получает
+ `not_found` с `next` к роли. Объект в `values.object` снят — такой вызов
+ получает отказ с адресом записи в `next`.
- **Объект, ещё не перечисленный в роли, добавляется сам.** Прежний писатель
- отказывал `object_not_listed` и требовал сперва внести объект Конфигуратором;
- канонический `right.set` заводит объектный блок вместе с правом.
+ ## Операция `right.add`
+ Создаёт записи прав для объектов, которых в роли ещё нет. Адрес — роль,
+ элемент `args.items` называет объект (`object`, например `Catalog.Демо`)
+ и его начальные права (`rights`, например `{"Read": true}`). Объект, у
+ которого запись уже есть, отвергается: его права меняет `right.set` по
+ адресу записи. Ограничение записей на новую запись ставит `right.set` в том
+ же пакете.
+
+ Права вложенного объекта (`DataProcessor.X.Command.Y`, реквизит) этим путём
+ пока недоступны: у такой записи нет адреса до экранирования точки
+ ([задача #1356](https://github.com/IngvarConsulting/unica/issues/1356)),
+ и `right.add` её отвергает. Адрес записи — только каноническое имя
+ `<Вид>_<Имя>` из ветви `Right`.
+
+ Операции выполняются по порядку и публикуются одной транзакцией: либо все,
+ либо ни одной. Повтор эквивалентной `right.set` даёт `changed: false` без
+ записи.
+
Платформа хранит объектное право только со значением, отличным от умолчания
роли `setForNewObjects`. Поэтому `right.set` со значением умолчания (обычно
- `false`) удаляет элемент права вместе с его RLS, а опустевший объектный блок —
- целиком; если право уже отсутствует, это законный no-op.
+ `false`) удаляет элемент права вместе с его RLS, а опустевшую запись —
+ целиком; если право уже отсутствует, это законный no-op. По той же причине
+ `right.add` отвергает запись, все права которой равны умолчанию: она
+ осталась бы пустой.
Автоматическое включение зависимых прав в согласуемый preview ещё не
реализовано ([задача #941](https://github.com/IngvarConsulting/unica/issues/941)).
До реализации проверь доказанные зависимости и согласуй полный набор прав
с человеком. Не считай одиночный `right.set` проверкой полноты этого набора.
Для `DataProcessor.*` значение `Use=false` применяет правило платформы:
- удаляется весь объектный блок вместе с зависимым правом `View`. На другие виды
+ удаляется вся запись вместе с зависимым правом `View`. На другие виды
объектов и права это не обобщается.
## MCP examples
### Предпросмотр
```json
{
"jsonrpc": "2.0",
"method": "tools/call",
"params": {
"name": "unica.apply",
"arguments": {
- "at": "main:Role.Демо",
+ "at": "main:Role.Демо.Right.Catalog_Демо",
"ops": [
{
"op": "right.set",
"args": {
- "at": "main:Role.Демо",
+ "at": "main:Role.Демо.Right.Catalog_Демо",
"values": {
- "object": "Catalog.Демо",
"right": "Delete",
"value": false
}
}
}
]
}
}
}
```
- ### Право с ограничением записей
+ ### Новая запись с ограничением записей
Сначала получи план этого изменения:
```json
{
"jsonrpc": "2.0",
"method": "tools/call",
"params": {
"name": "unica.apply",
"arguments": {
"at": "main:Role.Демо",
"ops": [
{
- "op": "right.set",
+ "op": "right.add",
"args": {
"at": "main:Role.Демо",
+ "items": [
+ {"object": "Document.Заказ", "rights": {"Read": true}}
+ ]
+ }
+ },
+ {
+ "op": "right.set",
+ "args": {
+ "at": "main:Role.Демо.Right.Document_Заказ",
"values": {
- "object": "Document.Заказ",
"right": "Read",
- "value": true,
"rls": "ГДЕ Автор = &Пользователь"
}
}
}
]
}
}
}
```
Для исполнения передай `data.executionToken` из этого успешного плана:
```json
{
"jsonrpc": "2.0",
"method": "tools/call",
"params": {
"name": "unica.apply",
"arguments": {
"executionToken": "<data.executionToken из успешного плана>"
}
}
}
```