ssl-patterns

$npx mdskill add SteelMorgan/1c-agent-based-dev-framework/ssl-patterns

Teaches agents to use the Standard Subsystem Library (SSL) effectively by following established patterns and avoiding duplication.

  • Helps developers avoid reinventing functionality by leveraging pre-tested SSL modules.
  • Integrates with the Standard Subsystem Library and its modules like ОбщегоНазначения.
  • Recommends using SSL functions based on rules for efficiency and code familiarity.
  • Presents results through code examples and guidelines for proper implementation.
SKILL.md
.github/skills/ssl-patternsView on GitHub ↗
---
name: ssl-patterns
description: Паттерны работы с БСП (Библиотека стандартных подсистем). Этот навык учит агента правильно использовать БСП (Библиотеку стандартных подсистем, англ.
---

# Паттерны работы с БСП (Библиотека стандартных подсистем)

Код БСП проверен на миллионах установок, обновляется централизованно, знаком другим разработчикам. Дублирование БСП — антипаттерн.

---

## Правило 1: Модуль ОбщегоНазначения — основной «швейцарский нож»

Прежде чем писать свою реализацию, проверьте — возможно, в БСП уже есть готовая функция.

| Функция | Когда использовать |
|---------|-------------------|
| `ЗначениеРеквизитаОбъекта()` | Вместо `Ссылка.Реквизит` (избегаем точечную нотацию) |
| `ЗначенияРеквизитовОбъекта()` | Несколько реквизитов одним вызовом |
| `СообщитьПользователю()` | Сообщение с привязкой к полю (вместо `Сообщить()`) |
| `МенеджерОбъектаПоСсылке()` | Вместо `Выполнить("Справочники." + Имя)` |
| `ПодсистемаСуществует()` | Условный вызов модулей |
| `ОбщийМодуль()` | Динамический вызов модуля БСП |
| `ЭтоСсылка()` | Валидация параметров |
| `СсылкаСуществует()` | Проверка перед обращением |

```bsl
// ПЛОХО: три обращения к БД через точку
Наименование = КонтрагентСсылка.Наименование;
ИНН = КонтрагентСсылка.ИНН;
Ответственный = КонтрагентСсылка.ОсновнойМенеджер;

// ПРАВИЛЬНО: одно обращение через БСП
РеквизитыКонтрагента = ОбщегоНазначения.ЗначенияРеквизитовОбъекта(
    КонтрагентСсылка,
    "Наименование, ИНН, ОсновнойМенеджер");
```

---

## Правило 2: СтроковыеФункцииКлиентСервер — работа со строками

Модуль содержит оптимизированные функции, корректно обрабатывающие edge cases.

| Функция | Когда использовать |
|---------|-------------------|
| `ПодставитьПараметрыВСтроку()` | Аналог `СтрШаблон()`, с дополнительными проверками |
| `СтрокаСЧисломПредметов()` | Склонение: «5 документов», «1 документ» |
| `ЕстьНедопустимыеСимволы()` | Валидация ввода |
| `ТолькоЦифрыВСтроке()` | Валидация ИНН, КПП |
| `РазложитьСтрокуВМассивПодстрок()` | Парсинг по разделителю |

```bsl
// Склонение: «1 документ», «2 документа», «5 документов»
ТекстОповещения = СтроковыеФункцииКлиентСервер.СтрокаСЧисломПредметов(
    КоличествоДокументов,
    НСтр("ru = 'документ, документа, документов'"));
```

---

## Правило 3: ОбщегоНазначенияКлиентСервер — утилиты для обеих сред

Директива `&НаКлиентеНаСервереБезКонтекста` — доступен и на клиенте, и на сервере.

| Функция | Описание |
|---------|----------|
| `ДополнитьМассив()` | Объединение двух массивов |
| `ДополнитьСтруктуру()` | Объединение двух структур |
| `СвойствоСтруктуры()` | Безопасное чтение свойства (значение по умолчанию если нет) |
| `ПроверитьПараметр()` | Валидация типа с информативной ошибкой |

```bsl
// Безопасный доступ с значением по умолчанию
ДатаНачала = ОбщегоНазначенияКлиентСервер.СвойствоСтруктуры(
    ПараметрыОтчёта, "ДатаНачала", НачалоГода(ТекущаяДатаСеанса()));
```

---

## Правило 4: Стратегия поиска функций БСП

### Алгоритм: LSP -> grep -> AI

1. **LSP** (если доступен): `navigate_symbol("ЗначенияРеквизитовОбъекта")`
2. **Поиск по тексту**: `grep -r "Функция.*КурсВалюты" src/CommonModules/`
3. **AI-ассистент**: «Есть ли в БСП функция для получения курса валюты на дату?»

### Когда писать своё vs использовать БСП

| Ситуация | Решение |
|----------|---------|
| В БСП есть подходящая функция | **Используй БСП** |
| В БСП есть похожая, но с лишним функционалом | **Используй БСП** — лишнее не мешает |
| Нужной функции нет в БСП | Пиши своё в стиле БСП |
| Конфигурация без БСП | Пиши своё |

---

## Правило 5: Работа с журналом регистрации через БСП

См. `error-handling`, правило 7.

---

## Правило 6: РаботаСФайлами — вместо прямого ФайловаяСистема

Прямая работа с файлами не учитывает: права доступа, временные файлы, кросс-платформенность.

```bsl
ИмяВременногоФайла = ПолучитьИмяВременногоФайла("xlsx");
Попытка
    ТабличныйДокумент.Записать(ИмяВременногоФайла, ТипФайлаТабличногоДокумента.XLSX);
    // ... работа с файлом ...
Исключение
    // Обработка ошибки
КонецПопытки;

// Явное удаление
УдалитьФайлы(ИмяВременногоФайла);
```

---

## Правило 7: Типовые паттерны БСП

### Проверка заполнения (ОбработкаПроверкиЗаполнения)

```bsl
Процедура ОбработкаПроверкиЗаполнения(Отказ, ПроверяемыеРеквизиты)

    Если НЕ ЗначениеЗаполнено(Контрагент) Тогда
        ОбщегоНазначения.СообщитьПользователю(
            НСтр("ru = 'Не заполнен контрагент.'"),
            ЭтотОбъект, "Контрагент",, Отказ);
    КонецЕсли;

    // Условное исключение реквизитов из проверки
    Если ВидОперации = Перечисления.ВидыОпераций.Услуга Тогда
        ОбщегоНазначенияКлиентСервер.УдалитьЗначениеИзМассива(
            ПроверяемыеРеквизиты, "Склад");
    КонецЕсли;

КонецПроцедуры
```

### Получение данных для печати

```bsl
Процедура Печать(МассивОбъектов, ПараметрыПечати, КоллекцияПечатныхФорм,
        ОбъектыПечати, ПараметрыВывода) Экспорт

    Если УправлениеПечатью.НужноПечататьМакет(КоллекцияПечатныхФорм, "Счёт") Тогда

        ТабличныйДокумент = Новый ТабличныйДокумент;
        ТабличныйДокумент.КлючПараметровПечати = "Документ.РеализацияТоваровУслуг.Счёт";

        УправлениеПечатью.ВывестиТабличныйДокументВКоллекцию(
            КоллекцияПечатныхФорм, "Счёт", НСтр("ru = 'Счёт на оплату'"),
            ТабличныйДокумент);
    КонецЕсли;

КонецПроцедуры
```

---

## Правило 8: Не дублируйте функционал БСП

| Что часто пишут сами | Что есть в БСП |
|----------------------|----------------|
| Получение реквизита по ссылке | `ОбщегоНазначения.ЗначениеРеквизитаОбъекта()` |
| Подстановка в строку | `СтроковыеФункцииКлиентСервер.ПодставитьПараметрыВСтроку()` |
| Склонение слов | `СтроковыеФункцииКлиентСервер.СтрокаСЧисломПредметов()` |
| Отправка почты | `РаботаСПочтовымиСообщениями` |
| Курс валюты | `РаботаСКурсамиВалют.ПолучитьКурсВалюты()` |

---

## Правило 9: Модули «КлиентСервер» — разделение ответственности

| Суффикс модуля | Среда | Пример |
|----------------|-------|--------|
| (без суффикса) | Сервер | `ОбщегоНазначения` |
| `Клиент` | Клиент | `ОбщегоНазначенияКлиент` |
| `КлиентСервер` | Обе среды | `ОбщегоНазначенияКлиентСервер` |
| `ПовтИсп` | Сервер, с кэшированием | `ОбщегоНазначенияПовтИсп` |

Для клиентского кода формы — ищите сначала в `*КлиентСервер`, потом в `*Клиент`. Для серверного — в основном модуле (без суффикса). `*ПовтИсп` — для часто запрашиваемых справочных данных.

---
depends_on: []
---
More from SteelMorgan/1c-agent-based-dev-framework