feat(meta-compile,meta-decompile): роундтрип CommonModule + EventSubscription + ScheduledJob (v1.57/v0.48)

Верификация 3 типов, заявленных в validTypes, но НИКОГДА не проверенных роундтрипом
(как и ожидалось — легаси-баги). Декомпилятор снят гейт +3; захват свойств.
ПОЛНЫЙ КОРПУС acc+erp 8017/8017 byte-exact, TOTAL 0. Регресс 61/61 ps1+py, ps1==py identical.

- **CommonModule**: comment был захардкожен пустым → динамический (флаги контекста уже верны).
- **EventSubscription**: (1) comment динамический; (2) **Source переписан на Emit-TypeContent** —
  легаси эмиттер писал `d5p1:CatalogObject.X` для ВСЕХ, но объектные типы в корпусе `cfg:` (harness
  не нормализует d5p1↔cfg для не-Ref) → рассинхрон. (3) **Голые метатипы Source**: Object/RecordSet +
  ConstantValueManager → `<v8:TypeSet>cfg:X`, прочие Manager/List → `<v8:Type>cfg:X` (эмпирика корпуса:
  DocumentManager=Type, DocumentObject/ConstantValueManager=TypeSet). +Sequence/Recalculation в cfgObjectKinds.
- **ScheduledJob**: (1) comment динамический; (2) **Description дефолт синоним→ПУСТО** (корпус 662 пустых/
  209 заданы — синоним-дефолт рвал роундтрип); (3) Description Esc-Xml→Esc-XmlText (кавычки в тексте не экранируем).

Декомпилятор: CommonModule(флаги+returnValuesReuse), EventSubscription(source v8:Type|v8:TypeSet/event/
handler), ScheduledJob(methodName/description/key/use/predefined/restart*). NB: unf_8.5 остаётся с
косметическим xmlns:pal в корне (глобально, вне acc+erp-корпуса). spec-обновление и py-декомпилятор — позже.
Кейсы event-subscription-sources; event-subscription/scheduled-job переснята (d5p1→cfg, Description).

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
This commit is contained in:
Nick Shirokov
2026-07-10 12:49:49 +03:00
co-authored by Claude Opus 4.8
parent f4fb260f68
commit f80446c035
10 changed files with 422 additions and 28 deletions
@@ -1,4 +1,4 @@
# meta-decompile v0.47 — XML объекта метаданных 1С → JSON-черновик формата meta-compile
# meta-decompile v0.48 — XML объекта метаданных 1С → JSON-черновик формата meta-compile
# Source: https://github.com/Nikolay-Shirokov/cc-1c-skills
#
# Поддержаны: Catalog, ExchangePlan, ChartOfCharacteristicTypes, ChartOfAccounts, ChartOfCalculationTypes, Document,
@@ -92,8 +92,8 @@ foreach ($c in $rootEl.ChildNodes) { if ($c.NodeType -eq 'Element') { $objNode =
if (-not $objNode) { [Console]::Error.WriteLine("meta-decompile: пустой MetaDataObject"); exit 3 }
$objType = $objNode.LocalName
if ($objType -notin @('Catalog', 'ExchangePlan', 'ChartOfCharacteristicTypes', 'ChartOfAccounts', 'ChartOfCalculationTypes', 'Document', 'InformationRegister', 'AccumulationRegister', 'AccountingRegister', 'CalculationRegister', 'BusinessProcess', 'Task', 'Enum', 'Report', 'DataProcessor', 'Constant', 'DefinedType', 'FunctionalOption', 'DocumentJournal', 'Sequence', 'FilterCriterion', 'DocumentNumerator', 'SettingsStorage')) {
[Console]::Error.WriteLine("meta-decompile: тип '$objType' пока не поддержан (…, Sequence, FilterCriterion, DocumentNumerator, SettingsStorage)"); exit 3
if ($objType -notin @('Catalog', 'ExchangePlan', 'ChartOfCharacteristicTypes', 'ChartOfAccounts', 'ChartOfCalculationTypes', 'Document', 'InformationRegister', 'AccumulationRegister', 'AccountingRegister', 'CalculationRegister', 'BusinessProcess', 'Task', 'Enum', 'Report', 'DataProcessor', 'Constant', 'DefinedType', 'FunctionalOption', 'DocumentJournal', 'Sequence', 'FilterCriterion', 'DocumentNumerator', 'SettingsStorage', 'CommonModule', 'EventSubscription', 'ScheduledJob')) {
[Console]::Error.WriteLine("meta-decompile: тип '$objType' пока не поддержан (…, CommonModule, EventSubscription, ScheduledJob)"); exit 3
}
$props = $objNode.SelectSingleNode('md:Properties', $nsm)
@@ -656,6 +656,38 @@ if ($objType -eq 'SettingsStorage') {
$fv = P $fp[0]; if ($fv) { $dsl[$fp[1]] = $fv }
}
}
# CommonModule — общий модуль: флаги контекста компиляции + повторное использование значений (тело .bsl вне скоупа).
if ($objType -eq 'CommonModule') {
Add-BoolProp 'global' 'Global' $false
Add-BoolProp 'clientManagedApplication' 'ClientManagedApplication' $false
Add-BoolProp 'server' 'Server' $false
Add-BoolProp 'externalConnection' 'ExternalConnection' $false
Add-BoolProp 'clientOrdinaryApplication' 'ClientOrdinaryApplication' $false
Add-BoolProp 'serverCall' 'ServerCall' $false
Add-BoolProp 'privileged' 'Privileged' $false
Add-EnumProp 'returnValuesReuse' 'ReturnValuesReuse' 'DontUse'
}
# EventSubscription — подписка на событие: источники (набор типов), событие, обработчик.
if ($objType -eq 'EventSubscription') {
$srcNode = $props.SelectSingleNode('md:Source', $nsm)
if ($srcNode) {
# Источник — набор v8:Type (конкретный CatalogObject.X) И/ИЛИ v8:TypeSet (голый метатип ExchangePlanObject).
$srcTypes = @($srcNode.SelectNodes('v8:Type|v8:TypeSet', $nsm) | ForEach-Object { Strip-NsPrefix $_.InnerText.Trim() })
if ($srcTypes.Count -gt 0) { $dsl['source'] = [System.Collections.ArrayList]@($srcTypes) }
}
Add-EnumProp 'event' 'Event' 'BeforeWrite'
$h = P 'Handler'; if ($h) { $dsl['handler'] = $h }
}
# ScheduledJob — регламентное задание: метод, ключ, флаги, рестарт.
if ($objType -eq 'ScheduledJob') {
$mn = P 'MethodName'; if ($mn) { $dsl['methodName'] = $mn }
$descr = P 'Description'; if ($descr) { $dsl['description'] = $descr }
$k = P 'Key'; if ($k) { $dsl['key'] = $k }
Add-BoolProp 'use' 'Use' $false
Add-BoolProp 'predefined' 'Predefined' $false
Add-IntProp 'restartCountOnFailure' 'RestartCountOnFailure' 3
Add-IntProp 'restartIntervalOnFailure' 'RestartIntervalOnFailure' 10
}
# Constant — богатый одиночный реквизит: Type + свойства значения (как у реквизита) + object-уровень.
if ($objType -eq 'Constant') {
$vt = Get-TypeShorthand ($props.SelectSingleNode('md:Type', $nsm))