diff --git a/.claude/skills/form-add/SKILL.md b/.claude/skills/form-add/SKILL.md index c050dd747..7970b9055 100644 --- a/.claude/skills/form-add/SKILL.md +++ b/.claude/skills/form-add/SKILL.md @@ -1,7 +1,7 @@ --- name: form-add description: Добавить пустую управляемую форму к объекту 1С. Используй когда нужно создать у объекта новую форму -argument-hint: [Purpose] [--set-default] +argument-hint: [-Purpose ] [-Synonym ] [-SetDefault] allowed-tools: - Bash - Read @@ -18,7 +18,7 @@ allowed-tools: ## Usage ``` -/form-add [Purpose] [Synonym] [--set-default] +/form-add [-Purpose ] [-Synonym ] [-SetDefault] ``` | Параметр | Обязательный | По умолчанию | Описание | @@ -27,7 +27,7 @@ allowed-tools: | FormName | да | — | Имя формы (ФормаДокумента) | | Purpose | нет | основная форма вида | Назначение формы — см. таблицу ниже: у справочника это форма объекта, у регистра сведений — форма записи, у журнала — форма списка | | Synonym | нет | = FormName | Синоним формы | -| --set-default | нет | авто | Сделать основной. Без флага основной становится первая форма каждого назначения | +| -SetDefault | нет | авто | Сделать основной. Без флага основной становится первая форма каждого назначения | ## Команда @@ -70,19 +70,19 @@ powershell.exe -NoProfile -File "${CLAUDE_SKILL_DIR}/scripts/form-add.ps1" -Obje ``` # Форма документа -/form-add Documents/АвансовыйОтчет.xml ФормаДокумента --purpose Object +/form-add Documents/АвансовыйОтчет.xml ФормаДокумента -Purpose Object # Форма списка каталога -/form-add Catalogs/Контрагенты.xml ФормаСписка --purpose List +/form-add Catalogs/Контрагенты.xml ФормаСписка -Purpose List # Форма записи регистра сведений -/form-add InformationRegisters/КурсыВалют.xml ФормаЗаписи --purpose Record +/form-add InformationRegisters/КурсыВалют.xml ФормаЗаписи -Purpose Record # Форма выбора с синонимом -/form-add Catalogs/Номенклатура.xml ФормаВыбора --purpose Choice --synonym "Выбор номенклатуры" +/form-add Catalogs/Номенклатура.xml ФормаВыбора -Purpose Choice -Synonym "Выбор номенклатуры" # Установить как форму по умолчанию -/form-add Documents/Заказ.xml ФормаДокументаНовая --purpose Object --set-default +/form-add Documents/Заказ.xml ФормаДокументаНовая -Purpose Object -SetDefault ``` ## Workflow diff --git a/.claude/skills/form-add/scripts/form-add.ps1 b/.claude/skills/form-add/scripts/form-add.ps1 index 484bad821..63a1ca22d 100644 --- a/.claude/skills/form-add/scripts/form-add.ps1 +++ b/.claude/skills/form-add/scripts/form-add.ps1 @@ -1,4 +1,4 @@ -# form-add v1.27 — Add managed form to 1C config object (+write_xml_file/write_utf8_bom: общий эталон записи) +# form-add v1.28 — Add managed form to 1C config object # Source: https://github.com/Nikolay-Shirokov/cc-1c-skills [CmdletBinding(PositionalBinding=$false)] param( @@ -15,6 +15,10 @@ param( # по умолчанию было бы неверным для видов, у которых формы объекта не бывает. [string]$Purpose = "", + # Алиас с дефисом внутри имени: вызов вида --set-default PowerShell разбирает как имя + # параметра "set-default" и без алиаса отвечает отказом биндинга. Написания -SetDefault, + # --SetDefault и --setdefault совпадают с именем параметра и так. + [Alias('set-default')] [switch]$SetDefault ) @@ -424,6 +428,34 @@ Write-Host "Object: $objectType.$objectName" # Назначение ищем в таблице регистронезависимо — как принимает PowerShell (в py-порту .lower()). $kindPurposes = $formKinds[$objectType] + +# Обиходные написания назначения приводим к канону молча: русское название вида формы и +# английское с суффиксом Form. Ключ нормализуем — регистр, пробелы и разделители не значимы. +# Канон в документации один; здесь только приём ошибочного ввода, чтобы вызов не падал на форме +# записи вместо назначения. Применимость назначения к виду объекта проверяется ниже как обычно. +$purposeSynonyms = @{ + "формаобъекта"="Object"; "формаэлемента"="Object"; "формадокумента"="Object" + "объект"="Object"; "элемент"="Object"; "документ"="Object"; "objectform"="Object" + "формасписка"="List"; "список"="List"; "listform"="List" + "формавыбора"="Choice"; "выбор"="Choice"; "choiceform"="Choice" + "формагруппы"="Folder"; "группа"="Folder"; "folderform"="Folder" + "формавыборагруппы"="FolderChoice"; "выборгруппы"="FolderChoice"; "folderchoiceform"="FolderChoice" + "формазаписи"="Record"; "запись"="Record"; "recordform"="Record" + "форманаборазаписей"="RecordSet"; "наборзаписей"="RecordSet"; "recordsetform"="RecordSet" + "формасохранения"="Save"; "формасохранениянастроек"="Save"; "сохранение"="Save"; "saveform"="Save" + "формазагрузки"="Load"; "формазагрузкинастроек"="Load"; "загрузка"="Load"; "loadform"="Load" + "произвольная"="Custom"; "произвольнаяформа"="Custom"; "customform"="Custom" +} +if ($Purpose) { + $purposeProbe = ($Purpose -replace '[\s_-]', '').ToLowerInvariant() + $isKnownPurpose = $false + foreach ($p in $kindPurposes.Keys) { + if ($p.ToLowerInvariant() -eq $Purpose.ToLowerInvariant()) { $isKnownPurpose = $true; break } + } + if (-not $isKnownPurpose -and $purposeSynonyms.ContainsKey($purposeProbe)) { + $Purpose = $purposeSynonyms[$purposeProbe] + } +} if (-not $Purpose) { foreach ($p in $kindPurposes.Keys) { if ($kindPurposes[$p].Primary) { $Purpose = $p; break } diff --git a/.claude/skills/form-add/scripts/form-add.py b/.claude/skills/form-add/scripts/form-add.py index dbdacb63c..bc06e70c9 100644 --- a/.claude/skills/form-add/scripts/form-add.py +++ b/.claude/skills/form-add/scripts/form-add.py @@ -1,5 +1,5 @@ #!/usr/bin/env python3 -# form-add v1.27 — Add managed form to 1C config object (+write_xml_file/write_utf8_bom: общий эталон записи) +# form-add v1.28 — Add managed form to 1C config object (Python port) # Source: https://github.com/Nikolay-Shirokov/cc-1c-skills import argparse @@ -326,7 +326,10 @@ def main(): # Пусто = основная форма вида (primary в таблице): у справочника это форма объекта, # у регистра сведений — форма записи, у журнала — форма списка. parser.add_argument("-Purpose", default="") - parser.add_argument("-SetDefault", action="store_true") + # Написания с дефисом внутри имени и с двойным дефисом: в PS-порте их принимает алиас + # set-default, здесь — перечисление опций, чтобы порты принимали ровно одно и то же. + parser.add_argument("-SetDefault", "--SetDefault", "--set-default", "-set-default", + dest="SetDefault", action="store_true") args = ci_parse_args(parser) object_path = args.ObjectPath @@ -610,6 +613,33 @@ def main(): # Назначение ищем в таблице регистронезависимо — как принимает PowerShell. kind_purposes = form_kinds[object_type] + + # Обиходные написания назначения приводим к канону молча: русское название вида формы и + # английское с суффиксом Form. Ключ нормализуем — регистр, пробелы и разделители не значимы. + # Канон в документации один; здесь только приём ошибочного ввода, чтобы вызов не падал на форме + # записи вместо назначения. Применимость назначения к виду объекта проверяется ниже как обычно. + purpose_synonyms = { + "формаобъекта": "Object", "формаэлемента": "Object", "формадокумента": "Object", + "объект": "Object", "элемент": "Object", "документ": "Object", "objectform": "Object", + "формасписка": "List", "список": "List", "listform": "List", + "формавыбора": "Choice", "выбор": "Choice", "choiceform": "Choice", + "формагруппы": "Folder", "группа": "Folder", "folderform": "Folder", + "формавыборагруппы": "FolderChoice", "выборгруппы": "FolderChoice", + "folderchoiceform": "FolderChoice", + "формазаписи": "Record", "запись": "Record", "recordform": "Record", + "форманаборазаписей": "RecordSet", "наборзаписей": "RecordSet", "recordsetform": "RecordSet", + "формасохранения": "Save", "формасохранениянастроек": "Save", "сохранение": "Save", + "saveform": "Save", + "формазагрузки": "Load", "формазагрузкинастроек": "Load", "загрузка": "Load", + "loadform": "Load", + "произвольная": "Custom", "произвольнаяформа": "Custom", "customform": "Custom", + } + if purpose: + purpose_probe = re.sub(r"[\s_-]", "", purpose).lower() + is_known_purpose = any(k.lower() == purpose.lower() for k in kind_purposes) + if not is_known_purpose and purpose_probe in purpose_synonyms: + purpose = purpose_synonyms[purpose_probe] + if not purpose: for k, rule in kind_purposes.items(): if rule.get("primary"): diff --git a/tests/skills/cases/form-add/lenient-purpose-and-flag-spellings.json b/tests/skills/cases/form-add/lenient-purpose-and-flag-spellings.json new file mode 100644 index 000000000..808f83e65 --- /dev/null +++ b/tests/skills/cases/form-add/lenient-purpose-and-flag-spellings.json @@ -0,0 +1,22 @@ +{ + "name": "Обиходные написания параметров принимаются: русское назначение и флаг через двойной дефис", + "preRun": [ + { + "script": "meta-compile/scripts/meta-compile", + "input": { "type": "Catalog", "name": "ТестПрощающийВвод" }, + "args": { "-JsonPath": "{inputFile}", "-OutputDir": "{workDir}" } + } + ], + "params": { + "objectPath": "Catalogs/ТестПрощающийВвод.xml", + "formName": "ФормаСпискаТест" + }, + "args_extra": ["-Purpose", "ФормаСписка", "--set-default"], + "validatePath": "Catalogs/ТестПрощающийВвод/Forms/ФормаСпискаТест", + "expect": { + "fileContains": { + "file": "Catalogs/ТестПрощающийВвод.xml", + "text": "Catalog.ТестПрощающийВвод.Form.ФормаСпискаТест" + } + } +} diff --git a/tests/skills/cases/form-add/snapshots/lenient-purpose-and-flag-spellings/Catalogs/ТестПрощающийВвод.xml b/tests/skills/cases/form-add/snapshots/lenient-purpose-and-flag-spellings/Catalogs/ТестПрощающийВвод.xml new file mode 100644 index 000000000..5cb191010 --- /dev/null +++ b/tests/skills/cases/form-add/snapshots/lenient-purpose-and-flag-spellings/Catalogs/ТестПрощающийВвод.xml @@ -0,0 +1,93 @@ + + + + + + UUID-002 + UUID-003 + + + UUID-004 + UUID-005 + + + UUID-006 + UUID-007 + + + UUID-008 + UUID-009 + + + UUID-010 + UUID-011 + + + + ТестПрощающийВвод + + + ru + Тест прощающий ввод + + + + false + HierarchyFoldersAndItems + false + 2 + true + true + + ToItems + 9 + 25 + String + Variable + WholeCatalog + false + true + AsDescription + + Auto + InDialog + false + BothWays + + Catalog.ТестПрощающийВвод.StandardAttribute.Description + Catalog.ТестПрощающийВвод.StandardAttribute.Code + + Begin + DontUse + Directly + + + Catalog.ТестПрощающийВвод.Form.ФормаСпискаТест + + + + + + + + false + + + Managed + Use + + + + + + Use + Auto + DontUse + false + false + + +
ФормаСпискаТест
+
+
+
\ No newline at end of file diff --git a/tests/skills/cases/form-add/snapshots/lenient-purpose-and-flag-spellings/Catalogs/ТестПрощающийВвод/Ext/ObjectModule.bsl b/tests/skills/cases/form-add/snapshots/lenient-purpose-and-flag-spellings/Catalogs/ТестПрощающийВвод/Ext/ObjectModule.bsl new file mode 100644 index 000000000..e69de29bb diff --git a/tests/skills/cases/form-add/snapshots/lenient-purpose-and-flag-spellings/Catalogs/ТестПрощающийВвод/Forms/ФормаСпискаТест.xml b/tests/skills/cases/form-add/snapshots/lenient-purpose-and-flag-spellings/Catalogs/ТестПрощающийВвод/Forms/ФормаСпискаТест.xml new file mode 100644 index 000000000..802533802 --- /dev/null +++ b/tests/skills/cases/form-add/snapshots/lenient-purpose-and-flag-spellings/Catalogs/ТестПрощающийВвод/Forms/ФормаСпискаТест.xml @@ -0,0 +1,21 @@ + + +
+ + ФормаСпискаТест + + + ru + ФормаСпискаТест + + + + Managed + false + + PlatformApplication + MobilePlatformApplication + + +
+
\ No newline at end of file diff --git a/tests/skills/cases/form-add/snapshots/lenient-purpose-and-flag-spellings/Catalogs/ТестПрощающийВвод/Forms/ФормаСпискаТест/Ext/Form.xml b/tests/skills/cases/form-add/snapshots/lenient-purpose-and-flag-spellings/Catalogs/ТестПрощающийВвод/Forms/ФормаСпискаТест/Ext/Form.xml new file mode 100644 index 000000000..d4df47e5c --- /dev/null +++ b/tests/skills/cases/form-add/snapshots/lenient-purpose-and-flag-spellings/Catalogs/ТестПрощающийВвод/Forms/ФормаСпискаТест/Ext/Form.xml @@ -0,0 +1,18 @@ + +
+ + true + + + + + + cfg:DynamicList + + true + + Catalog.ТестПрощающийВвод + + + + \ No newline at end of file diff --git a/tests/skills/cases/form-add/snapshots/lenient-purpose-and-flag-spellings/Catalogs/ТестПрощающийВвод/Forms/ФормаСпискаТест/Ext/Form/Module.bsl b/tests/skills/cases/form-add/snapshots/lenient-purpose-and-flag-spellings/Catalogs/ТестПрощающийВвод/Forms/ФормаСпискаТест/Ext/Form/Module.bsl new file mode 100644 index 000000000..8ead4cec0 --- /dev/null +++ b/tests/skills/cases/form-add/snapshots/lenient-purpose-and-flag-spellings/Catalogs/ТестПрощающийВвод/Forms/ФормаСпискаТест/Ext/Form/Module.bsl @@ -0,0 +1,19 @@ +#Область ОбработчикиСобытийФормы + +#КонецОбласти + +#Область ОбработчикиСобытийЭлементовФормы + +#КонецОбласти + +#Область ОбработчикиКомандФормы + +#КонецОбласти + +#Область ОбработчикиОповещений + +#КонецОбласти + +#Область СлужебныеПроцедурыИФункции + +#КонецОбласти \ No newline at end of file diff --git a/tests/skills/cases/form-add/snapshots/lenient-purpose-and-flag-spellings/Configuration.xml b/tests/skills/cases/form-add/snapshots/lenient-purpose-and-flag-spellings/Configuration.xml new file mode 100644 index 000000000..299f2b5ef --- /dev/null +++ b/tests/skills/cases/form-add/snapshots/lenient-purpose-and-flag-spellings/Configuration.xml @@ -0,0 +1,252 @@ + + + + + + UUID-002 + UUID-003 + + + UUID-004 + UUID-005 + + + UUID-006 + UUID-007 + + + UUID-008 + UUID-009 + + + UUID-010 + UUID-011 + + + UUID-012 + UUID-013 + + + UUID-014 + UUID-015 + + + + TestConfig + + + ru + TestConfig + + + + + Version8_3_24 + ManagedApplication + + PlatformApplication + + Russian + + + + + false + false + false + + + + + + + + + + + + + + + + + + + + + + Biometrics + true + + + Location + false + + + BackgroundLocation + false + + + BluetoothPrinters + false + + + WiFiPrinters + false + + + Contacts + false + + + Calendars + false + + + PushNotifications + false + + + LocalNotifications + false + + + InAppPurchases + false + + + PersonalComputerFileExchange + false + + + Ads + false + + + NumberDialing + false + + + CallProcessing + false + + + CallLog + false + + + AutoSendSMS + false + + + ReceiveSMS + false + + + SMSLog + false + + + Camera + false + + + Microphone + false + + + MusicLibrary + false + + + PictureAndVideoLibraries + false + + + AudioPlaybackAndVibration + false + + + BackgroundAudioPlaybackAndVibration + false + + + InstallPackages + false + + + OSBackup + true + + + ApplicationUsageStatistics + false + + + BarcodeScanning + false + + + BackgroundAudioRecording + false + + + AllFilesAccess + false + + + Videoconferences + false + + + NFC + false + + + DocumentScanning + false + + + SpeechToText + false + + + Geofences + false + + + IncomingShareRequests + false + + + AllIncomingShareRequestsTypesProcessing + false + + + + + + Normal + + + Language.Русский + + + + + + Managed + NotAutoFree + DontUse + DontUse + TaxiEnableVersion8_2 + DontUse + Version8_3_24 + + + + Русский + ТестПрощающийВвод + + + \ No newline at end of file diff --git a/tests/skills/cases/form-add/snapshots/lenient-purpose-and-flag-spellings/Ext/ClientApplicationInterface.xml b/tests/skills/cases/form-add/snapshots/lenient-purpose-and-flag-spellings/Ext/ClientApplicationInterface.xml new file mode 100644 index 000000000..3c1161b2d --- /dev/null +++ b/tests/skills/cases/form-add/snapshots/lenient-purpose-and-flag-spellings/Ext/ClientApplicationInterface.xml @@ -0,0 +1,18 @@ + + + + + UUID-002 + + + + + UUID-004 + + + + + + + + \ No newline at end of file diff --git a/tests/skills/cases/form-add/snapshots/lenient-purpose-and-flag-spellings/Languages/Русский.xml b/tests/skills/cases/form-add/snapshots/lenient-purpose-and-flag-spellings/Languages/Русский.xml new file mode 100644 index 000000000..37c60d786 --- /dev/null +++ b/tests/skills/cases/form-add/snapshots/lenient-purpose-and-flag-spellings/Languages/Русский.xml @@ -0,0 +1,16 @@ + + + + + Русский + + + ru + Русский + + + + ru + + + \ No newline at end of file