d365fo-mcp 1.0.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/LICENSE +21 -0
- package/README.md +205 -0
- package/dist/bridge/bridgeAdapter.d.ts +319 -0
- package/dist/bridge/bridgeAdapter.d.ts.map +1 -0
- package/dist/bridge/bridgeAdapter.js +2003 -0
- package/dist/bridge/bridgeAdapter.js.map +1 -0
- package/dist/bridge/bridgeClient.d.ts +255 -0
- package/dist/bridge/bridgeClient.d.ts.map +1 -0
- package/dist/bridge/bridgeClient.js +741 -0
- package/dist/bridge/bridgeClient.js.map +1 -0
- package/dist/bridge/bridgeTypes.d.ts +561 -0
- package/dist/bridge/bridgeTypes.d.ts.map +1 -0
- package/dist/bridge/bridgeTypes.js +6 -0
- package/dist/bridge/bridgeTypes.js.map +1 -0
- package/dist/bridge/debouncedRefresh.d.ts +16 -0
- package/dist/bridge/debouncedRefresh.d.ts.map +1 -0
- package/dist/bridge/debouncedRefresh.js +77 -0
- package/dist/bridge/debouncedRefresh.js.map +1 -0
- package/dist/bridge/index.d.ts +21 -0
- package/dist/bridge/index.d.ts.map +1 -0
- package/dist/bridge/index.js +20 -0
- package/dist/bridge/index.js.map +1 -0
- package/dist/cli/commands/config.d.ts +8 -0
- package/dist/cli/commands/config.d.ts.map +1 -0
- package/dist/cli/commands/config.js +77 -0
- package/dist/cli/commands/config.js.map +1 -0
- package/dist/cli/commands/doctor.d.ts +2 -0
- package/dist/cli/commands/doctor.d.ts.map +1 -0
- package/dist/cli/commands/doctor.js +177 -0
- package/dist/cli/commands/doctor.js.map +1 -0
- package/dist/cli/commands/indexCmd.d.ts +8 -0
- package/dist/cli/commands/indexCmd.d.ts.map +1 -0
- package/dist/cli/commands/indexCmd.js +78 -0
- package/dist/cli/commands/indexCmd.js.map +1 -0
- package/dist/cli/commands/instance.d.ts +4 -0
- package/dist/cli/commands/instance.d.ts.map +1 -0
- package/dist/cli/commands/instance.js +183 -0
- package/dist/cli/commands/instance.js.map +1 -0
- package/dist/cli/commands/setup.d.ts +4 -0
- package/dist/cli/commands/setup.d.ts.map +1 -0
- package/dist/cli/commands/setup.js +246 -0
- package/dist/cli/commands/setup.js.map +1 -0
- package/dist/cli/commands/start.d.ts +2 -0
- package/dist/cli/commands/start.d.ts.map +1 -0
- package/dist/cli/commands/start.js +49 -0
- package/dist/cli/commands/start.js.map +1 -0
- package/dist/cli/commands/update.d.ts +4 -0
- package/dist/cli/commands/update.d.ts.map +1 -0
- package/dist/cli/commands/update.js +55 -0
- package/dist/cli/commands/update.js.map +1 -0
- package/dist/cli/context.d.ts +26 -0
- package/dist/cli/context.d.ts.map +1 -0
- package/dist/cli/context.js +38 -0
- package/dist/cli/context.js.map +1 -0
- package/dist/cli/envFile.d.ts +23 -0
- package/dist/cli/envFile.d.ts.map +1 -0
- package/dist/cli/envFile.js +79 -0
- package/dist/cli/envFile.js.map +1 -0
- package/dist/cli/exec.d.ts +13 -0
- package/dist/cli/exec.d.ts.map +1 -0
- package/dist/cli/exec.js +47 -0
- package/dist/cli/exec.js.map +1 -0
- package/dist/cli/index.d.ts +3 -0
- package/dist/cli/index.d.ts.map +1 -0
- package/dist/cli/index.js +122 -0
- package/dist/cli/index.js.map +1 -0
- package/dist/cli/instances.d.ts +19 -0
- package/dist/cli/instances.d.ts.map +1 -0
- package/dist/cli/instances.js +60 -0
- package/dist/cli/instances.js.map +1 -0
- package/dist/cli/mcpJson.d.ts +15 -0
- package/dist/cli/mcpJson.d.ts.map +1 -0
- package/dist/cli/mcpJson.js +44 -0
- package/dist/cli/mcpJson.js.map +1 -0
- package/dist/cli/settingsPrompt.d.ts +20 -0
- package/dist/cli/settingsPrompt.d.ts.map +1 -0
- package/dist/cli/settingsPrompt.js +150 -0
- package/dist/cli/settingsPrompt.js.map +1 -0
- package/dist/cli/settingsStore.d.ts +47 -0
- package/dist/cli/settingsStore.d.ts.map +1 -0
- package/dist/cli/settingsStore.js +144 -0
- package/dist/cli/settingsStore.js.map +1 -0
- package/dist/cli/target.d.ts +23 -0
- package/dist/cli/target.d.ts.map +1 -0
- package/dist/cli/target.js +62 -0
- package/dist/cli/target.js.map +1 -0
- package/dist/cli/ui.d.ts +26 -0
- package/dist/cli/ui.d.ts.map +1 -0
- package/dist/cli/ui.js +48 -0
- package/dist/cli/ui.js.map +1 -0
- package/dist/cli/xppConfig.d.ts +35 -0
- package/dist/cli/xppConfig.d.ts.map +1 -0
- package/dist/cli/xppConfig.js +97 -0
- package/dist/cli/xppConfig.js.map +1 -0
- package/dist/config/configFile.d.ts +50 -0
- package/dist/config/configFile.d.ts.map +1 -0
- package/dist/config/configFile.js +152 -0
- package/dist/config/configFile.js.map +1 -0
- package/dist/config/settings.d.ts +58 -0
- package/dist/config/settings.d.ts.map +1 -0
- package/dist/config/settings.js +641 -0
- package/dist/config/settings.js.map +1 -0
- package/dist/database/download.d.ts +27 -0
- package/dist/database/download.d.ts.map +1 -0
- package/dist/database/download.js +241 -0
- package/dist/database/download.js.map +1 -0
- package/dist/eval/audit/knowledgeAudit.d.ts +66 -0
- package/dist/eval/audit/knowledgeAudit.d.ts.map +1 -0
- package/dist/eval/audit/knowledgeAudit.js +117 -0
- package/dist/eval/audit/knowledgeAudit.js.map +1 -0
- package/dist/eval/audit/knowledgeAuditCli.d.ts +17 -0
- package/dist/eval/audit/knowledgeAuditCli.d.ts.map +1 -0
- package/dist/eval/audit/knowledgeAuditCli.js +83 -0
- package/dist/eval/audit/knowledgeAuditCli.js.map +1 -0
- package/dist/eval/audit/knowledgeRefs.d.ts +37 -0
- package/dist/eval/audit/knowledgeRefs.d.ts.map +1 -0
- package/dist/eval/audit/knowledgeRefs.js +150 -0
- package/dist/eval/audit/knowledgeRefs.js.map +1 -0
- package/dist/eval/audit/symbolLookup.d.ts +23 -0
- package/dist/eval/audit/symbolLookup.d.ts.map +1 -0
- package/dist/eval/audit/symbolLookup.js +80 -0
- package/dist/eval/audit/symbolLookup.js.map +1 -0
- package/dist/eval/coverage/coverage.d.ts +65 -0
- package/dist/eval/coverage/coverage.d.ts.map +1 -0
- package/dist/eval/coverage/coverage.js +136 -0
- package/dist/eval/coverage/coverage.js.map +1 -0
- package/dist/eval/coverage/coverageCli.d.ts +13 -0
- package/dist/eval/coverage/coverageCli.d.ts.map +1 -0
- package/dist/eval/coverage/coverageCli.js +106 -0
- package/dist/eval/coverage/coverageCli.js.map +1 -0
- package/dist/eval/coverage/sources.d.ts +17 -0
- package/dist/eval/coverage/sources.d.ts.map +1 -0
- package/dist/eval/coverage/sources.js +40 -0
- package/dist/eval/coverage/sources.js.map +1 -0
- package/dist/eval/coverage/taxonomy.d.ts +59 -0
- package/dist/eval/coverage/taxonomy.d.ts.map +1 -0
- package/dist/eval/coverage/taxonomy.js +400 -0
- package/dist/eval/coverage/taxonomy.js.map +1 -0
- package/dist/eval/improver/caseMining.d.ts +55 -0
- package/dist/eval/improver/caseMining.d.ts.map +1 -0
- package/dist/eval/improver/caseMining.js +64 -0
- package/dist/eval/improver/caseMining.js.map +1 -0
- package/dist/eval/improver/caseMiningCli.d.ts +10 -0
- package/dist/eval/improver/caseMiningCli.d.ts.map +1 -0
- package/dist/eval/improver/caseMiningCli.js +50 -0
- package/dist/eval/improver/caseMiningCli.js.map +1 -0
- package/dist/eval/improver/cli.d.ts +11 -0
- package/dist/eval/improver/cli.d.ts.map +1 -0
- package/dist/eval/improver/cli.js +73 -0
- package/dist/eval/improver/cli.js.map +1 -0
- package/dist/eval/improver/cluster.d.ts +47 -0
- package/dist/eval/improver/cluster.d.ts.map +1 -0
- package/dist/eval/improver/cluster.js +0 -0
- package/dist/eval/improver/cluster.js.map +1 -0
- package/dist/eval/improver/corpusIO.d.ts +26 -0
- package/dist/eval/improver/corpusIO.d.ts.map +1 -0
- package/dist/eval/improver/corpusIO.js +50 -0
- package/dist/eval/improver/corpusIO.js.map +1 -0
- package/dist/eval/improver/fixBrief.d.ts +34 -0
- package/dist/eval/improver/fixBrief.d.ts.map +1 -0
- package/dist/eval/improver/fixBrief.js +69 -0
- package/dist/eval/improver/fixBrief.js.map +1 -0
- package/dist/eval/improver/fixBriefCli.d.ts +11 -0
- package/dist/eval/improver/fixBriefCli.d.ts.map +1 -0
- package/dist/eval/improver/fixBriefCli.js +46 -0
- package/dist/eval/improver/fixBriefCli.js.map +1 -0
- package/dist/eval/improver/flakeDetection.d.ts +50 -0
- package/dist/eval/improver/flakeDetection.d.ts.map +1 -0
- package/dist/eval/improver/flakeDetection.js +0 -0
- package/dist/eval/improver/flakeDetection.js.map +1 -0
- package/dist/eval/improver/flakeDetectionCli.d.ts +8 -0
- package/dist/eval/improver/flakeDetectionCli.d.ts.map +1 -0
- package/dist/eval/improver/flakeDetectionCli.js +27 -0
- package/dist/eval/improver/flakeDetectionCli.js.map +1 -0
- package/dist/eval/improver/heldout.d.ts +44 -0
- package/dist/eval/improver/heldout.d.ts.map +1 -0
- package/dist/eval/improver/heldout.js +52 -0
- package/dist/eval/improver/heldout.js.map +1 -0
- package/dist/eval/improver/knowledgeFeedback.d.ts +56 -0
- package/dist/eval/improver/knowledgeFeedback.d.ts.map +1 -0
- package/dist/eval/improver/knowledgeFeedback.js +88 -0
- package/dist/eval/improver/knowledgeFeedback.js.map +1 -0
- package/dist/eval/improver/knowledgeFeedbackCli.d.ts +8 -0
- package/dist/eval/improver/knowledgeFeedbackCli.d.ts.map +1 -0
- package/dist/eval/improver/knowledgeFeedbackCli.js +28 -0
- package/dist/eval/improver/knowledgeFeedbackCli.js.map +1 -0
- package/dist/eval/improver/report.d.ts +36 -0
- package/dist/eval/improver/report.d.ts.map +1 -0
- package/dist/eval/improver/report.js +61 -0
- package/dist/eval/improver/report.js.map +1 -0
- package/dist/eval/improver/reportCli.d.ts +7 -0
- package/dist/eval/improver/reportCli.d.ts.map +1 -0
- package/dist/eval/improver/reportCli.js +27 -0
- package/dist/eval/improver/reportCli.js.map +1 -0
- package/dist/eval/oracle/actualArtifactResolution.d.ts +49 -0
- package/dist/eval/oracle/actualArtifactResolution.d.ts.map +1 -0
- package/dist/eval/oracle/actualArtifactResolution.js +73 -0
- package/dist/eval/oracle/actualArtifactResolution.js.map +1 -0
- package/dist/eval/oracle/cli.d.ts +30 -0
- package/dist/eval/oracle/cli.d.ts.map +1 -0
- package/dist/eval/oracle/cli.js +179 -0
- package/dist/eval/oracle/cli.js.map +1 -0
- package/dist/eval/oracle/diff.d.ts +26 -0
- package/dist/eval/oracle/diff.d.ts.map +1 -0
- package/dist/eval/oracle/diff.js +51 -0
- package/dist/eval/oracle/diff.js.map +1 -0
- package/dist/eval/oracle/index.d.ts +81 -0
- package/dist/eval/oracle/index.d.ts.map +1 -0
- package/dist/eval/oracle/index.js +55 -0
- package/dist/eval/oracle/index.js.map +1 -0
- package/dist/eval/oracle/normalize.d.ts +85 -0
- package/dist/eval/oracle/normalize.d.ts.map +1 -0
- package/dist/eval/oracle/normalize.js +321 -0
- package/dist/eval/oracle/normalize.js.map +1 -0
- package/dist/eval/oracle/score.d.ts +26 -0
- package/dist/eval/oracle/score.d.ts.map +1 -0
- package/dist/eval/oracle/score.js +15 -0
- package/dist/eval/oracle/score.js.map +1 -0
- package/dist/eval/oracle/systest.d.ts +30 -0
- package/dist/eval/oracle/systest.d.ts.map +1 -0
- package/dist/eval/oracle/systest.js +98 -0
- package/dist/eval/oracle/systest.js.map +1 -0
- package/dist/index.d.ts +6 -0
- package/dist/index.d.ts.map +1 -0
- package/dist/index.js +753 -0
- package/dist/index.js.map +1 -0
- package/dist/knowledge/formPatterns/catalog/subPatterns/customFilters.d.ts +10 -0
- package/dist/knowledge/formPatterns/catalog/subPatterns/customFilters.d.ts.map +1 -0
- package/dist/knowledge/formPatterns/catalog/subPatterns/customFilters.js +38 -0
- package/dist/knowledge/formPatterns/catalog/subPatterns/customFilters.js.map +1 -0
- package/dist/knowledge/formPatterns/catalog/subPatterns/fields.d.ts +21 -0
- package/dist/knowledge/formPatterns/catalog/subPatterns/fields.d.ts.map +1 -0
- package/dist/knowledge/formPatterns/catalog/subPatterns/fields.js +168 -0
- package/dist/knowledge/formPatterns/catalog/subPatterns/fields.js.map +1 -0
- package/dist/knowledge/formPatterns/catalog/subPatterns/panels.d.ts +9 -0
- package/dist/knowledge/formPatterns/catalog/subPatterns/panels.d.ts.map +1 -0
- package/dist/knowledge/formPatterns/catalog/subPatterns/panels.js +47 -0
- package/dist/knowledge/formPatterns/catalog/subPatterns/panels.js.map +1 -0
- package/dist/knowledge/formPatterns/catalog/subPatterns/toolbar.d.ts +16 -0
- package/dist/knowledge/formPatterns/catalog/subPatterns/toolbar.d.ts.map +1 -0
- package/dist/knowledge/formPatterns/catalog/subPatterns/toolbar.js +124 -0
- package/dist/knowledge/formPatterns/catalog/subPatterns/toolbar.js.map +1 -0
- package/dist/knowledge/formPatterns/catalog/subPatterns/workspaceSections.d.ts +12 -0
- package/dist/knowledge/formPatterns/catalog/subPatterns/workspaceSections.d.ts.map +1 -0
- package/dist/knowledge/formPatterns/catalog/subPatterns/workspaceSections.js +36 -0
- package/dist/knowledge/formPatterns/catalog/subPatterns/workspaceSections.js.map +1 -0
- package/dist/knowledge/formPatterns/catalog/topLevel/common.d.ts +11 -0
- package/dist/knowledge/formPatterns/catalog/topLevel/common.d.ts.map +1 -0
- package/dist/knowledge/formPatterns/catalog/topLevel/common.js +37 -0
- package/dist/knowledge/formPatterns/catalog/topLevel/common.js.map +1 -0
- package/dist/knowledge/formPatterns/catalog/topLevel/detailsMaster.d.ts +8 -0
- package/dist/knowledge/formPatterns/catalog/topLevel/detailsMaster.d.ts.map +1 -0
- package/dist/knowledge/formPatterns/catalog/topLevel/detailsMaster.js +86 -0
- package/dist/knowledge/formPatterns/catalog/topLevel/detailsMaster.js.map +1 -0
- package/dist/knowledge/formPatterns/catalog/topLevel/detailsTransaction.d.ts +7 -0
- package/dist/knowledge/formPatterns/catalog/topLevel/detailsTransaction.d.ts.map +1 -0
- package/dist/knowledge/formPatterns/catalog/topLevel/detailsTransaction.js +69 -0
- package/dist/knowledge/formPatterns/catalog/topLevel/detailsTransaction.js.map +1 -0
- package/dist/knowledge/formPatterns/catalog/topLevel/dialog.d.ts +14 -0
- package/dist/knowledge/formPatterns/catalog/topLevel/dialog.d.ts.map +1 -0
- package/dist/knowledge/formPatterns/catalog/topLevel/dialog.js +187 -0
- package/dist/knowledge/formPatterns/catalog/topLevel/dialog.js.map +1 -0
- package/dist/knowledge/formPatterns/catalog/topLevel/factBox.d.ts +10 -0
- package/dist/knowledge/formPatterns/catalog/topLevel/factBox.d.ts.map +1 -0
- package/dist/knowledge/formPatterns/catalog/topLevel/factBox.js +54 -0
- package/dist/knowledge/formPatterns/catalog/topLevel/factBox.js.map +1 -0
- package/dist/knowledge/formPatterns/catalog/topLevel/listPage.d.ts +7 -0
- package/dist/knowledge/formPatterns/catalog/topLevel/listPage.d.ts.map +1 -0
- package/dist/knowledge/formPatterns/catalog/topLevel/listPage.js +33 -0
- package/dist/knowledge/formPatterns/catalog/topLevel/listPage.js.map +1 -0
- package/dist/knowledge/formPatterns/catalog/topLevel/lookup.d.ts +10 -0
- package/dist/knowledge/formPatterns/catalog/topLevel/lookup.d.ts.map +1 -0
- package/dist/knowledge/formPatterns/catalog/topLevel/lookup.js +95 -0
- package/dist/knowledge/formPatterns/catalog/topLevel/lookup.js.map +1 -0
- package/dist/knowledge/formPatterns/catalog/topLevel/simpleDetails.d.ts +16 -0
- package/dist/knowledge/formPatterns/catalog/topLevel/simpleDetails.d.ts.map +1 -0
- package/dist/knowledge/formPatterns/catalog/topLevel/simpleDetails.js +158 -0
- package/dist/knowledge/formPatterns/catalog/topLevel/simpleDetails.js.map +1 -0
- package/dist/knowledge/formPatterns/catalog/topLevel/simpleList.d.ts +7 -0
- package/dist/knowledge/formPatterns/catalog/topLevel/simpleList.d.ts.map +1 -0
- package/dist/knowledge/formPatterns/catalog/topLevel/simpleList.js +34 -0
- package/dist/knowledge/formPatterns/catalog/topLevel/simpleList.js.map +1 -0
- package/dist/knowledge/formPatterns/catalog/topLevel/simpleListDetails.d.ts +9 -0
- package/dist/knowledge/formPatterns/catalog/topLevel/simpleListDetails.d.ts.map +1 -0
- package/dist/knowledge/formPatterns/catalog/topLevel/simpleListDetails.js +99 -0
- package/dist/knowledge/formPatterns/catalog/topLevel/simpleListDetails.js.map +1 -0
- package/dist/knowledge/formPatterns/catalog/topLevel/tableOfContents.d.ts +8 -0
- package/dist/knowledge/formPatterns/catalog/topLevel/tableOfContents.d.ts.map +1 -0
- package/dist/knowledge/formPatterns/catalog/topLevel/tableOfContents.js +95 -0
- package/dist/knowledge/formPatterns/catalog/topLevel/tableOfContents.js.map +1 -0
- package/dist/knowledge/formPatterns/catalog/topLevel/task.d.ts +9 -0
- package/dist/knowledge/formPatterns/catalog/topLevel/task.d.ts.map +1 -0
- package/dist/knowledge/formPatterns/catalog/topLevel/task.js +42 -0
- package/dist/knowledge/formPatterns/catalog/topLevel/task.js.map +1 -0
- package/dist/knowledge/formPatterns/catalog/topLevel/wizard.d.ts +7 -0
- package/dist/knowledge/formPatterns/catalog/topLevel/wizard.d.ts.map +1 -0
- package/dist/knowledge/formPatterns/catalog/topLevel/wizard.js +42 -0
- package/dist/knowledge/formPatterns/catalog/topLevel/wizard.js.map +1 -0
- package/dist/knowledge/formPatterns/catalog/topLevel/workspace.d.ts +17 -0
- package/dist/knowledge/formPatterns/catalog/topLevel/workspace.d.ts.map +1 -0
- package/dist/knowledge/formPatterns/catalog/topLevel/workspace.js +157 -0
- package/dist/knowledge/formPatterns/catalog/topLevel/workspace.js.map +1 -0
- package/dist/knowledge/formPatterns/crossCheck.d.ts +44 -0
- package/dist/knowledge/formPatterns/crossCheck.d.ts.map +1 -0
- package/dist/knowledge/formPatterns/crossCheck.js +109 -0
- package/dist/knowledge/formPatterns/crossCheck.js.map +1 -0
- package/dist/knowledge/formPatterns/index.d.ts +30 -0
- package/dist/knowledge/formPatterns/index.d.ts.map +1 -0
- package/dist/knowledge/formPatterns/index.js +158 -0
- package/dist/knowledge/formPatterns/index.js.map +1 -0
- package/dist/knowledge/formPatterns/methodStubs.d.ts +45 -0
- package/dist/knowledge/formPatterns/methodStubs.d.ts.map +1 -0
- package/dist/knowledge/formPatterns/methodStubs.js +257 -0
- package/dist/knowledge/formPatterns/methodStubs.js.map +1 -0
- package/dist/knowledge/formPatterns/types.d.ts +115 -0
- package/dist/knowledge/formPatterns/types.d.ts.map +1 -0
- package/dist/knowledge/formPatterns/types.js +44 -0
- package/dist/knowledge/formPatterns/types.js.map +1 -0
- package/dist/metadata/enhancedParser.d.ts +91 -0
- package/dist/metadata/enhancedParser.d.ts.map +1 -0
- package/dist/metadata/enhancedParser.js +379 -0
- package/dist/metadata/enhancedParser.js.map +1 -0
- package/dist/metadata/formPatternMiner.d.ts +78 -0
- package/dist/metadata/formPatternMiner.d.ts.map +1 -0
- package/dist/metadata/formPatternMiner.js +220 -0
- package/dist/metadata/formPatternMiner.js.map +1 -0
- package/dist/metadata/labelParser.d.ts +71 -0
- package/dist/metadata/labelParser.d.ts.map +1 -0
- package/dist/metadata/labelParser.js +258 -0
- package/dist/metadata/labelParser.js.map +1 -0
- package/dist/metadata/symbolCountsWorker.d.ts +16 -0
- package/dist/metadata/symbolCountsWorker.d.ts.map +1 -0
- package/dist/metadata/symbolCountsWorker.js +42 -0
- package/dist/metadata/symbolCountsWorker.js.map +1 -0
- package/dist/metadata/symbolIndex.d.ts +474 -0
- package/dist/metadata/symbolIndex.d.ts.map +1 -0
- package/dist/metadata/symbolIndex.js +3152 -0
- package/dist/metadata/symbolIndex.js.map +1 -0
- package/dist/metadata/types.d.ts +267 -0
- package/dist/metadata/types.d.ts.map +1 -0
- package/dist/metadata/types.js +5 -0
- package/dist/metadata/types.js.map +1 -0
- package/dist/metadata/xmlParser.d.ts +232 -0
- package/dist/metadata/xmlParser.d.ts.map +1 -0
- package/dist/metadata/xmlParser.js +1021 -0
- package/dist/metadata/xmlParser.js.map +1 -0
- package/dist/metadata/xppDeclaration.d.ts +116 -0
- package/dist/metadata/xppDeclaration.d.ts.map +1 -0
- package/dist/metadata/xppDeclaration.js +350 -0
- package/dist/metadata/xppDeclaration.js.map +1 -0
- package/dist/middleware/apiKeyAuth.d.ts +7 -0
- package/dist/middleware/apiKeyAuth.d.ts.map +1 -0
- package/dist/middleware/apiKeyAuth.js +70 -0
- package/dist/middleware/apiKeyAuth.js.map +1 -0
- package/dist/middleware/rateLimiter.d.ts +7 -0
- package/dist/middleware/rateLimiter.d.ts.map +1 -0
- package/dist/middleware/rateLimiter.js +78 -0
- package/dist/middleware/rateLimiter.js.map +1 -0
- package/dist/prompts/codeReview.d.ts +8 -0
- package/dist/prompts/codeReview.d.ts.map +1 -0
- package/dist/prompts/codeReview.js +619 -0
- package/dist/prompts/codeReview.js.map +1 -0
- package/dist/prompts/index.d.ts +6 -0
- package/dist/prompts/index.d.ts.map +1 -0
- package/dist/prompts/index.js +6 -0
- package/dist/prompts/index.js.map +1 -0
- package/dist/prompts/systemInstructions.d.ts +33 -0
- package/dist/prompts/systemInstructions.d.ts.map +1 -0
- package/dist/prompts/systemInstructions.js +154 -0
- package/dist/prompts/systemInstructions.js.map +1 -0
- package/dist/resources/classResource.d.ts +17 -0
- package/dist/resources/classResource.d.ts.map +1 -0
- package/dist/resources/classResource.js +33 -0
- package/dist/resources/classResource.js.map +1 -0
- package/dist/resources/index.d.ts +20 -0
- package/dist/resources/index.d.ts.map +1 -0
- package/dist/resources/index.js +154 -0
- package/dist/resources/index.js.map +1 -0
- package/dist/server/mcpServer.d.ts +11 -0
- package/dist/server/mcpServer.d.ts.map +1 -0
- package/dist/server/mcpServer.js +185 -0
- package/dist/server/mcpServer.js.map +1 -0
- package/dist/server/serverMode.d.ts +53 -0
- package/dist/server/serverMode.d.ts.map +1 -0
- package/dist/server/serverMode.js +72 -0
- package/dist/server/serverMode.js.map +1 -0
- package/dist/server/toolAnnotations.d.ts +28 -0
- package/dist/server/toolAnnotations.d.ts.map +1 -0
- package/dist/server/toolAnnotations.js +70 -0
- package/dist/server/toolAnnotations.js.map +1 -0
- package/dist/server/toolSchemas/analyzeCode.d.ts +71 -0
- package/dist/server/toolSchemas/analyzeCode.d.ts.map +1 -0
- package/dist/server/toolSchemas/analyzeCode.js +50 -0
- package/dist/server/toolSchemas/analyzeCode.js.map +1 -0
- package/dist/server/toolSchemas/batchGetInfo.d.ts +32 -0
- package/dist/server/toolSchemas/batchGetInfo.d.ts.map +1 -0
- package/dist/server/toolSchemas/batchGetInfo.js +35 -0
- package/dist/server/toolSchemas/batchGetInfo.js.map +1 -0
- package/dist/server/toolSchemas/buildD365foProject.d.ts +44 -0
- package/dist/server/toolSchemas/buildD365foProject.d.ts.map +1 -0
- package/dist/server/toolSchemas/buildD365foProject.js +47 -0
- package/dist/server/toolSchemas/buildD365foProject.js.map +1 -0
- package/dist/server/toolSchemas/d365foFile.d.ts +99 -0
- package/dist/server/toolSchemas/d365foFile.d.ts.map +1 -0
- package/dist/server/toolSchemas/d365foFile.js +163 -0
- package/dist/server/toolSchemas/d365foFile.js.map +1 -0
- package/dist/server/toolSchemas/extensionInfo.d.ts +65 -0
- package/dist/server/toolSchemas/extensionInfo.d.ts.map +1 -0
- package/dist/server/toolSchemas/extensionInfo.js +73 -0
- package/dist/server/toolSchemas/extensionInfo.js.map +1 -0
- package/dist/server/toolSchemas/findReferences.d.ts +35 -0
- package/dist/server/toolSchemas/findReferences.d.ts.map +1 -0
- package/dist/server/toolSchemas/findReferences.js +35 -0
- package/dist/server/toolSchemas/findReferences.js.map +1 -0
- package/dist/server/toolSchemas/generateObject.d.ts +246 -0
- package/dist/server/toolSchemas/generateObject.d.ts.map +1 -0
- package/dist/server/toolSchemas/generateObject.js +158 -0
- package/dist/server/toolSchemas/generateObject.js.map +1 -0
- package/dist/server/toolSchemas/getKnowledge.d.ts +39 -0
- package/dist/server/toolSchemas/getKnowledge.d.ts.map +1 -0
- package/dist/server/toolSchemas/getKnowledge.js +46 -0
- package/dist/server/toolSchemas/getKnowledge.js.map +1 -0
- package/dist/server/toolSchemas/getMethod.d.ts +30 -0
- package/dist/server/toolSchemas/getMethod.d.ts.map +1 -0
- package/dist/server/toolSchemas/getMethod.js +34 -0
- package/dist/server/toolSchemas/getMethod.js.map +1 -0
- package/dist/server/toolSchemas/getObjectInfo.d.ts +24 -0
- package/dist/server/toolSchemas/getObjectInfo.d.ts.map +1 -0
- package/dist/server/toolSchemas/getObjectInfo.js +30 -0
- package/dist/server/toolSchemas/getObjectInfo.js.map +1 -0
- package/dist/server/toolSchemas/getWorkspaceInfo.d.ts +29 -0
- package/dist/server/toolSchemas/getWorkspaceInfo.d.ts.map +1 -0
- package/dist/server/toolSchemas/getWorkspaceInfo.js +29 -0
- package/dist/server/toolSchemas/getWorkspaceInfo.js.map +1 -0
- package/dist/server/toolSchemas/index.d.ts +1142 -0
- package/dist/server/toolSchemas/index.d.ts.map +1 -0
- package/dist/server/toolSchemas/index.js +60 -0
- package/dist/server/toolSchemas/index.js.map +1 -0
- package/dist/server/toolSchemas/labels.d.ts +172 -0
- package/dist/server/toolSchemas/labels.d.ts.map +1 -0
- package/dist/server/toolSchemas/labels.js +159 -0
- package/dist/server/toolSchemas/labels.js.map +1 -0
- package/dist/server/toolSchemas/objectPatterns.d.ts +93 -0
- package/dist/server/toolSchemas/objectPatterns.d.ts.map +1 -0
- package/dist/server/toolSchemas/objectPatterns.js +104 -0
- package/dist/server/toolSchemas/objectPatterns.js.map +1 -0
- package/dist/server/toolSchemas/prepare.d.ts +49 -0
- package/dist/server/toolSchemas/prepare.d.ts.map +1 -0
- package/dist/server/toolSchemas/prepare.js +57 -0
- package/dist/server/toolSchemas/prepare.js.map +1 -0
- package/dist/server/toolSchemas/reviewWorkspaceChanges.d.ts +20 -0
- package/dist/server/toolSchemas/reviewWorkspaceChanges.d.ts.map +1 -0
- package/dist/server/toolSchemas/reviewWorkspaceChanges.js +19 -0
- package/dist/server/toolSchemas/reviewWorkspaceChanges.js.map +1 -0
- package/dist/server/toolSchemas/runBpCheck.d.ts +36 -0
- package/dist/server/toolSchemas/runBpCheck.d.ts.map +1 -0
- package/dist/server/toolSchemas/runBpCheck.js +21 -0
- package/dist/server/toolSchemas/runBpCheck.js.map +1 -0
- package/dist/server/toolSchemas/runSystestClass.d.ts +32 -0
- package/dist/server/toolSchemas/runSystestClass.d.ts.map +1 -0
- package/dist/server/toolSchemas/runSystestClass.js +20 -0
- package/dist/server/toolSchemas/runSystestClass.js.map +1 -0
- package/dist/server/toolSchemas/search.d.ts +109 -0
- package/dist/server/toolSchemas/search.d.ts.map +1 -0
- package/dist/server/toolSchemas/search.js +123 -0
- package/dist/server/toolSchemas/search.js.map +1 -0
- package/dist/server/toolSchemas/securityInfo.d.ts +45 -0
- package/dist/server/toolSchemas/securityInfo.d.ts.map +1 -0
- package/dist/server/toolSchemas/securityInfo.js +39 -0
- package/dist/server/toolSchemas/securityInfo.js.map +1 -0
- package/dist/server/toolSchemas/suggestEdt.d.ts +29 -0
- package/dist/server/toolSchemas/suggestEdt.d.ts.map +1 -0
- package/dist/server/toolSchemas/suggestEdt.js +29 -0
- package/dist/server/toolSchemas/suggestEdt.js.map +1 -0
- package/dist/server/toolSchemas/triggerDbSync.d.ts +47 -0
- package/dist/server/toolSchemas/triggerDbSync.d.ts.map +1 -0
- package/dist/server/toolSchemas/triggerDbSync.js +31 -0
- package/dist/server/toolSchemas/triggerDbSync.js.map +1 -0
- package/dist/server/toolSchemas/undoLastModification.d.ts +20 -0
- package/dist/server/toolSchemas/undoLastModification.d.ts.map +1 -0
- package/dist/server/toolSchemas/undoLastModification.js +17 -0
- package/dist/server/toolSchemas/undoLastModification.js.map +1 -0
- package/dist/server/toolSchemas/updateSymbolIndex.d.ts +19 -0
- package/dist/server/toolSchemas/updateSymbolIndex.d.ts.map +1 -0
- package/dist/server/toolSchemas/updateSymbolIndex.js +18 -0
- package/dist/server/toolSchemas/updateSymbolIndex.js.map +1 -0
- package/dist/server/toolSchemas/validateCode.d.ts +35 -0
- package/dist/server/toolSchemas/validateCode.d.ts.map +1 -0
- package/dist/server/toolSchemas/validateCode.js +38 -0
- package/dist/server/toolSchemas/validateCode.js.map +1 -0
- package/dist/server/toolSchemas/validateObjectNaming.d.ts +33 -0
- package/dist/server/toolSchemas/validateObjectNaming.d.ts.map +1 -0
- package/dist/server/toolSchemas/validateObjectNaming.js +32 -0
- package/dist/server/toolSchemas/validateObjectNaming.js.map +1 -0
- package/dist/server/toolSchemas/verifyD365foProject.d.ts +50 -0
- package/dist/server/toolSchemas/verifyD365foProject.d.ts.map +1 -0
- package/dist/server/toolSchemas/verifyD365foProject.js +46 -0
- package/dist/server/toolSchemas/verifyD365foProject.js.map +1 -0
- package/dist/server/transport.d.ts +30 -0
- package/dist/server/transport.d.ts.map +1 -0
- package/dist/server/transport.js +391 -0
- package/dist/server/transport.js.map +1 -0
- package/dist/tools/analyzeCode.d.ts +17 -0
- package/dist/tools/analyzeCode.d.ts.map +1 -0
- package/dist/tools/analyzeCode.js +63 -0
- package/dist/tools/analyzeCode.js.map +1 -0
- package/dist/tools/analyzeCompleteness.d.ts +20 -0
- package/dist/tools/analyzeCompleteness.d.ts.map +1 -0
- package/dist/tools/analyzeCompleteness.js +103 -0
- package/dist/tools/analyzeCompleteness.js.map +1 -0
- package/dist/tools/analyzeExtensionPoints.d.ts +21 -0
- package/dist/tools/analyzeExtensionPoints.d.ts.map +1 -0
- package/dist/tools/analyzeExtensionPoints.js +343 -0
- package/dist/tools/analyzeExtensionPoints.js.map +1 -0
- package/dist/tools/analyzePatterns.d.ts +20 -0
- package/dist/tools/analyzePatterns.d.ts.map +1 -0
- package/dist/tools/analyzePatterns.js +71 -0
- package/dist/tools/analyzePatterns.js.map +1 -0
- package/dist/tools/apiUsagePatterns.d.ts +20 -0
- package/dist/tools/apiUsagePatterns.d.ts.map +1 -0
- package/dist/tools/apiUsagePatterns.js +136 -0
- package/dist/tools/apiUsagePatterns.js.map +1 -0
- package/dist/tools/batchGetInfo.d.ts +50 -0
- package/dist/tools/batchGetInfo.d.ts.map +1 -0
- package/dist/tools/batchGetInfo.js +52 -0
- package/dist/tools/batchGetInfo.js.map +1 -0
- package/dist/tools/batchSearch.d.ts +64 -0
- package/dist/tools/batchSearch.d.ts.map +1 -0
- package/dist/tools/batchSearch.js +265 -0
- package/dist/tools/batchSearch.js.map +1 -0
- package/dist/tools/buildProject.d.ts +28 -0
- package/dist/tools/buildProject.d.ts.map +1 -0
- package/dist/tools/buildProject.js +929 -0
- package/dist/tools/buildProject.js.map +1 -0
- package/dist/tools/classInfo.d.ts +8 -0
- package/dist/tools/classInfo.d.ts.map +1 -0
- package/dist/tools/classInfo.js +235 -0
- package/dist/tools/classInfo.js.map +1 -0
- package/dist/tools/codeGen.d.ts +19 -0
- package/dist/tools/codeGen.d.ts.map +1 -0
- package/dist/tools/codeGen.js +1956 -0
- package/dist/tools/codeGen.js.map +1 -0
- package/dist/tools/completion.d.ts +8 -0
- package/dist/tools/completion.d.ts.map +1 -0
- package/dist/tools/completion.js +272 -0
- package/dist/tools/completion.js.map +1 -0
- package/dist/tools/configKeyInfo.d.ts +22 -0
- package/dist/tools/configKeyInfo.d.ts.map +1 -0
- package/dist/tools/configKeyInfo.js +74 -0
- package/dist/tools/configKeyInfo.js.map +1 -0
- package/dist/tools/createD365File.d.ts +479 -0
- package/dist/tools/createD365File.d.ts.map +1 -0
- package/dist/tools/createD365File.js +4185 -0
- package/dist/tools/createD365File.js.map +1 -0
- package/dist/tools/createLabel.d.ts +51 -0
- package/dist/tools/createLabel.d.ts.map +1 -0
- package/dist/tools/createLabel.js +761 -0
- package/dist/tools/createLabel.js.map +1 -0
- package/dist/tools/d365foErrorHelp.d.ts +29 -0
- package/dist/tools/d365foErrorHelp.d.ts.map +1 -0
- package/dist/tools/d365foErrorHelp.js +389 -0
- package/dist/tools/d365foErrorHelp.js.map +1 -0
- package/dist/tools/d365foFile.d.ts +20 -0
- package/dist/tools/d365foFile.d.ts.map +1 -0
- package/dist/tools/d365foFile.js +58 -0
- package/dist/tools/d365foFile.js.map +1 -0
- package/dist/tools/d365foFileOpSpecs.d.ts +41 -0
- package/dist/tools/d365foFileOpSpecs.d.ts.map +1 -0
- package/dist/tools/d365foFileOpSpecs.js +336 -0
- package/dist/tools/d365foFileOpSpecs.js.map +1 -0
- package/dist/tools/dataEntityInfo.d.ts +23 -0
- package/dist/tools/dataEntityInfo.d.ts.map +1 -0
- package/dist/tools/dataEntityInfo.js +45 -0
- package/dist/tools/dataEntityInfo.js.map +1 -0
- package/dist/tools/dataEntityXml.d.ts +31 -0
- package/dist/tools/dataEntityXml.d.ts.map +1 -0
- package/dist/tools/dataEntityXml.js +131 -0
- package/dist/tools/dataEntityXml.js.map +1 -0
- package/dist/tools/dbSync.d.ts +8 -0
- package/dist/tools/dbSync.d.ts.map +1 -0
- package/dist/tools/dbSync.js +285 -0
- package/dist/tools/dbSync.js.map +1 -0
- package/dist/tools/edtInfo.d.ts +23 -0
- package/dist/tools/edtInfo.d.ts.map +1 -0
- package/dist/tools/edtInfo.js +122 -0
- package/dist/tools/edtInfo.js.map +1 -0
- package/dist/tools/enumInfo.d.ts +17 -0
- package/dist/tools/enumInfo.d.ts.map +1 -0
- package/dist/tools/enumInfo.js +44 -0
- package/dist/tools/enumInfo.js.map +1 -0
- package/dist/tools/extensionInfo.d.ts +26 -0
- package/dist/tools/extensionInfo.d.ts.map +1 -0
- package/dist/tools/extensionInfo.js +73 -0
- package/dist/tools/extensionInfo.js.map +1 -0
- package/dist/tools/extensionSearch.d.ts +20 -0
- package/dist/tools/extensionSearch.d.ts.map +1 -0
- package/dist/tools/extensionSearch.js +72 -0
- package/dist/tools/extensionSearch.js.map +1 -0
- package/dist/tools/extensionStrategyAdvisor.d.ts +15 -0
- package/dist/tools/extensionStrategyAdvisor.d.ts.map +1 -0
- package/dist/tools/extensionStrategyAdvisor.js +519 -0
- package/dist/tools/extensionStrategyAdvisor.js.map +1 -0
- package/dist/tools/findCocExtensions.d.ts +20 -0
- package/dist/tools/findCocExtensions.d.ts.map +1 -0
- package/dist/tools/findCocExtensions.js +285 -0
- package/dist/tools/findCocExtensions.js.map +1 -0
- package/dist/tools/findEventHandlers.d.ts +21 -0
- package/dist/tools/findEventHandlers.d.ts.map +1 -0
- package/dist/tools/findEventHandlers.js +196 -0
- package/dist/tools/findEventHandlers.js.map +1 -0
- package/dist/tools/findReferences.d.ts +30 -0
- package/dist/tools/findReferences.d.ts.map +1 -0
- package/dist/tools/findReferences.js +551 -0
- package/dist/tools/findReferences.js.map +1 -0
- package/dist/tools/formInfo.d.ts +13 -0
- package/dist/tools/formInfo.d.ts.map +1 -0
- package/dist/tools/formInfo.js +407 -0
- package/dist/tools/formInfo.js.map +1 -0
- package/dist/tools/formPattern.d.ts +19 -0
- package/dist/tools/formPattern.d.ts.map +1 -0
- package/dist/tools/formPattern.js +52 -0
- package/dist/tools/formPattern.js.map +1 -0
- package/dist/tools/generateD365Xml.d.ts +12 -0
- package/dist/tools/generateD365Xml.d.ts.map +1 -0
- package/dist/tools/generateD365Xml.js +1454 -0
- package/dist/tools/generateD365Xml.js.map +1 -0
- package/dist/tools/generateFindMethods.d.ts +69 -0
- package/dist/tools/generateFindMethods.d.ts.map +1 -0
- package/dist/tools/generateFindMethods.js +207 -0
- package/dist/tools/generateFindMethods.js.map +1 -0
- package/dist/tools/generateMetadata.d.ts +37 -0
- package/dist/tools/generateMetadata.d.ts.map +1 -0
- package/dist/tools/generateMetadata.js +213 -0
- package/dist/tools/generateMetadata.js.map +1 -0
- package/dist/tools/generateObject.d.ts +34 -0
- package/dist/tools/generateObject.d.ts.map +1 -0
- package/dist/tools/generateObject.js +47 -0
- package/dist/tools/generateObject.js.map +1 -0
- package/dist/tools/generateRelationXpp.d.ts +45 -0
- package/dist/tools/generateRelationXpp.d.ts.map +1 -0
- package/dist/tools/generateRelationXpp.js +129 -0
- package/dist/tools/generateRelationXpp.js.map +1 -0
- package/dist/tools/generateSmart.d.ts +32 -0
- package/dist/tools/generateSmart.d.ts.map +1 -0
- package/dist/tools/generateSmart.js +52 -0
- package/dist/tools/generateSmart.js.map +1 -0
- package/dist/tools/generateSmartForm.d.ts +82 -0
- package/dist/tools/generateSmartForm.d.ts.map +1 -0
- package/dist/tools/generateSmartForm.js +996 -0
- package/dist/tools/generateSmartForm.js.map +1 -0
- package/dist/tools/generateSmartReport.d.ts +90 -0
- package/dist/tools/generateSmartReport.d.ts.map +1 -0
- package/dist/tools/generateSmartReport.js +1254 -0
- package/dist/tools/generateSmartReport.js.map +1 -0
- package/dist/tools/generateSmartTable.d.ts +138 -0
- package/dist/tools/generateSmartTable.d.ts.map +1 -0
- package/dist/tools/generateSmartTable.js +1305 -0
- package/dist/tools/generateSmartTable.js.map +1 -0
- package/dist/tools/generateTableFields.d.ts +48 -0
- package/dist/tools/generateTableFields.d.ts.map +1 -0
- package/dist/tools/generateTableFields.js +186 -0
- package/dist/tools/generateTableFields.js.map +1 -0
- package/dist/tools/generateTableRelation.d.ts +35 -0
- package/dist/tools/generateTableRelation.d.ts.map +1 -0
- package/dist/tools/generateTableRelation.js +161 -0
- package/dist/tools/generateTableRelation.js.map +1 -0
- package/dist/tools/getFormPatternSpec.d.ts +13 -0
- package/dist/tools/getFormPatternSpec.d.ts.map +1 -0
- package/dist/tools/getFormPatternSpec.js +290 -0
- package/dist/tools/getFormPatternSpec.js.map +1 -0
- package/dist/tools/getFormPatterns.d.ts +68 -0
- package/dist/tools/getFormPatterns.d.ts.map +1 -0
- package/dist/tools/getFormPatterns.js +471 -0
- package/dist/tools/getFormPatterns.js.map +1 -0
- package/dist/tools/getKnowledge.d.ts +27 -0
- package/dist/tools/getKnowledge.d.ts.map +1 -0
- package/dist/tools/getKnowledge.js +50 -0
- package/dist/tools/getKnowledge.js.map +1 -0
- package/dist/tools/getLabelInfo.d.ts +21 -0
- package/dist/tools/getLabelInfo.d.ts.map +1 -0
- package/dist/tools/getLabelInfo.js +138 -0
- package/dist/tools/getLabelInfo.js.map +1 -0
- package/dist/tools/getMethod.d.ts +19 -0
- package/dist/tools/getMethod.d.ts.map +1 -0
- package/dist/tools/getMethod.js +77 -0
- package/dist/tools/getMethod.js.map +1 -0
- package/dist/tools/getMethodSource.d.ts +17 -0
- package/dist/tools/getMethodSource.d.ts.map +1 -0
- package/dist/tools/getMethodSource.js +161 -0
- package/dist/tools/getMethodSource.js.map +1 -0
- package/dist/tools/getObjectInfo.d.ts +17 -0
- package/dist/tools/getObjectInfo.d.ts.map +1 -0
- package/dist/tools/getObjectInfo.js +88 -0
- package/dist/tools/getObjectInfo.js.map +1 -0
- package/dist/tools/getTablePatterns.d.ts +45 -0
- package/dist/tools/getTablePatterns.d.ts.map +1 -0
- package/dist/tools/getTablePatterns.js +235 -0
- package/dist/tools/getTablePatterns.js.map +1 -0
- package/dist/tools/index.d.ts +11 -0
- package/dist/tools/index.d.ts.map +1 -0
- package/dist/tools/index.js +11 -0
- package/dist/tools/index.js.map +1 -0
- package/dist/tools/labels.d.ts +25 -0
- package/dist/tools/labels.d.ts.map +1 -0
- package/dist/tools/labels.js +111 -0
- package/dist/tools/labels.js.map +1 -0
- package/dist/tools/macroInfo.d.ts +23 -0
- package/dist/tools/macroInfo.d.ts.map +1 -0
- package/dist/tools/macroInfo.js +62 -0
- package/dist/tools/macroInfo.js.map +1 -0
- package/dist/tools/mapInfo.d.ts +21 -0
- package/dist/tools/mapInfo.d.ts.map +1 -0
- package/dist/tools/mapInfo.js +54 -0
- package/dist/tools/mapInfo.js.map +1 -0
- package/dist/tools/mapXml.d.ts +26 -0
- package/dist/tools/mapXml.d.ts.map +1 -0
- package/dist/tools/mapXml.js +88 -0
- package/dist/tools/mapXml.js.map +1 -0
- package/dist/tools/menuItemInfo.d.ts +20 -0
- package/dist/tools/menuItemInfo.d.ts.map +1 -0
- package/dist/tools/menuItemInfo.js +185 -0
- package/dist/tools/menuItemInfo.js.map +1 -0
- package/dist/tools/methodSignature.d.ts +33 -0
- package/dist/tools/methodSignature.d.ts.map +1 -0
- package/dist/tools/methodSignature.js +348 -0
- package/dist/tools/methodSignature.js.map +1 -0
- package/dist/tools/modifyD365File.d.ts +130 -0
- package/dist/tools/modifyD365File.d.ts.map +1 -0
- package/dist/tools/modifyD365File.js +2179 -0
- package/dist/tools/modifyD365File.js.map +1 -0
- package/dist/tools/objectInfoRegistry.d.ts +36 -0
- package/dist/tools/objectInfoRegistry.d.ts.map +1 -0
- package/dist/tools/objectInfoRegistry.js +98 -0
- package/dist/tools/objectInfoRegistry.js.map +1 -0
- package/dist/tools/objectPatterns.d.ts +16 -0
- package/dist/tools/objectPatterns.d.ts.map +1 -0
- package/dist/tools/objectPatterns.js +84 -0
- package/dist/tools/objectPatterns.js.map +1 -0
- package/dist/tools/prepare.d.ts +18 -0
- package/dist/tools/prepare.d.ts.map +1 -0
- package/dist/tools/prepare.js +47 -0
- package/dist/tools/prepare.js.map +1 -0
- package/dist/tools/prepareChange.d.ts +43 -0
- package/dist/tools/prepareChange.d.ts.map +1 -0
- package/dist/tools/prepareChange.js +327 -0
- package/dist/tools/prepareChange.js.map +1 -0
- package/dist/tools/prepareCreate.d.ts +45 -0
- package/dist/tools/prepareCreate.d.ts.map +1 -0
- package/dist/tools/prepareCreate.js +263 -0
- package/dist/tools/prepareCreate.js.map +1 -0
- package/dist/tools/queryInfo.d.ts +17 -0
- package/dist/tools/queryInfo.d.ts.map +1 -0
- package/dist/tools/queryInfo.js +46 -0
- package/dist/tools/queryInfo.js.map +1 -0
- package/dist/tools/queryViewXml.d.ts +36 -0
- package/dist/tools/queryViewXml.d.ts.map +1 -0
- package/dist/tools/queryViewXml.js +129 -0
- package/dist/tools/queryViewXml.js.map +1 -0
- package/dist/tools/renameLabel.d.ts +29 -0
- package/dist/tools/renameLabel.d.ts.map +1 -0
- package/dist/tools/renameLabel.js +377 -0
- package/dist/tools/renameLabel.js.map +1 -0
- package/dist/tools/repairFormControls.d.ts +21 -0
- package/dist/tools/repairFormControls.d.ts.map +1 -0
- package/dist/tools/repairFormControls.js +151 -0
- package/dist/tools/repairFormControls.js.map +1 -0
- package/dist/tools/reportInfo.d.ts +14 -0
- package/dist/tools/reportInfo.d.ts.map +1 -0
- package/dist/tools/reportInfo.js +302 -0
- package/dist/tools/reportInfo.js.map +1 -0
- package/dist/tools/resolveReferences.d.ts +89 -0
- package/dist/tools/resolveReferences.d.ts.map +1 -0
- package/dist/tools/resolveReferences.js +791 -0
- package/dist/tools/resolveReferences.js.map +1 -0
- package/dist/tools/reviewWorkspaceChanges.d.ts +14 -0
- package/dist/tools/reviewWorkspaceChanges.d.ts.map +1 -0
- package/dist/tools/reviewWorkspaceChanges.js +73 -0
- package/dist/tools/reviewWorkspaceChanges.js.map +1 -0
- package/dist/tools/runBpCheck.d.ts +14 -0
- package/dist/tools/runBpCheck.d.ts.map +1 -0
- package/dist/tools/runBpCheck.js +241 -0
- package/dist/tools/runBpCheck.js.map +1 -0
- package/dist/tools/search.d.ts +20 -0
- package/dist/tools/search.d.ts.map +1 -0
- package/dist/tools/search.js +246 -0
- package/dist/tools/search.js.map +1 -0
- package/dist/tools/searchLabels.d.ts +26 -0
- package/dist/tools/searchLabels.d.ts.map +1 -0
- package/dist/tools/searchLabels.js +91 -0
- package/dist/tools/searchLabels.js.map +1 -0
- package/dist/tools/searchUnified.d.ts +28 -0
- package/dist/tools/searchUnified.d.ts.map +1 -0
- package/dist/tools/searchUnified.js +48 -0
- package/dist/tools/searchUnified.js.map +1 -0
- package/dist/tools/securityArtifactInfo.d.ts +14 -0
- package/dist/tools/securityArtifactInfo.d.ts.map +1 -0
- package/dist/tools/securityArtifactInfo.js +192 -0
- package/dist/tools/securityArtifactInfo.js.map +1 -0
- package/dist/tools/securityCoverageInfo.d.ts +21 -0
- package/dist/tools/securityCoverageInfo.d.ts.map +1 -0
- package/dist/tools/securityCoverageInfo.js +248 -0
- package/dist/tools/securityCoverageInfo.js.map +1 -0
- package/dist/tools/securityInfo.d.ts +22 -0
- package/dist/tools/securityInfo.d.ts.map +1 -0
- package/dist/tools/securityInfo.js +43 -0
- package/dist/tools/securityInfo.js.map +1 -0
- package/dist/tools/securityPolicyInfo.d.ts +22 -0
- package/dist/tools/securityPolicyInfo.d.ts.map +1 -0
- package/dist/tools/securityPolicyInfo.js +49 -0
- package/dist/tools/securityPolicyInfo.js.map +1 -0
- package/dist/tools/securityPrivilegeXml.d.ts +21 -0
- package/dist/tools/securityPrivilegeXml.d.ts.map +1 -0
- package/dist/tools/securityPrivilegeXml.js +61 -0
- package/dist/tools/securityPrivilegeXml.js.map +1 -0
- package/dist/tools/serviceInfo.d.ts +25 -0
- package/dist/tools/serviceInfo.d.ts.map +1 -0
- package/dist/tools/serviceInfo.js +93 -0
- package/dist/tools/serviceInfo.js.map +1 -0
- package/dist/tools/suggestEdt.d.ts +15 -0
- package/dist/tools/suggestEdt.d.ts.map +1 -0
- package/dist/tools/suggestEdt.js +348 -0
- package/dist/tools/suggestEdt.js.map +1 -0
- package/dist/tools/suggestImplementation.d.ts +20 -0
- package/dist/tools/suggestImplementation.d.ts.map +1 -0
- package/dist/tools/suggestImplementation.js +144 -0
- package/dist/tools/suggestImplementation.js.map +1 -0
- package/dist/tools/sysTestRunner.d.ts +14 -0
- package/dist/tools/sysTestRunner.d.ts.map +1 -0
- package/dist/tools/sysTestRunner.js +145 -0
- package/dist/tools/sysTestRunner.js.map +1 -0
- package/dist/tools/tableExtensionInfo.d.ts +91 -0
- package/dist/tools/tableExtensionInfo.d.ts.map +1 -0
- package/dist/tools/tableExtensionInfo.js +305 -0
- package/dist/tools/tableExtensionInfo.js.map +1 -0
- package/dist/tools/tableInfo.d.ts +23 -0
- package/dist/tools/tableInfo.d.ts.map +1 -0
- package/dist/tools/tableInfo.js +125 -0
- package/dist/tools/tableInfo.js.map +1 -0
- package/dist/tools/toolHandler.d.ts +4 -0
- package/dist/tools/toolHandler.d.ts.map +1 -0
- package/dist/tools/toolHandler.js +508 -0
- package/dist/tools/toolHandler.js.map +1 -0
- package/dist/tools/undoLastModification.d.ts +15 -0
- package/dist/tools/undoLastModification.d.ts.map +1 -0
- package/dist/tools/undoLastModification.js +147 -0
- package/dist/tools/undoLastModification.js.map +1 -0
- package/dist/tools/updateSymbolIndex.d.ts +15 -0
- package/dist/tools/updateSymbolIndex.d.ts.map +1 -0
- package/dist/tools/updateSymbolIndex.js +520 -0
- package/dist/tools/updateSymbolIndex.js.map +1 -0
- package/dist/tools/validateCode.d.ts +24 -0
- package/dist/tools/validateCode.d.ts.map +1 -0
- package/dist/tools/validateCode.js +201 -0
- package/dist/tools/validateCode.js.map +1 -0
- package/dist/tools/validateFormPattern.d.ts +51 -0
- package/dist/tools/validateFormPattern.d.ts.map +1 -0
- package/dist/tools/validateFormPattern.js +201 -0
- package/dist/tools/validateFormPattern.js.map +1 -0
- package/dist/tools/validateObjectNaming.d.ts +21 -0
- package/dist/tools/validateObjectNaming.d.ts.map +1 -0
- package/dist/tools/validateObjectNaming.js +319 -0
- package/dist/tools/validateObjectNaming.js.map +1 -0
- package/dist/tools/validateXpp.d.ts +79 -0
- package/dist/tools/validateXpp.d.ts.map +1 -0
- package/dist/tools/validateXpp.js +705 -0
- package/dist/tools/validateXpp.js.map +1 -0
- package/dist/tools/verifyD365Project.d.ts +21 -0
- package/dist/tools/verifyD365Project.d.ts.map +1 -0
- package/dist/tools/verifyD365Project.js +299 -0
- package/dist/tools/verifyD365Project.js.map +1 -0
- package/dist/tools/viewInfo.d.ts +17 -0
- package/dist/tools/viewInfo.d.ts.map +1 -0
- package/dist/tools/viewInfo.js +46 -0
- package/dist/tools/viewInfo.js.map +1 -0
- package/dist/tools/xppKnowledge.d.ts +45 -0
- package/dist/tools/xppKnowledge.d.ts.map +1 -0
- package/dist/tools/xppKnowledge.js +2815 -0
- package/dist/tools/xppKnowledge.js.map +1 -0
- package/dist/types/context.d.ts +56 -0
- package/dist/types/context.d.ts.map +1 -0
- package/dist/types/context.js +5 -0
- package/dist/types/context.js.map +1 -0
- package/dist/utils/callDedup.d.ts +29 -0
- package/dist/utils/callDedup.d.ts.map +1 -0
- package/dist/utils/callDedup.js +87 -0
- package/dist/utils/callDedup.js.map +1 -0
- package/dist/utils/configManager.d.ts +307 -0
- package/dist/utils/configManager.d.ts.map +1 -0
- package/dist/utils/configManager.js +1169 -0
- package/dist/utils/configManager.js.map +1 -0
- package/dist/utils/d365XmlNormalizer.d.ts +9 -0
- package/dist/utils/d365XmlNormalizer.d.ts.map +1 -0
- package/dist/utils/d365XmlNormalizer.js +24 -0
- package/dist/utils/d365XmlNormalizer.js.map +1 -0
- package/dist/utils/edtExtensionValidator.d.ts +110 -0
- package/dist/utils/edtExtensionValidator.d.ts.map +1 -0
- package/dist/utils/edtExtensionValidator.js +367 -0
- package/dist/utils/edtExtensionValidator.js.map +1 -0
- package/dist/utils/eolUtils.d.ts +15 -0
- package/dist/utils/eolUtils.d.ts.map +1 -0
- package/dist/utils/eolUtils.js +21 -0
- package/dist/utils/eolUtils.js.map +1 -0
- package/dist/utils/extractManifest.d.ts +34 -0
- package/dist/utils/extractManifest.d.ts.map +1 -0
- package/dist/utils/extractManifest.js +43 -0
- package/dist/utils/extractManifest.js.map +1 -0
- package/dist/utils/fieldControlTypes.d.ts +44 -0
- package/dist/utils/fieldControlTypes.d.ts.map +1 -0
- package/dist/utils/fieldControlTypes.js +97 -0
- package/dist/utils/fieldControlTypes.js.map +1 -0
- package/dist/utils/formCloner.d.ts +77 -0
- package/dist/utils/formCloner.d.ts.map +1 -0
- package/dist/utils/formCloner.js +364 -0
- package/dist/utils/formCloner.js.map +1 -0
- package/dist/utils/formControlExpander.d.ts +68 -0
- package/dist/utils/formControlExpander.d.ts.map +1 -0
- package/dist/utils/formControlExpander.js +207 -0
- package/dist/utils/formControlExpander.js.map +1 -0
- package/dist/utils/formControlRepair.d.ts +81 -0
- package/dist/utils/formControlRepair.d.ts.map +1 -0
- package/dist/utils/formControlRepair.js +203 -0
- package/dist/utils/formControlRepair.js.map +1 -0
- package/dist/utils/formExtensionShapeValidator.d.ts +44 -0
- package/dist/utils/formExtensionShapeValidator.d.ts.map +1 -0
- package/dist/utils/formExtensionShapeValidator.js +99 -0
- package/dist/utils/formExtensionShapeValidator.js.map +1 -0
- package/dist/utils/formPatternTemplates.d.ts +77 -0
- package/dist/utils/formPatternTemplates.d.ts.map +1 -0
- package/dist/utils/formPatternTemplates.js +1917 -0
- package/dist/utils/formPatternTemplates.js.map +1 -0
- package/dist/utils/fsExtensionScanner.d.ts +76 -0
- package/dist/utils/fsExtensionScanner.d.ts.map +1 -0
- package/dist/utils/fsExtensionScanner.js +271 -0
- package/dist/utils/fsExtensionScanner.js.map +1 -0
- package/dist/utils/fuzzyMatching.d.ts +41 -0
- package/dist/utils/fuzzyMatching.d.ts.map +1 -0
- package/dist/utils/fuzzyMatching.js +186 -0
- package/dist/utils/fuzzyMatching.js.map +1 -0
- package/dist/utils/indexStaleness.d.ts +30 -0
- package/dist/utils/indexStaleness.d.ts.map +1 -0
- package/dist/utils/indexStaleness.js +104 -0
- package/dist/utils/indexStaleness.js.map +1 -0
- package/dist/utils/loadEnv.d.ts +32 -0
- package/dist/utils/loadEnv.d.ts.map +1 -0
- package/dist/utils/loadEnv.js +83 -0
- package/dist/utils/loadEnv.js.map +1 -0
- package/dist/utils/logger.d.ts +4 -0
- package/dist/utils/logger.d.ts.map +1 -0
- package/dist/utils/logger.js +11 -0
- package/dist/utils/logger.js.map +1 -0
- package/dist/utils/metadataResolver.d.ts +155 -0
- package/dist/utils/metadataResolver.d.ts.map +1 -0
- package/dist/utils/metadataResolver.js +277 -0
- package/dist/utils/metadataResolver.js.map +1 -0
- package/dist/utils/modelClassifier.d.ts +180 -0
- package/dist/utils/modelClassifier.d.ts.map +1 -0
- package/dist/utils/modelClassifier.js +373 -0
- package/dist/utils/modelClassifier.js.map +1 -0
- package/dist/utils/operationLocks.d.ts +26 -0
- package/dist/utils/operationLocks.d.ts.map +1 -0
- package/dist/utils/operationLocks.js +182 -0
- package/dist/utils/operationLocks.js.map +1 -0
- package/dist/utils/packageResolver.d.ts +52 -0
- package/dist/utils/packageResolver.d.ts.map +1 -0
- package/dist/utils/packageResolver.js +174 -0
- package/dist/utils/packageResolver.js.map +1 -0
- package/dist/utils/pathContainment.d.ts +60 -0
- package/dist/utils/pathContainment.d.ts.map +1 -0
- package/dist/utils/pathContainment.js +270 -0
- package/dist/utils/pathContainment.js.map +1 -0
- package/dist/utils/projectUtils.d.ts +14 -0
- package/dist/utils/projectUtils.d.ts.map +1 -0
- package/dist/utils/projectUtils.js +48 -0
- package/dist/utils/projectUtils.js.map +1 -0
- package/dist/utils/provenanceStore.d.ts +54 -0
- package/dist/utils/provenanceStore.d.ts.map +1 -0
- package/dist/utils/provenanceStore.js +203 -0
- package/dist/utils/provenanceStore.js.map +1 -0
- package/dist/utils/richContext.d.ts +45 -0
- package/dist/utils/richContext.d.ts.map +1 -0
- package/dist/utils/richContext.js +316 -0
- package/dist/utils/richContext.js.map +1 -0
- package/dist/utils/smartXmlBuilder.d.ts +187 -0
- package/dist/utils/smartXmlBuilder.d.ts.map +1 -0
- package/dist/utils/smartXmlBuilder.js +504 -0
- package/dist/utils/smartXmlBuilder.js.map +1 -0
- package/dist/utils/stdioSessionInfo.d.ts +53 -0
- package/dist/utils/stdioSessionInfo.d.ts.map +1 -0
- package/dist/utils/stdioSessionInfo.js +47 -0
- package/dist/utils/stdioSessionInfo.js.map +1 -0
- package/dist/utils/suggestionEngine.d.ts +20 -0
- package/dist/utils/suggestionEngine.d.ts.map +1 -0
- package/dist/utils/suggestionEngine.js +145 -0
- package/dist/utils/suggestionEngine.js.map +1 -0
- package/dist/utils/symbolLookup.d.ts +60 -0
- package/dist/utils/symbolLookup.d.ts.map +1 -0
- package/dist/utils/symbolLookup.js +0 -0
- package/dist/utils/symbolLookup.js.map +1 -0
- package/dist/utils/terminalUi.d.ts +85 -0
- package/dist/utils/terminalUi.d.ts.map +1 -0
- package/dist/utils/terminalUi.js +182 -0
- package/dist/utils/terminalUi.js.map +1 -0
- package/dist/utils/toolMetrics.d.ts +32 -0
- package/dist/utils/toolMetrics.d.ts.map +1 -0
- package/dist/utils/toolMetrics.js +89 -0
- package/dist/utils/toolMetrics.js.map +1 -0
- package/dist/utils/toolProgressMessage.d.ts +8 -0
- package/dist/utils/toolProgressMessage.d.ts.map +1 -0
- package/dist/utils/toolProgressMessage.js +182 -0
- package/dist/utils/toolProgressMessage.js.map +1 -0
- package/dist/utils/workspaceDetector.d.ts +51 -0
- package/dist/utils/workspaceDetector.d.ts.map +1 -0
- package/dist/utils/workspaceDetector.js +328 -0
- package/dist/utils/workspaceDetector.js.map +1 -0
- package/dist/utils/xppConfigProvider.d.ts +48 -0
- package/dist/utils/xppConfigProvider.d.ts.map +1 -0
- package/dist/utils/xppConfigProvider.js +121 -0
- package/dist/utils/xppConfigProvider.js.map +1 -0
- package/dist/utils/xppDocGen.d.ts +39 -0
- package/dist/utils/xppDocGen.d.ts.map +1 -0
- package/dist/utils/xppDocGen.js +518 -0
- package/dist/utils/xppDocGen.js.map +1 -0
- package/dist/utils/xppFormat.d.ts +21 -0
- package/dist/utils/xppFormat.d.ts.map +1 -0
- package/dist/utils/xppFormat.js +102 -0
- package/dist/utils/xppFormat.js.map +1 -0
- package/dist/utils/xppSelectLint.d.ts +18 -0
- package/dist/utils/xppSelectLint.d.ts.map +1 -0
- package/dist/utils/xppSelectLint.js +80 -0
- package/dist/utils/xppSelectLint.js.map +1 -0
- package/dist/validation/formPatternValidator.d.ts +53 -0
- package/dist/validation/formPatternValidator.d.ts.map +1 -0
- package/dist/validation/formPatternValidator.js +454 -0
- package/dist/validation/formPatternValidator.js.map +1 -0
- package/dist/workspace/contextRanker.d.ts +58 -0
- package/dist/workspace/contextRanker.d.ts.map +1 -0
- package/dist/workspace/contextRanker.js +216 -0
- package/dist/workspace/contextRanker.js.map +1 -0
- package/dist/workspace/contextSnapshot.d.ts +68 -0
- package/dist/workspace/contextSnapshot.d.ts.map +1 -0
- package/dist/workspace/contextSnapshot.js +193 -0
- package/dist/workspace/contextSnapshot.js.map +1 -0
- package/dist/workspace/hybridSearch.d.ts +39 -0
- package/dist/workspace/hybridSearch.d.ts.map +1 -0
- package/dist/workspace/hybridSearch.js +96 -0
- package/dist/workspace/hybridSearch.js.map +1 -0
- package/dist/workspace/workspaceScanner.d.ts +95 -0
- package/dist/workspace/workspaceScanner.d.ts.map +1 -0
- package/dist/workspace/workspaceScanner.js +247 -0
- package/dist/workspace/workspaceScanner.js.map +1 -0
- package/dist/workspace/workspaceUtils.d.ts +23 -0
- package/dist/workspace/workspaceUtils.d.ts.map +1 -0
- package/dist/workspace/workspaceUtils.js +77 -0
- package/dist/workspace/workspaceUtils.js.map +1 -0
- package/package.json +94 -0
|
@@ -0,0 +1,996 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Generate Smart Form Tool
|
|
3
|
+
* AI-driven form generation using indexed metadata patterns
|
|
4
|
+
*/
|
|
5
|
+
import { SmartXmlBuilder } from '../utils/smartXmlBuilder.js';
|
|
6
|
+
import { FormPatternTemplates } from '../utils/formPatternTemplates.js';
|
|
7
|
+
import { handleGetFormPatterns } from './getFormPatterns.js';
|
|
8
|
+
import path from 'path';
|
|
9
|
+
import fs from 'fs';
|
|
10
|
+
import { getConfigManager } from '../utils/configManager.js';
|
|
11
|
+
import { resolveObjectPrefix, applyObjectPrefix, getObjectSuffix, applyObjectSuffix } from '../utils/modelClassifier.js';
|
|
12
|
+
import { ProjectFileManager } from './createD365File.js';
|
|
13
|
+
import { extractModelFromProject, findProjectInSolution } from '../utils/projectUtils.js';
|
|
14
|
+
import { normalizeD365Xml } from '../utils/d365XmlNormalizer.js';
|
|
15
|
+
import { validateFormPatternXml } from '../validation/formPatternValidator.js';
|
|
16
|
+
import { resolvePattern } from '../knowledge/formPatterns/index.js';
|
|
17
|
+
import { expandPatternToXml, canExpandPattern } from '../utils/formControlExpander.js';
|
|
18
|
+
import { cloneFormXml } from '../utils/formCloner.js';
|
|
19
|
+
import { methodStubsForPattern, injectMethodStubs } from '../knowledge/formPatterns/methodStubs.js';
|
|
20
|
+
import { findBaseFormXml } from './modifyD365File.js';
|
|
21
|
+
import { getFieldControlMap } from '../utils/fieldControlTypes.js';
|
|
22
|
+
import { lookupSymbolNocase } from '../utils/symbolLookup.js';
|
|
23
|
+
export const generateSmartFormTool = {
|
|
24
|
+
name: 'generate_smart_form',
|
|
25
|
+
description: 'Generate AxForm XML using D365FO pattern-aware templates. Supported patterns: SimpleList | SimpleListDetails | DetailsMaster | DetailsTransaction | Dialog | TableOfContents | Lookup | Workspace. Can copy structure from existing forms or auto-generate grid from table fields.',
|
|
26
|
+
inputSchema: {
|
|
27
|
+
type: 'object',
|
|
28
|
+
properties: {
|
|
29
|
+
name: {
|
|
30
|
+
type: 'string',
|
|
31
|
+
description: 'Form name (e.g., "MyCustomForm")',
|
|
32
|
+
},
|
|
33
|
+
label: {
|
|
34
|
+
type: 'string',
|
|
35
|
+
description: 'Optional label for the form',
|
|
36
|
+
},
|
|
37
|
+
caption: {
|
|
38
|
+
type: 'string',
|
|
39
|
+
description: 'Optional caption/title datasource',
|
|
40
|
+
},
|
|
41
|
+
dataSource: {
|
|
42
|
+
type: 'string',
|
|
43
|
+
description: 'Optional: Table name for primary datasource. Tool will auto-generate grid with fields.',
|
|
44
|
+
},
|
|
45
|
+
linesTable: {
|
|
46
|
+
type: 'string',
|
|
47
|
+
description: 'Optional: Lines table name for header+lines patterns (DetailsTransaction). ' +
|
|
48
|
+
'Creates a second datasource joined to the header (JoinSource + LinkType=Delayed), ' +
|
|
49
|
+
'populates the lines grid with typed field controls, and the field list on the datasource.',
|
|
50
|
+
},
|
|
51
|
+
linesDataSource: {
|
|
52
|
+
type: 'string',
|
|
53
|
+
description: 'Optional: explicit lines datasource name (defaults to the lines table name).',
|
|
54
|
+
},
|
|
55
|
+
formPattern: {
|
|
56
|
+
type: 'string',
|
|
57
|
+
description: 'Optional: D365FO form pattern. Valid values: SimpleList (default, for setup/config lists), SimpleListDetails (list + detail panel), DetailsMaster (full master record), DetailsTransaction (header+lines, e.g. orders), Dialog (popup dialog), TableOfContents (tabbed settings page), Lookup (dropdown lookup), Workspace (operational workspace with KPI tiles and panorama sections). Aliases like "list", "master", "transaction", "dialog", "workspace", "panorama" are also accepted.',
|
|
58
|
+
},
|
|
59
|
+
copyFrom: {
|
|
60
|
+
type: 'string',
|
|
61
|
+
description: 'Optional (legacy): Copy datasource list from an existing form. Prefer cloneFrom for full-fidelity cloning.',
|
|
62
|
+
},
|
|
63
|
+
cloneFrom: {
|
|
64
|
+
type: 'string',
|
|
65
|
+
description: 'PREFERRED strategy: clone the COMPLETE XML of an existing form (full control hierarchy, ' +
|
|
66
|
+
'patterns and sub-patterns preserved), then re-bind it via tableMapping. ' +
|
|
67
|
+
'Use a Microsoft reference form for the chosen pattern (e.g. CustGroup for SimpleList, ' +
|
|
68
|
+
'PaymTerm for SimpleListDetails, CustParameters for TableOfContents). ' +
|
|
69
|
+
'Methods except classDeclaration are stripped; fields missing on target tables are dropped (reported).',
|
|
70
|
+
},
|
|
71
|
+
tableMapping: {
|
|
72
|
+
type: 'object',
|
|
73
|
+
additionalProperties: { type: 'string' },
|
|
74
|
+
description: 'With cloneFrom: map of sourceTable → targetTable, e.g. {"CustGroup": "MyPrefixRentalGroup"}. ' +
|
|
75
|
+
'Datasources are re-bound, fields not present on the target table are dropped and reported.',
|
|
76
|
+
},
|
|
77
|
+
includeMethodStubs: {
|
|
78
|
+
type: 'boolean',
|
|
79
|
+
description: 'If true, inject pattern-appropriate lifecycle method stubs ' +
|
|
80
|
+
'(form init/executeQuery/closeOk, datasource initValue/active/validateWrite) with TODO markers.',
|
|
81
|
+
},
|
|
82
|
+
generateControls: {
|
|
83
|
+
type: 'boolean',
|
|
84
|
+
description: 'If true, auto-generate grid controls for datasource fields',
|
|
85
|
+
},
|
|
86
|
+
modelName: {
|
|
87
|
+
type: 'string',
|
|
88
|
+
description: 'Model name for file creation (auto-detected from projectPath)',
|
|
89
|
+
},
|
|
90
|
+
projectPath: {
|
|
91
|
+
type: 'string',
|
|
92
|
+
description: 'Path to .rnrproj file (used to extract correct ModelName)',
|
|
93
|
+
},
|
|
94
|
+
solutionPath: {
|
|
95
|
+
type: 'string',
|
|
96
|
+
description: 'Path to solution directory (alternative to projectPath)',
|
|
97
|
+
},
|
|
98
|
+
},
|
|
99
|
+
required: ['name'],
|
|
100
|
+
},
|
|
101
|
+
};
|
|
102
|
+
/**
|
|
103
|
+
* Default Design/Caption for a scaffolded form (pure — no DB access).
|
|
104
|
+
*
|
|
105
|
+
* Regression (eval/corpus/runs/2026-07-06T17__L1-form-listpage__cb1b73d.json,
|
|
106
|
+
* cross-referenced by L1-form-dialog and L1-form-lookup — "a systemic
|
|
107
|
+
* scaffold default, not a one-off"): when neither an explicit `caption` nor
|
|
108
|
+
* `label` argument was given, the caption defaulted to the raw object name
|
|
109
|
+
* (e.g. "PFXDemoNoteHeaderListPage") instead of reusing the bound
|
|
110
|
+
* datasource table's own Label — even though that Label is resolvable via
|
|
111
|
+
* the bridge/symbol index and is exactly the value real D365FO forms use
|
|
112
|
+
* (raw-text captions also trip BPErrorLabelIsText and cascade into
|
|
113
|
+
* BPErrorCaptionNotDefined on unlabeled ActionPane/ButtonGroups). Reusing
|
|
114
|
+
* the bound table's Label when available is both more correct and BP-clean.
|
|
115
|
+
*/
|
|
116
|
+
export function resolveFormCaption(explicitCaption, explicitLabel, tableLabel, fallbackName) {
|
|
117
|
+
return explicitCaption || explicitLabel || tableLabel || fallbackName;
|
|
118
|
+
}
|
|
119
|
+
/**
|
|
120
|
+
* Look up a table's own Label reference (e.g. "@TaxTransactionInquiry:HeaderNote")
|
|
121
|
+
* from the symbol index, for use as a scaffolded form's default caption. Returns
|
|
122
|
+
* undefined when the table is unindexed or has no Label recorded — callers fall
|
|
123
|
+
* back to `label`/the raw object name via `resolveFormCaption`.
|
|
124
|
+
*/
|
|
125
|
+
export function lookupTableLabel(symbolIndex, table) {
|
|
126
|
+
if (!table)
|
|
127
|
+
return undefined;
|
|
128
|
+
try {
|
|
129
|
+
return symbolIndex.getSymbolByName?.(table, 'table')?.signature || undefined;
|
|
130
|
+
}
|
|
131
|
+
catch {
|
|
132
|
+
return undefined;
|
|
133
|
+
}
|
|
134
|
+
}
|
|
135
|
+
/**
|
|
136
|
+
* Pre-write check for cloneFrom: cloning copies the reference form's control
|
|
137
|
+
* hierarchy and sub-patterns verbatim. If the caller asked for a different
|
|
138
|
+
* pattern than the reference declares, the result will likely violate the
|
|
139
|
+
* requested pattern (e.g. SimpleListDetails forbids a Tab the source carried)
|
|
140
|
+
* and be rejected by the form-pattern validator. Returns a warning line when the
|
|
141
|
+
* cloned form's declared <Pattern> differs from the requested pattern, or null
|
|
142
|
+
* when they match / either can't be determined.
|
|
143
|
+
*/
|
|
144
|
+
export function cloneFromPatternMismatchWarning(requestedPattern, clonedXml, sourceFormName) {
|
|
145
|
+
if (!requestedPattern)
|
|
146
|
+
return null;
|
|
147
|
+
const intended = resolvePattern(requestedPattern);
|
|
148
|
+
const clonedPattern = clonedXml.match(/<Pattern xmlns="">([^<]+)<\/Pattern>/)?.[1];
|
|
149
|
+
if (!intended || !clonedPattern)
|
|
150
|
+
return null;
|
|
151
|
+
if (intended.xmlName.toLowerCase() === clonedPattern.toLowerCase())
|
|
152
|
+
return null;
|
|
153
|
+
const ref = intended.referenceForms?.[0];
|
|
154
|
+
return (`🛑 PATTERN MISMATCH — you requested "${intended.xmlName}" but "${sourceFormName}" is a "${clonedPattern}" form. ` +
|
|
155
|
+
`Cloning copies that structure verbatim, so the result may violate "${intended.xmlName}" ` +
|
|
156
|
+
`(controls/sub-patterns the target pattern disallows) and be rejected by the form-pattern validator.` +
|
|
157
|
+
(ref
|
|
158
|
+
? ` Clone a "${intended.xmlName}" reference instead, e.g. cloneFrom="${ref}".`
|
|
159
|
+
: ` Clone a reference form that already uses "${intended.xmlName}".`));
|
|
160
|
+
}
|
|
161
|
+
/**
|
|
162
|
+
* Pre-clone table-mapping coverage check (pure — no DB/fs access).
|
|
163
|
+
*
|
|
164
|
+
* `getTableFields(table)` must return the field-name list for a table, or `null`
|
|
165
|
+
* when the table is unknown to the caller (e.g. not yet in the symbol index).
|
|
166
|
+
* Two independent failure classes, checked separately:
|
|
167
|
+
* - unknownTargets: the MAPPED target table has no known fields at all — cloning
|
|
168
|
+
* cannot verify overlap, and (per cloneFormXml's own "unknown table → keep
|
|
169
|
+
* fields" fallback) would silently leave that datasource bound to the SOURCE
|
|
170
|
+
* table's fields instead of failing. Always worth surfacing loudly.
|
|
171
|
+
* - poorOverlap: both tables are known, but share too few fields (<30%) for the
|
|
172
|
+
* clone to be structurally meaningful.
|
|
173
|
+
* Source tables with <3 known fields are skipped (too little signal either way).
|
|
174
|
+
*/
|
|
175
|
+
export function checkTableMappingCoverage(tableMapping, getTableFields) {
|
|
176
|
+
const unknownTargets = [];
|
|
177
|
+
const poorOverlap = [];
|
|
178
|
+
for (const [srcTable, tgtTable] of Object.entries(tableMapping)) {
|
|
179
|
+
if (!tgtTable || srcTable.toLowerCase() === tgtTable.toLowerCase())
|
|
180
|
+
continue;
|
|
181
|
+
const srcFields = getTableFields(srcTable);
|
|
182
|
+
const tgtFields = getTableFields(tgtTable);
|
|
183
|
+
if (!tgtFields || tgtFields.length === 0) {
|
|
184
|
+
unknownTargets.push(tgtTable);
|
|
185
|
+
continue;
|
|
186
|
+
}
|
|
187
|
+
if (!srcFields || srcFields.length < 3)
|
|
188
|
+
continue;
|
|
189
|
+
const tgtFieldSet = new Set(tgtFields.map((f) => f.toLowerCase()));
|
|
190
|
+
const shared = srcFields.filter((f) => tgtFieldSet.has(f.toLowerCase()));
|
|
191
|
+
const ratio = shared.length / srcFields.length;
|
|
192
|
+
if (ratio < 0.3) {
|
|
193
|
+
poorOverlap.push(`${srcTable} → ${tgtTable}: ${shared.length}/${srcFields.length} fields shared (${Math.round(ratio * 100)} %)`);
|
|
194
|
+
}
|
|
195
|
+
}
|
|
196
|
+
return { unknownTargets: [...new Set(unknownTargets)], poorOverlap };
|
|
197
|
+
}
|
|
198
|
+
export async function handleGenerateSmartForm(args, symbolIndex) {
|
|
199
|
+
const { name, label, caption, dataSource, linesTable, linesDataSource, formPattern, copyFrom, cloneFrom, tableMapping, includeMethodStubs, generateControls, modelName, projectPath, solutionPath, } = args;
|
|
200
|
+
console.log(`[generateSmartForm] Generating form: ${name}, dataSource=${dataSource}, pattern=${formPattern}, copyFrom=${copyFrom}, cloneFrom=${cloneFrom}`);
|
|
201
|
+
const builder = new SmartXmlBuilder(symbolIndex);
|
|
202
|
+
let dataSources = [];
|
|
203
|
+
let controls = [];
|
|
204
|
+
// Strategy 1: copy datasources from an existing form
|
|
205
|
+
if (copyFrom) {
|
|
206
|
+
console.log(`[generateSmartForm] Copying structure from: ${copyFrom}`);
|
|
207
|
+
try {
|
|
208
|
+
const db = symbolIndex.getReadDb();
|
|
209
|
+
const dbDataSources = db.prepare(`
|
|
210
|
+
SELECT datasource_name, table_name, allow_edit, allow_create, allow_delete
|
|
211
|
+
FROM form_datasources
|
|
212
|
+
WHERE form_name = ?
|
|
213
|
+
ORDER BY datasource_name
|
|
214
|
+
`).all(copyFrom);
|
|
215
|
+
if (dbDataSources.length === 0) {
|
|
216
|
+
const formExists = db.prepare(`
|
|
217
|
+
SELECT name FROM symbols WHERE type = 'form' AND name = ? LIMIT 1
|
|
218
|
+
`).get(copyFrom);
|
|
219
|
+
if (!formExists) {
|
|
220
|
+
throw new Error(`Form "${copyFrom}" not found in index`);
|
|
221
|
+
}
|
|
222
|
+
console.warn(`[generateSmartForm] Form "${copyFrom}" found but has no indexed datasources`);
|
|
223
|
+
}
|
|
224
|
+
dataSources = dbDataSources.map((ds) => ({
|
|
225
|
+
name: ds.datasource_name,
|
|
226
|
+
table: ds.table_name,
|
|
227
|
+
allowEdit: ds.allow_edit === 1,
|
|
228
|
+
allowCreate: ds.allow_create === 1,
|
|
229
|
+
allowDelete: ds.allow_delete === 1,
|
|
230
|
+
}));
|
|
231
|
+
console.log(`[generateSmartForm] Copied ${dataSources.length} datasources from ${copyFrom}`);
|
|
232
|
+
}
|
|
233
|
+
catch (error) {
|
|
234
|
+
console.error(`[generateSmartForm] Failed to copy from ${copyFrom}:`, error);
|
|
235
|
+
throw new Error(`Failed to copy structure from ${copyFrom}: ${error instanceof Error ? error.message : String(error)}`);
|
|
236
|
+
}
|
|
237
|
+
}
|
|
238
|
+
// Strategy 2: create datasource from table and analyze patterns
|
|
239
|
+
if (dataSource && !copyFrom) {
|
|
240
|
+
// Validates the table exists and fuzzy-corrects pluralisation (e.g. "...Tables" -> "...Table").
|
|
241
|
+
let dataSourceResolved = dataSource;
|
|
242
|
+
try {
|
|
243
|
+
const db = symbolIndex.getReadDb();
|
|
244
|
+
// Index-safe nocase lookup; also canonicalizes the casing so the field
|
|
245
|
+
// probes below stay BINARY on idx_parent_type_name.
|
|
246
|
+
const directHit = lookupSymbolNocase(db, dataSource, ['table']);
|
|
247
|
+
if (directHit) {
|
|
248
|
+
dataSourceResolved = directHit.name;
|
|
249
|
+
}
|
|
250
|
+
else {
|
|
251
|
+
const add = (n) => {
|
|
252
|
+
const v = (n ?? '').trim();
|
|
253
|
+
if (v && !candidates.some((c) => c.toLowerCase() === v.toLowerCase()))
|
|
254
|
+
candidates.push(v);
|
|
255
|
+
};
|
|
256
|
+
const candidates = [];
|
|
257
|
+
add(dataSource.replace(/s$/i, ''));
|
|
258
|
+
add(dataSource.replace(/Tables?$/i, 'Table'));
|
|
259
|
+
add(dataSource.replace(/Table$/i, ''));
|
|
260
|
+
const matched = candidates
|
|
261
|
+
.map(c => lookupSymbolNocase(db, c, ['table']))
|
|
262
|
+
.find(r => r)?.name;
|
|
263
|
+
if (matched) {
|
|
264
|
+
console.log(`[generateSmartForm] dataSource "${dataSource}" → "${matched}" (auto-corrected)`);
|
|
265
|
+
dataSourceResolved = matched;
|
|
266
|
+
}
|
|
267
|
+
else {
|
|
268
|
+
const alt = db.prepare(`SELECT name FROM symbols WHERE type = 'table' AND name LIKE ? COLLATE NOCASE ORDER BY LENGTH(name) ASC LIMIT 1`).get(`${dataSource.replace(/s$/i, '')}%`);
|
|
269
|
+
const suggestion = alt ? `\n\nDid you mean \`dataSource="${alt.name}"\`?` : '';
|
|
270
|
+
return {
|
|
271
|
+
content: [{
|
|
272
|
+
type: 'text',
|
|
273
|
+
text: `❌ Table "${dataSource}" not found in the symbol index.${suggestion}\n\nIf the table was just created in this session, call \`update_symbol_index\` first, then retry.`,
|
|
274
|
+
}],
|
|
275
|
+
};
|
|
276
|
+
}
|
|
277
|
+
}
|
|
278
|
+
}
|
|
279
|
+
catch {
|
|
280
|
+
/* index unavailable — proceed with provided name */
|
|
281
|
+
}
|
|
282
|
+
console.log(`[generateSmartForm] Creating datasource for table: ${dataSourceResolved}`);
|
|
283
|
+
dataSources.push({
|
|
284
|
+
name: dataSourceResolved,
|
|
285
|
+
table: dataSourceResolved,
|
|
286
|
+
allowEdit: true,
|
|
287
|
+
allowCreate: true,
|
|
288
|
+
allowDelete: true,
|
|
289
|
+
});
|
|
290
|
+
if (formPattern) {
|
|
291
|
+
try {
|
|
292
|
+
await handleGetFormPatterns({ formPattern }, symbolIndex);
|
|
293
|
+
console.log(`[generateSmartForm] Analyzed pattern: ${formPattern}`);
|
|
294
|
+
}
|
|
295
|
+
catch (error) {
|
|
296
|
+
console.warn(`[generateSmartForm] Pattern analysis failed:`, error);
|
|
297
|
+
}
|
|
298
|
+
}
|
|
299
|
+
}
|
|
300
|
+
// Strategy 3: generate controls for datasource fields (also collects gridFields
|
|
301
|
+
// for pattern templates regardless of the generateControls flag)
|
|
302
|
+
let gridFields = [];
|
|
303
|
+
// Field -> control-type map (enum->ComboBox, date->Date, etc.) so generated controls
|
|
304
|
+
// aren't all typed as String.
|
|
305
|
+
let fieldTypes;
|
|
306
|
+
let linesFields = [];
|
|
307
|
+
let linesFieldTypes;
|
|
308
|
+
// Table fields minus system fields, capped for a sensible grid width.
|
|
309
|
+
const collectGridFields = (db, table) => {
|
|
310
|
+
// Canonicalize first — `parent_name = ? COLLATE NOCASE` cannot use
|
|
311
|
+
// idx_parent_type_name and scans all 360k field rows (180 s cold).
|
|
312
|
+
const canonical = lookupSymbolNocase(db, table)?.name ?? table;
|
|
313
|
+
const dbFields = db.prepare(`
|
|
314
|
+
SELECT name FROM symbols
|
|
315
|
+
WHERE type = 'field' AND parent_name = ?
|
|
316
|
+
ORDER BY name
|
|
317
|
+
`).all(canonical);
|
|
318
|
+
return dbFields
|
|
319
|
+
.map((f) => f.name)
|
|
320
|
+
.filter((n) => !['RecId', 'RecVersion', 'DataAreaId', 'Partition'].includes(n))
|
|
321
|
+
.slice(0, 8);
|
|
322
|
+
};
|
|
323
|
+
// May differ from the input after fuzzy resolution above.
|
|
324
|
+
const dataSourceEffective = dataSources[0]?.table ?? dataSource;
|
|
325
|
+
if (dataSource && dataSources.length > 0) {
|
|
326
|
+
try {
|
|
327
|
+
const db = symbolIndex.getReadDb();
|
|
328
|
+
gridFields = collectGridFields(db, dataSourceEffective);
|
|
329
|
+
fieldTypes = getFieldControlMap(db, dataSourceEffective);
|
|
330
|
+
if (gridFields.length > 0) {
|
|
331
|
+
if (generateControls) {
|
|
332
|
+
const gridControl = builder.buildGridControl(`${dataSourceEffective}Grid`, dataSourceEffective, gridFields, fieldTypes);
|
|
333
|
+
controls.push(gridControl);
|
|
334
|
+
console.log(`[generateSmartForm] Generated grid with ${gridFields.length} fields`);
|
|
335
|
+
}
|
|
336
|
+
else {
|
|
337
|
+
console.log(`[generateSmartForm] Collected ${gridFields.length} grid fields for pattern template`);
|
|
338
|
+
}
|
|
339
|
+
}
|
|
340
|
+
}
|
|
341
|
+
catch (error) {
|
|
342
|
+
console.warn(`[generateSmartForm] Failed to generate controls:`, error);
|
|
343
|
+
}
|
|
344
|
+
}
|
|
345
|
+
// Lines datasource (header+lines patterns): add a second datasource bound to
|
|
346
|
+
// the lines table, with its own typed field controls and field list.
|
|
347
|
+
let linesTableResolved = linesTable || linesDataSource;
|
|
348
|
+
// Effective lines datasource name; may differ from the corrected table name when an
|
|
349
|
+
// explicit, distinct linesDataSource is supplied. Hoisted so method-stub injection
|
|
350
|
+
// below references the same name as the datasource actually emitted.
|
|
351
|
+
let linesDsNameResolved;
|
|
352
|
+
// Note about an auto-corrected lines table name, surfaced via cloneNotes.
|
|
353
|
+
let linesTableNote = '';
|
|
354
|
+
if (linesTableResolved) {
|
|
355
|
+
// Lines table names are commonly guessed wrong (e.g. header "...Table" -> "...TableLines"
|
|
356
|
+
// instead of the real "...Line"). Try structured candidates from the given name and the
|
|
357
|
+
// header table, auto-correct to the first that exists, hard-fail only if none resolve.
|
|
358
|
+
try {
|
|
359
|
+
const db = symbolIndex.getReadDb();
|
|
360
|
+
const exists = (n) => lookupSymbolNocase(db, n, ['table']);
|
|
361
|
+
const direct = exists(linesTableResolved);
|
|
362
|
+
if (direct) {
|
|
363
|
+
linesTableResolved = direct.name; // canonical casing for BINARY field probes
|
|
364
|
+
}
|
|
365
|
+
else {
|
|
366
|
+
const candidates = [];
|
|
367
|
+
const add = (n) => {
|
|
368
|
+
const v = (n ?? '').trim();
|
|
369
|
+
if (v && !candidates.some(c => c.toLowerCase() === v.toLowerCase()))
|
|
370
|
+
candidates.push(v);
|
|
371
|
+
};
|
|
372
|
+
const ln = linesTableResolved;
|
|
373
|
+
add(ln.replace(/s$/i, ''));
|
|
374
|
+
add(ln.replace(/Lines$/i, 'Line'));
|
|
375
|
+
add(ln.replace(/Table(Lines?)$/i, 'Line'));
|
|
376
|
+
add(ln.replace(/Table(Lines?)$/i, '$1'));
|
|
377
|
+
if (dataSource) {
|
|
378
|
+
const base = dataSource.replace(/Table$/i, ''); // header base, e.g. ContosoRentAgreement
|
|
379
|
+
add(`${base}Line`);
|
|
380
|
+
add(`${base}Lines`);
|
|
381
|
+
add(`${base}TransLine`);
|
|
382
|
+
add(`${base}Trans`);
|
|
383
|
+
}
|
|
384
|
+
let matched;
|
|
385
|
+
for (const cand of candidates) {
|
|
386
|
+
const hit = exists(cand);
|
|
387
|
+
if (hit) {
|
|
388
|
+
matched = hit.name;
|
|
389
|
+
break;
|
|
390
|
+
}
|
|
391
|
+
}
|
|
392
|
+
if (matched) {
|
|
393
|
+
linesTableNote =
|
|
394
|
+
`\n 🔍 linesTable "${linesTableResolved}" not found — auto-corrected to "${matched}" (verified in the index).`;
|
|
395
|
+
console.log(`[generateSmartForm] linesTable "${linesTableResolved}" → "${matched}" (auto-corrected)`);
|
|
396
|
+
linesTableResolved = matched;
|
|
397
|
+
}
|
|
398
|
+
else {
|
|
399
|
+
const stem = linesTableResolved.replace(/s$/i, '');
|
|
400
|
+
const alt = db.prepare(`SELECT name FROM symbols WHERE type = 'table' AND name LIKE ? COLLATE NOCASE ORDER BY LENGTH(name) ASC LIMIT 1`).get(`${stem}%`);
|
|
401
|
+
const suggestion = alt && alt.name.toLowerCase() !== linesTableResolved.toLowerCase()
|
|
402
|
+
? `\n\nDid you mean \`linesTable="${alt.name}"\`?`
|
|
403
|
+
: '';
|
|
404
|
+
return {
|
|
405
|
+
content: [{
|
|
406
|
+
type: 'text',
|
|
407
|
+
text: `❌ Lines table "${linesTableResolved}" not found in the symbol index.` +
|
|
408
|
+
suggestion +
|
|
409
|
+
`\n\nIf the table was just created in this session, call \`update_symbol_index\` first, then retry.`,
|
|
410
|
+
}],
|
|
411
|
+
isError: true,
|
|
412
|
+
};
|
|
413
|
+
}
|
|
414
|
+
}
|
|
415
|
+
}
|
|
416
|
+
catch {
|
|
417
|
+
/* index unavailable — skip validation and proceed */
|
|
418
|
+
}
|
|
419
|
+
// Datasource name: by D365FO convention it equals the (corrected) table name.
|
|
420
|
+
// Honor an explicit linesDataSource ONLY when it is a genuinely distinct name —
|
|
421
|
+
// not just the wrong pluralized guess (e.g. "ContosoRentAgreementLines") that the
|
|
422
|
+
// table auto-correction above already resolved to "ContosoRentAgreementLine".
|
|
423
|
+
// Otherwise the form ends up with a datasource named after a non-existent table.
|
|
424
|
+
// Local const captures the (possibly auto-corrected) table name so TS keeps the
|
|
425
|
+
// non-undefined narrowing through the reassignments above.
|
|
426
|
+
const linesTbl = linesTableResolved;
|
|
427
|
+
const explicitDsIsStalePlural = !!linesDataSource &&
|
|
428
|
+
linesDataSource.toLowerCase() !== linesTbl.toLowerCase() &&
|
|
429
|
+
(linesDataSource.replace(/s$/i, '').toLowerCase() === linesTbl.toLowerCase() ||
|
|
430
|
+
linesDataSource.toLowerCase() === `${linesTbl.toLowerCase()}s`);
|
|
431
|
+
const dsName = linesDataSource && !explicitDsIsStalePlural ? linesDataSource : linesTbl;
|
|
432
|
+
linesDsNameResolved = dsName;
|
|
433
|
+
// Guard against a duplicate datasource: skip when one already targets the same
|
|
434
|
+
// table or already uses the same name (prevents the stale "…Lines" + correct
|
|
435
|
+
// "…Line" double-datasource the form scaffolder previously produced).
|
|
436
|
+
const isDuplicateDs = dataSources.some(ds => ds.table.toLowerCase() === linesTbl.toLowerCase() ||
|
|
437
|
+
ds.name.toLowerCase() === dsName.toLowerCase());
|
|
438
|
+
if (!isDuplicateDs) {
|
|
439
|
+
dataSources.push({
|
|
440
|
+
name: dsName,
|
|
441
|
+
table: linesTbl,
|
|
442
|
+
allowEdit: true,
|
|
443
|
+
allowCreate: true,
|
|
444
|
+
allowDelete: true,
|
|
445
|
+
});
|
|
446
|
+
}
|
|
447
|
+
else {
|
|
448
|
+
console.log(`[generateSmartForm] Skipped duplicate lines datasource for table "${linesTbl}"`);
|
|
449
|
+
}
|
|
450
|
+
try {
|
|
451
|
+
const db = symbolIndex.getReadDb();
|
|
452
|
+
linesFields = collectGridFields(db, linesTableResolved);
|
|
453
|
+
linesFieldTypes = getFieldControlMap(db, linesTableResolved);
|
|
454
|
+
console.log(`[generateSmartForm] Lines datasource ${linesDsNameResolved} with ${linesFields.length} fields`);
|
|
455
|
+
}
|
|
456
|
+
catch (error) {
|
|
457
|
+
console.warn(`[generateSmartForm] Failed to collect lines fields:`, error);
|
|
458
|
+
}
|
|
459
|
+
}
|
|
460
|
+
// Fallback: At least one datasource needed
|
|
461
|
+
if (dataSources.length === 0) {
|
|
462
|
+
console.warn(`[generateSmartForm] No datasource configured, form will be empty`);
|
|
463
|
+
}
|
|
464
|
+
// Determine package path — prefer the bridge's custom packages root (where bridge-backed
|
|
465
|
+
// writes actually land) so the reported/fallback path matches the real write location.
|
|
466
|
+
const configManager = getConfigManager();
|
|
467
|
+
const customPackagesRoot = await configManager.getCustomPackagesPath();
|
|
468
|
+
const packagePath = customPackagesRoot || configManager.getPackagePath() || 'K:\\AosService\\PackagesLocalDirectory';
|
|
469
|
+
// Resolve project/solution path — fall back to configManager (from .mcp.json / auto-detection)
|
|
470
|
+
let resolvedProjectPath = projectPath;
|
|
471
|
+
let resolvedSolutionPath = solutionPath;
|
|
472
|
+
if (!resolvedProjectPath && !resolvedSolutionPath) {
|
|
473
|
+
resolvedProjectPath = (await configManager.getProjectPath()) || undefined;
|
|
474
|
+
resolvedSolutionPath = (await configManager.getSolutionPath()) || undefined;
|
|
475
|
+
if (resolvedProjectPath) {
|
|
476
|
+
console.log(`[generateSmartForm] Using projectPath from config/auto-detect: ${resolvedProjectPath}`);
|
|
477
|
+
}
|
|
478
|
+
else if (resolvedSolutionPath) {
|
|
479
|
+
console.log(`[generateSmartForm] Using solutionPath from config/auto-detect: ${resolvedSolutionPath}`);
|
|
480
|
+
}
|
|
481
|
+
}
|
|
482
|
+
// Resolve actual model name — always prefer extracting from .rnrproj over using modelName arg
|
|
483
|
+
let resolvedModel = modelName;
|
|
484
|
+
if (resolvedProjectPath) {
|
|
485
|
+
const extracted = extractModelFromProject(resolvedProjectPath);
|
|
486
|
+
if (extracted) {
|
|
487
|
+
resolvedModel = extracted;
|
|
488
|
+
console.log(`[generateSmartForm] Extracted model from .rnrproj: ${resolvedModel}`);
|
|
489
|
+
}
|
|
490
|
+
}
|
|
491
|
+
else if (resolvedSolutionPath) {
|
|
492
|
+
const project = findProjectInSolution(resolvedSolutionPath);
|
|
493
|
+
if (project) {
|
|
494
|
+
const extracted = extractModelFromProject(project);
|
|
495
|
+
if (extracted) {
|
|
496
|
+
resolvedModel = extracted;
|
|
497
|
+
console.log(`[generateSmartForm] Extracted model from solution .rnrproj: ${resolvedModel}`);
|
|
498
|
+
}
|
|
499
|
+
}
|
|
500
|
+
}
|
|
501
|
+
const isNonWindows = process.platform !== 'win32';
|
|
502
|
+
if (!resolvedModel) {
|
|
503
|
+
// .rnrproj extraction failed (or wasn't attempted) — fall back in this order on ALL platforms:
|
|
504
|
+
// 1. .mcp.json context (modelName field or last segment of workspacePath)
|
|
505
|
+
// 2. Auto-detected model name (async) — e.g. from PackagesLocalDirectory regex / well-known paths
|
|
506
|
+
// 3. D365FO_MODEL_NAME env var
|
|
507
|
+
// 4. modelName arg — LAST because the AI often passes a placeholder like "any" or "whatever"
|
|
508
|
+
const configModel = configManager.getModelName();
|
|
509
|
+
const autoModel = configModel ? null : (await configManager.getAutoDetectedModelName());
|
|
510
|
+
resolvedModel = configModel || autoModel || process.env.D365FO_MODEL_NAME || modelName || undefined;
|
|
511
|
+
if (resolvedModel) {
|
|
512
|
+
const ctx = configManager.getContext();
|
|
513
|
+
const source = configModel === resolvedModel
|
|
514
|
+
? (ctx?.modelName ? 'modelName (mcp.json)' : 'workspacePath (mcp.json)')
|
|
515
|
+
: autoModel === resolvedModel ? 'auto-detected (well-known paths)'
|
|
516
|
+
: process.env.D365FO_MODEL_NAME === resolvedModel ? 'D365FO_MODEL_NAME env var'
|
|
517
|
+
: 'modelName arg (fallback)';
|
|
518
|
+
console.log(`[generateSmartForm] Using model from ${source}: ${resolvedModel}`);
|
|
519
|
+
}
|
|
520
|
+
else if (!isNonWindows) {
|
|
521
|
+
// Windows VM: all sources exhausted — tell the user exactly what to configure.
|
|
522
|
+
throw new Error('Could not resolve model name. Provide modelName, projectPath, or solutionPath, ' +
|
|
523
|
+
'or configure projectPath/solutionPath in .mcp.json or set D365FO_MODEL_NAME env var.');
|
|
524
|
+
}
|
|
525
|
+
// Non-Windows: if still null, continue without a prefix.
|
|
526
|
+
}
|
|
527
|
+
console.log(`[generateSmartForm] Using model: ${resolvedModel ?? '(none — no prefix)'}`);
|
|
528
|
+
// Apply extension prefix to form name (skip when model unknown)
|
|
529
|
+
const objectPrefix = resolvedModel ? resolveObjectPrefix(resolvedModel) : '';
|
|
530
|
+
let finalName = objectPrefix ? applyObjectPrefix(name, objectPrefix) : name;
|
|
531
|
+
const objectSuffix = getObjectSuffix();
|
|
532
|
+
finalName = applyObjectSuffix(finalName, objectSuffix);
|
|
533
|
+
if (finalName !== name) {
|
|
534
|
+
console.log(`[generateSmartForm] Applied naming: ${name} → ${finalName}`);
|
|
535
|
+
}
|
|
536
|
+
// Generate XML: clone an existing form (preferred) or build from a template.
|
|
537
|
+
// Without an explicit pattern, default to the majority pattern mined from
|
|
538
|
+
// standard models (property_stats), falling back to SimpleList.
|
|
539
|
+
const normalizedPattern = formPattern
|
|
540
|
+
? FormPatternTemplates.normalizePattern(formPattern)
|
|
541
|
+
: builder.defaultFormPattern();
|
|
542
|
+
const primaryDs = dataSources[0];
|
|
543
|
+
let xml;
|
|
544
|
+
let cloneNotes = linesTableNote;
|
|
545
|
+
if (cloneFrom) {
|
|
546
|
+
const sourceXml = await findBaseFormXml(cloneFrom, symbolIndex);
|
|
547
|
+
if (!sourceXml) {
|
|
548
|
+
return {
|
|
549
|
+
content: [{
|
|
550
|
+
type: 'text',
|
|
551
|
+
text: `❌ cloneFrom: form "${cloneFrom}" could not be read from the metadata store.\n\n` +
|
|
552
|
+
`Options:\n` +
|
|
553
|
+
` 1. Check the form name with search("${cloneFrom}", type="form").\n` +
|
|
554
|
+
` 2. Rebuild/update the symbol index if the form is new.\n` +
|
|
555
|
+
` 3. Fall back to a template: generate_object(mode="scaffold", objectType="form", name="${name}", formPattern="...", dataSource="...").`,
|
|
556
|
+
}],
|
|
557
|
+
isError: true,
|
|
558
|
+
};
|
|
559
|
+
}
|
|
560
|
+
const db = symbolIndex.getReadDb();
|
|
561
|
+
// BINARY parent probe on idx_parent_type_name; mapping targets are
|
|
562
|
+
// canonicalized in the callback below (NOCASE here scanned all field rows).
|
|
563
|
+
const fieldStmt = db.prepare(`
|
|
564
|
+
SELECT name FROM symbols WHERE type = 'field' AND parent_name = ?
|
|
565
|
+
`);
|
|
566
|
+
// ── PRE-CLONE FIELD-OVERLAP CHECK ──────────────────────────────────────
|
|
567
|
+
// Before cloning, verify the source and target tables are structurally
|
|
568
|
+
// related (≥ 30 % shared fields per mapped pair). If the overlap is too
|
|
569
|
+
// low, cloning will strip most controls and produce a useless form.
|
|
570
|
+
// Fail-fast here rather than returning a gutted result.
|
|
571
|
+
if (tableMapping && Object.keys(tableMapping).length > 0) {
|
|
572
|
+
// Found live 2026-07-01 (usage-examples eval, scenario 2): cloneFrom="CustGroup"
|
|
573
|
+
// + tableMapping to a just-created table not yet in the symbol index silently
|
|
574
|
+
// produced a form with 0 datasources/controls, self-reported as success —
|
|
575
|
+
// getTableFields returning null/empty for an unknown table used to make
|
|
576
|
+
// cloneFormXml leave that datasource's fields untouched (still bound to the
|
|
577
|
+
// SOURCE table) instead of failing. checkTableMappingCoverage now catches this
|
|
578
|
+
// as `unknownTargets`, separate from the pre-existing `poorOverlap` check.
|
|
579
|
+
const { unknownTargets, poorOverlap } = checkTableMappingCoverage(tableMapping, (table) => {
|
|
580
|
+
const canonical = lookupSymbolNocase(db, table)?.name ?? table;
|
|
581
|
+
const rows = fieldStmt.all(canonical);
|
|
582
|
+
return rows.length > 0 ? rows.map((r) => r.name) : null;
|
|
583
|
+
});
|
|
584
|
+
if (unknownTargets.length > 0) {
|
|
585
|
+
return {
|
|
586
|
+
content: [{
|
|
587
|
+
type: 'text',
|
|
588
|
+
text: `❌ PRE-CLONE CHECK — target table${unknownTargets.length > 1 ? 's' : ''} not found in the symbol index: ` +
|
|
589
|
+
`${unknownTargets.join(', ')}.\n\n` +
|
|
590
|
+
`Cloning cannot verify field overlap against an unindexed table, and the clone would silently keep ` +
|
|
591
|
+
`"${cloneFrom}"'s OWN fields unmapped instead of failing — producing a form that looks bound to your ` +
|
|
592
|
+
`table but whose datasource/controls still reference the source table's fields.\n\n` +
|
|
593
|
+
`**Fix — choose one:**\n` +
|
|
594
|
+
`1. If ${unknownTargets.join(', ')} was just created this session, index it first, then retry:\n` +
|
|
595
|
+
` \`update_symbol_index(filePath="<absolute path to ${unknownTargets[0]}.xml>")\`\n` +
|
|
596
|
+
`2. Check the table name for a typo with \`search("${unknownTargets[0]}", type="table")\`.`,
|
|
597
|
+
}],
|
|
598
|
+
isError: true,
|
|
599
|
+
};
|
|
600
|
+
}
|
|
601
|
+
if (poorOverlap.length > 0) {
|
|
602
|
+
const targetList = Object.values(tableMapping).filter(Boolean).join(', ');
|
|
603
|
+
return {
|
|
604
|
+
content: [{
|
|
605
|
+
type: 'text',
|
|
606
|
+
text: `❌ PRE-CLONE CHECK — Poor field overlap between source and target tables:\n` +
|
|
607
|
+
poorOverlap.map((s) => ` • ${s}`).join('\n') +
|
|
608
|
+
`\n\nCloning "${cloneFrom}" would strip most of its controls ` +
|
|
609
|
+
`(source and target tables are structurally unrelated).\n\n` +
|
|
610
|
+
`**✅ Recommended fix — scaffold from a pattern template (fast, no cloning needed):**\n` +
|
|
611
|
+
`\`\`\`\ngenerate_object(mode="scaffold", objectType="form",\n name="${name}",\n formPattern="${formPattern ?? 'SimpleList'}",\n dataSource="${targetList}"\n)\n\`\`\`\n\n` +
|
|
612
|
+
`**Alternative — find a structurally similar reference form first:**\n` +
|
|
613
|
+
`\`object_patterns(domain="form", action="analyze", recommend={ "dataSource": "${targetList}", "pattern": "${formPattern ?? 'auto'}" })\`\n` +
|
|
614
|
+
`Then re-run with the suggested \`cloneFrom\` value.`,
|
|
615
|
+
}],
|
|
616
|
+
isError: true,
|
|
617
|
+
};
|
|
618
|
+
}
|
|
619
|
+
}
|
|
620
|
+
// ── end pre-clone field-overlap check ─────────────────────────────────
|
|
621
|
+
const cloneResult = cloneFormXml(sourceXml, {
|
|
622
|
+
targetFormName: finalName,
|
|
623
|
+
tableMapping,
|
|
624
|
+
caption: caption || label,
|
|
625
|
+
getTableFields: (table) => {
|
|
626
|
+
const rows = fieldStmt.all(table);
|
|
627
|
+
return rows.length > 0 ? rows.map((r) => r.name) : null; // unknown table → keep fields
|
|
628
|
+
},
|
|
629
|
+
});
|
|
630
|
+
xml = cloneResult.xml;
|
|
631
|
+
const noteLines = [` Cloned from: ${cloneResult.sourceFormName}`];
|
|
632
|
+
if (cloneResult.renamedDataSources.length > 0) {
|
|
633
|
+
noteLines.push(` Datasources re-bound: ${cloneResult.renamedDataSources.map(r => `${r.from}→${r.to}`).join(', ')}`);
|
|
634
|
+
}
|
|
635
|
+
if (cloneResult.strippedMethods.length > 0) {
|
|
636
|
+
noteLines.push(` Methods stripped (re-add what you need via d365fo_file(action="modify") add-method): ${cloneResult.strippedMethods.join(', ')}`);
|
|
637
|
+
}
|
|
638
|
+
if (cloneResult.clearedSourceCodeMirror) {
|
|
639
|
+
noteLines.push(` SourceCode datasource/control method mirror cleared (stale field/control method holders)`);
|
|
640
|
+
}
|
|
641
|
+
if (cloneResult.resetClassDeclaration) {
|
|
642
|
+
noteLines.push(` classDeclaration body reset to empty (source member vars/macros dropped with the methods)`);
|
|
643
|
+
}
|
|
644
|
+
if (cloneResult.removedIndexes.length > 0) {
|
|
645
|
+
noteLines.push(` Default datasource index dropped (source-table index): ${cloneResult.removedIndexes.map(i => `${i.dataSource}.${i.index}`).join(', ')}`);
|
|
646
|
+
}
|
|
647
|
+
if (cloneResult.droppedFields.length > 0) {
|
|
648
|
+
noteLines.push(` ⚠️ Fields dropped (missing on target table): ${cloneResult.droppedFields.map(d => `${d.dataSource}.${d.field}`).join(', ')}`);
|
|
649
|
+
}
|
|
650
|
+
// Poor-match guard: if a re-bound datasource lost most of its fields, the
|
|
651
|
+
// reference form's table is structurally unrelated to the target — the clone
|
|
652
|
+
// is likely unusable. Return an error immediately so the caller is forced to
|
|
653
|
+
// pick a structurally similar reference form or scaffold from a template.
|
|
654
|
+
// (Previously this only emitted a warning note and still returned the gutted
|
|
655
|
+
// XML, which the model then tried to use — always resulting in manual rewrite.)
|
|
656
|
+
const poorMatches = cloneResult.fieldStats.filter(s => s.total >= 3 && s.dropped / s.total >= 0.6);
|
|
657
|
+
if (poorMatches.length > 0) {
|
|
658
|
+
const matchSummary = poorMatches.map(s => `${s.dataSource}: ${s.dropped}/${s.total} fields dropped`).join('; ');
|
|
659
|
+
const tableList = Object.values(tableMapping ?? {}).filter(Boolean).join(', ') || 'your target table';
|
|
660
|
+
return {
|
|
661
|
+
content: [{
|
|
662
|
+
type: 'text',
|
|
663
|
+
text: `❌ POOR CLONE MATCH — ${matchSummary}.\n\n` +
|
|
664
|
+
`"${cloneResult.sourceFormName}" is bound to a table structurally unrelated to ${tableList}, ` +
|
|
665
|
+
`so cloning would strip ${poorMatches.reduce((a, s) => a + s.dropped, 0)} of ${poorMatches.reduce((a, s) => a + s.total, 0)} controls and produce an unusable form.\n\n` +
|
|
666
|
+
`**Fix — choose one:**\n` +
|
|
667
|
+
`1. Find a structurally similar reference form first:\n` +
|
|
668
|
+
` \`object_patterns(domain="form", action="analyze", recommend={ "dataSource": "${tableList}", "pattern": "${formPattern ?? 'auto'}" })\`\n` +
|
|
669
|
+
` Then re-run with the suggested \`cloneFrom\` value.\n\n` +
|
|
670
|
+
`2. Scaffold from a pattern template (no cloning needed):\n` +
|
|
671
|
+
` \`generate_object(mode="scaffold", objectType="form", name="${name}", formPattern="${formPattern ?? 'SimpleList'}", dataSource="${tableList}")\``,
|
|
672
|
+
}],
|
|
673
|
+
isError: true,
|
|
674
|
+
};
|
|
675
|
+
}
|
|
676
|
+
if (cloneResult.removedControls.length > 0) {
|
|
677
|
+
noteLines.push(` ⚠️ Controls removed (bound to dropped fields): ${cloneResult.removedControls.join(', ')}`);
|
|
678
|
+
}
|
|
679
|
+
for (const rq of cloneResult.repointedQuickFilters) {
|
|
680
|
+
noteLines.push(rq.to
|
|
681
|
+
? ` QuickFilter default column repointed: ${rq.from} → ${rq.to}`
|
|
682
|
+
: ` ⚠️ QuickFilter default column "${rq.from}" was removed and no surviving column was found — set defaultColumnName manually`);
|
|
683
|
+
}
|
|
684
|
+
// Pattern-compatibility pre-check (see cloneFromPatternMismatchWarning).
|
|
685
|
+
const mismatch = cloneFromPatternMismatchWarning(formPattern, xml, cloneResult.sourceFormName);
|
|
686
|
+
if (mismatch)
|
|
687
|
+
noteLines.push(` ${mismatch}`);
|
|
688
|
+
cloneNotes = `\n${noteLines.join('\n')}`;
|
|
689
|
+
}
|
|
690
|
+
else {
|
|
691
|
+
const templateOpts = {
|
|
692
|
+
formName: finalName,
|
|
693
|
+
dsName: primaryDs?.name,
|
|
694
|
+
dsTable: primaryDs?.table,
|
|
695
|
+
caption: resolveFormCaption(caption, label, lookupTableLabel(symbolIndex, primaryDs?.table), finalName),
|
|
696
|
+
gridFields,
|
|
697
|
+
fieldTypes,
|
|
698
|
+
linesDsName: linesDsNameResolved ?? (linesTableResolved || undefined),
|
|
699
|
+
linesDsTable: linesTableResolved || undefined,
|
|
700
|
+
linesFields,
|
|
701
|
+
linesFieldTypes,
|
|
702
|
+
};
|
|
703
|
+
// Patterns FormPatternTemplates has a dedicated, hand-tuned builder for.
|
|
704
|
+
// Anything else previously degraded silently to SimpleList; we now expand it
|
|
705
|
+
// deterministically from the catalog instead (single source of truth).
|
|
706
|
+
const TEMPLATED_PATTERNS = new Set([
|
|
707
|
+
'SimpleList', 'SimpleListDetails', 'DetailsMaster', 'DetailsTransaction',
|
|
708
|
+
'Dialog', 'TableOfContents', 'Lookup', 'ListPage', 'Workspace',
|
|
709
|
+
]);
|
|
710
|
+
const intendedSpec = formPattern ? resolvePattern(formPattern) : undefined;
|
|
711
|
+
let expanded;
|
|
712
|
+
if (intendedSpec && !TEMPLATED_PATTERNS.has(intendedSpec.xmlName) && canExpandPattern(intendedSpec)) {
|
|
713
|
+
// Deterministic catalog expansion. Self-test it: only adopt the result when
|
|
714
|
+
// it is structurally error-free — otherwise fall through to the proven
|
|
715
|
+
// template path so we can never regress.
|
|
716
|
+
const candidate = expandPatternToXml(intendedSpec, templateOpts);
|
|
717
|
+
const candidateReport = await validateFormPatternXml(candidate);
|
|
718
|
+
if (!candidateReport.violations.some(v => v.severity === 'error')) {
|
|
719
|
+
expanded = candidate;
|
|
720
|
+
cloneNotes += `\n ✅ Generated deterministically from the form-pattern catalog (pattern "${intendedSpec.xmlName}", no clone needed).`;
|
|
721
|
+
}
|
|
722
|
+
else {
|
|
723
|
+
console.warn(`[generateSmartForm] Expander output for "${intendedSpec.xmlName}" failed self-test — falling back to template.`);
|
|
724
|
+
}
|
|
725
|
+
}
|
|
726
|
+
if (expanded) {
|
|
727
|
+
xml = expanded;
|
|
728
|
+
}
|
|
729
|
+
else {
|
|
730
|
+
xml = FormPatternTemplates.build(normalizedPattern, templateOpts);
|
|
731
|
+
// Warn when the requested pattern has no dedicated template and silently
|
|
732
|
+
// degraded to another base (or to SimpleList). The emitted <Pattern> reflects
|
|
733
|
+
// the template, not the request, and the self-test validates only the emitted
|
|
734
|
+
// pattern — so this mismatch would otherwise pass unnoticed.
|
|
735
|
+
const degradedPattern = xml.match(/<Pattern xmlns="">([^<]+)<\/Pattern>/)?.[1];
|
|
736
|
+
if (formPattern && degradedPattern) {
|
|
737
|
+
const intended = resolvePattern(formPattern);
|
|
738
|
+
if (intended && intended.xmlName.toLowerCase() !== degradedPattern.toLowerCase()) {
|
|
739
|
+
const ref = intended.referenceForms?.[0];
|
|
740
|
+
cloneNotes +=
|
|
741
|
+
`\n ⚠️ No dedicated template for pattern "${intended.xmlName}" — generated a "${degradedPattern}" form instead.` +
|
|
742
|
+
(ref
|
|
743
|
+
? ` For a true "${intended.xmlName}", clone a reference form: ` +
|
|
744
|
+
`generate_object(mode="scaffold", objectType="form", name="${name}", cloneFrom="${ref}", tableMapping={...}).`
|
|
745
|
+
: ` Clone a reference form for that pattern via cloneFrom=.`);
|
|
746
|
+
}
|
|
747
|
+
}
|
|
748
|
+
}
|
|
749
|
+
// Align the Design-level PatternVersion with the version this environment uses
|
|
750
|
+
// for the pattern; template defaults can lag and be rejected by BP.
|
|
751
|
+
const designPattern = xml.match(/<Pattern xmlns="">([^<]+)<\/Pattern>/)?.[1];
|
|
752
|
+
if (designPattern) {
|
|
753
|
+
const envVersion = resolveEnvPatternVersion(symbolIndex.getReadDb(), designPattern);
|
|
754
|
+
if (envVersion) {
|
|
755
|
+
const current = xml.match(/<PatternVersion xmlns="">([^<]*)<\/PatternVersion>/)?.[1];
|
|
756
|
+
if (current && current !== envVersion) {
|
|
757
|
+
xml = xml.replace(/(<PatternVersion xmlns="">)[^<]*(<\/PatternVersion>)/, `$1${envVersion}$2`);
|
|
758
|
+
cloneNotes += `\n PatternVersion aligned to this environment: ${current} → ${envVersion}`;
|
|
759
|
+
}
|
|
760
|
+
}
|
|
761
|
+
}
|
|
762
|
+
}
|
|
763
|
+
// Optional lifecycle method stubs (pattern-appropriate, with TODO markers)
|
|
764
|
+
if (includeMethodStubs) {
|
|
765
|
+
const patternInXml = xml.match(/<Pattern xmlns="">([^<]+)<\/Pattern>/)?.[1] ?? normalizedPattern;
|
|
766
|
+
const stubDsName = xml.match(/<AxFormDataSource[^>]*>\s*<Name>([^<]+)<\/Name>/)?.[1] ?? primaryDs?.name ?? '';
|
|
767
|
+
const stubLinesDsName = linesTableResolved ? (linesDsNameResolved || linesTableResolved) : undefined;
|
|
768
|
+
const stubResult = injectMethodStubs(xml, methodStubsForPattern(patternInXml, stubDsName, stubLinesDsName), stubDsName, stubLinesDsName);
|
|
769
|
+
xml = stubResult.xml;
|
|
770
|
+
if (stubResult.injected.length > 0) {
|
|
771
|
+
cloneNotes += `\n Method stubs injected: ${stubResult.injected.join(', ')}`;
|
|
772
|
+
}
|
|
773
|
+
}
|
|
774
|
+
// Several patterns (SimpleList's Grid, and the FieldsFieldGroups Group control
|
|
775
|
+
// on SimpleListDetails/DetailsMaster) bind <DataGroup>Overview</DataGroup> —
|
|
776
|
+
// this ONLY builds if the datasource table has a matching AxTableFieldGroup
|
|
777
|
+
// named "Overview". A brand-new/custom table created earlier in the same
|
|
778
|
+
// session almost never has one yet, so the very next build fails with
|
|
779
|
+
// "Field group 'Overview' does not exist" — a confusing failure with no clue
|
|
780
|
+
// back to this control. Confirmed on this exact scaffold path (corpus:
|
|
781
|
+
// eval/corpus/runs/2026-07-07T11__L3-form-add-datasource-lines__cb1b73d.json,
|
|
782
|
+
// eval/corpus/runs/2026-07-07T15__L4-master-security-slice__cb1b73d.json).
|
|
783
|
+
// This tool has no bridge/table-write access here to auto-create the field
|
|
784
|
+
// group (and a prior investigation found that even a same-session
|
|
785
|
+
// add-field-group call did not reliably become visible to xppc's build —
|
|
786
|
+
// suspected metadata-provider staleness, unconfirmed without a live VM
|
|
787
|
+
// re-check) — surface the dependency loudly instead of failing silently.
|
|
788
|
+
if (/<DataGroup>Overview<\/DataGroup>/.test(xml)) {
|
|
789
|
+
const overviewDsTable = xml.match(/<AxFormDataSource[^>]*>\s*<Name>[^<]+<\/Name>\s*<Table>([^<]+)<\/Table>/)?.[1]
|
|
790
|
+
?? primaryDs?.table ?? primaryDs?.name ?? dataSources[0]?.table;
|
|
791
|
+
cloneNotes +=
|
|
792
|
+
`\n ⚠️ This form references a field group named "Overview" on ` +
|
|
793
|
+
`${overviewDsTable ?? 'the datasource table'} — verify it already exists, or add one BEFORE ` +
|
|
794
|
+
`building via d365fo_file(action="modify", objectType="table", objectName="${overviewDsTable ?? '<table>'}", ` +
|
|
795
|
+
`operation="add-field-group", fieldGroupName="Overview", fieldGroupFields=[...]). Without it the ` +
|
|
796
|
+
`build fails with "Field group 'Overview' does not exist".`;
|
|
797
|
+
}
|
|
798
|
+
console.log(`[generateSmartForm] Generated XML (${xml.length} bytes)`);
|
|
799
|
+
// Self-test: generated XML must conform to its declared pattern.
|
|
800
|
+
// - Template path: errors mean template/catalog drift → hard-fail.
|
|
801
|
+
// - Clone path: a real source form may legitimately deviate from the
|
|
802
|
+
// catalog → report, don't block here (the write gate decides per
|
|
803
|
+
// FORM_PATTERN_ENFORCE at create time).
|
|
804
|
+
const patternReport = await validateFormPatternXml(xml);
|
|
805
|
+
const patternErrors = patternReport.violations.filter(v => v.severity === 'error');
|
|
806
|
+
if (patternErrors.length > 0) {
|
|
807
|
+
const errorList = patternErrors.map(v => `🔴 [${v.rule}] ${v.path}: ${v.excerpt}`).join('\n');
|
|
808
|
+
if (!cloneFrom) {
|
|
809
|
+
return {
|
|
810
|
+
content: [{
|
|
811
|
+
type: 'text',
|
|
812
|
+
text: `❌ generate internal error: the generated XML violates its own pattern ` +
|
|
813
|
+
`(${patternReport.pattern ?? normalizedPattern}). This indicates template/catalog drift — please report it.\n\n` +
|
|
814
|
+
errorList,
|
|
815
|
+
}],
|
|
816
|
+
isError: true,
|
|
817
|
+
};
|
|
818
|
+
}
|
|
819
|
+
cloneNotes +=
|
|
820
|
+
`\n ⚠️ Pattern validation found ${patternErrors.length} error(s) in the cloned XML ` +
|
|
821
|
+
`(d365fo_file(action="create") will block them while FORM_PATTERN_ENFORCE=true):\n` +
|
|
822
|
+
errorList.split('\n').map(l => ` ${l}`).join('\n');
|
|
823
|
+
}
|
|
824
|
+
// Warn when a datasource is bound to a table that does not exist in the index,
|
|
825
|
+
// suggesting the closest real table name.
|
|
826
|
+
//
|
|
827
|
+
// Regression (eval/corpus/runs/2026-07-06T17__L1-form-dialog__cb1b73d.json): a
|
|
828
|
+
// `symbols` row for a table can OUTLIVE the table itself — the index is a cache,
|
|
829
|
+
// not invalidated when an object is deleted/rolled back on the VM. `SELECT 1 ...
|
|
830
|
+
// WHERE name = ?` matched a phantom row from a prior (rolled-back) run's table, so
|
|
831
|
+
// this check silently passed and the scaffold produced a form bound to a table with
|
|
832
|
+
// no file on disk — a build failure with no warning here. Verify the indexed
|
|
833
|
+
// file_path still exists before trusting a hit; a stale row is treated the same as
|
|
834
|
+
// "not found".
|
|
835
|
+
try {
|
|
836
|
+
const db = symbolIndex.getReadDb();
|
|
837
|
+
const seenTables = new Set();
|
|
838
|
+
for (const m of xml.matchAll(/<Table>([^<]+)<\/Table>/g)) {
|
|
839
|
+
const table = m[1].trim();
|
|
840
|
+
if (!table || seenTables.has(table.toLowerCase()))
|
|
841
|
+
continue;
|
|
842
|
+
seenTables.add(table.toLowerCase());
|
|
843
|
+
const row = lookupSymbolNocase(db, table, ['table']);
|
|
844
|
+
const stale = row?.file_path && !fs.existsSync(row.file_path);
|
|
845
|
+
if (row && !stale)
|
|
846
|
+
continue;
|
|
847
|
+
const stem = table.replace(/s$/i, '');
|
|
848
|
+
const alt = db.prepare(`SELECT name FROM symbols WHERE type = 'table' AND name LIKE ? COLLATE NOCASE ORDER BY LENGTH(name) ASC LIMIT 1`).get(`${stem}%`);
|
|
849
|
+
cloneNotes +=
|
|
850
|
+
`\n ⚠️ Datasource table "${table}" ${stale ? 'is stale in the index (its file no longer exists on disk — run update_symbol_index)' : 'not found in the index'}` +
|
|
851
|
+
(alt && alt.name.toLowerCase() !== table.toLowerCase() ? ` — did you mean "${alt.name}"?` : '') +
|
|
852
|
+
` The form will not build until that table exists or the datasource is re-pointed.`;
|
|
853
|
+
}
|
|
854
|
+
}
|
|
855
|
+
catch {
|
|
856
|
+
/* index unavailable — skip the existence check */
|
|
857
|
+
}
|
|
858
|
+
// On non-Windows (Azure/Linux) — return XML as text, no file write possible.
|
|
859
|
+
if (isNonWindows) {
|
|
860
|
+
console.log(`[generateSmartForm] Non-Windows environment — returning XML as text (no file write)`);
|
|
861
|
+
const noModelNote = resolvedModel
|
|
862
|
+
? ''
|
|
863
|
+
: `\n> ⚠️ No model resolved — XML generated without prefix. Pass \`modelName\` with the actual model name from .mcp.json (e.g. \`"ContosoExt"\`) for correct object naming.`;
|
|
864
|
+
const nextStep = [
|
|
865
|
+
``,
|
|
866
|
+
`**✅ MANDATORY NEXT STEP — immediately call \`d365fo_file(action="create")\` with the XML below:**`,
|
|
867
|
+
`\`\`\``,
|
|
868
|
+
`d365fo_file(action="create", `,
|
|
869
|
+
` objectType="form",`,
|
|
870
|
+
` objectName="${finalName}",`,
|
|
871
|
+
` xmlContent="<copy the full XML block below>",`,
|
|
872
|
+
` addToProject=true`,
|
|
873
|
+
`)`,
|
|
874
|
+
`\`\`\``,
|
|
875
|
+
`⛔ NEVER use \`create_file\`, PowerShell scripts, or any built-in file tool — they corrupt D365FO metadata and break VS project integration.`,
|
|
876
|
+
].join('\n');
|
|
877
|
+
return {
|
|
878
|
+
content: [
|
|
879
|
+
{
|
|
880
|
+
type: 'text',
|
|
881
|
+
text: [
|
|
882
|
+
`✅ Form XML generated for **${finalName}**`,
|
|
883
|
+
resolvedModel ? ` Model: ${resolvedModel}` : ` ℹ️ No model resolved — no prefix applied. Pass modelName to set prefix.`,
|
|
884
|
+
` DataSources: ${dataSources.length}, Controls: ${controls.length}`,
|
|
885
|
+
cloneNotes,
|
|
886
|
+
noModelNote,
|
|
887
|
+
``,
|
|
888
|
+
`ℹ️ MCP server is running on Azure/Linux — file writing is handled by the local Windows companion. This is the expected hybrid workflow.`,
|
|
889
|
+
nextStep,
|
|
890
|
+
``,
|
|
891
|
+
`\`\`\`xml`,
|
|
892
|
+
xml,
|
|
893
|
+
`\`\`\``,
|
|
894
|
+
].join('\n'),
|
|
895
|
+
},
|
|
896
|
+
],
|
|
897
|
+
};
|
|
898
|
+
}
|
|
899
|
+
// Windows — write to file
|
|
900
|
+
// Defense-in-depth: resolvedModel should have been validated in the block above,
|
|
901
|
+
// but path.join(packagePath, undefined, ...) throws a cryptic TypeError — guard explicitly.
|
|
902
|
+
if (!resolvedModel) {
|
|
903
|
+
return {
|
|
904
|
+
content: [{
|
|
905
|
+
type: 'text',
|
|
906
|
+
text: `❌ Cannot write form file: model name could not be resolved.\n\n` +
|
|
907
|
+
`Add \`projectPath\` to .mcp.json so the tool can extract the model name from your .rnrproj:\n` +
|
|
908
|
+
`\`\`\`json\n{ "servers": { "context": { "projectPath": "K:\\\\VSProjects\\\\...\\\\YourProject.rnrproj" } } }\n\`\`\``,
|
|
909
|
+
}],
|
|
910
|
+
isError: true,
|
|
911
|
+
};
|
|
912
|
+
}
|
|
913
|
+
const targetPath = path.join(packagePath, resolvedModel, resolvedModel, 'AxForm', `${finalName}.xml`);
|
|
914
|
+
const normalizedPath = targetPath.replace(/\//g, '\\');
|
|
915
|
+
// Verify drive/root exists
|
|
916
|
+
const driveOrRoot = path.parse(normalizedPath).root;
|
|
917
|
+
if (driveOrRoot && !fs.existsSync(driveOrRoot)) {
|
|
918
|
+
throw new Error(`❌ Drive or root path does not exist: ${driveOrRoot}\n\n` +
|
|
919
|
+
`Attempting to create: ${normalizedPath}\n\n` +
|
|
920
|
+
`Update "packagePath" in .mcp.json to match your actual D365FO installation.`);
|
|
921
|
+
}
|
|
922
|
+
const dir = path.dirname(normalizedPath);
|
|
923
|
+
if (!fs.existsSync(dir)) {
|
|
924
|
+
fs.mkdirSync(dir, { recursive: true });
|
|
925
|
+
}
|
|
926
|
+
fs.writeFileSync(normalizedPath, normalizeD365Xml(xml), 'utf-8');
|
|
927
|
+
console.log(`[generateSmartForm] Created file: ${normalizedPath}`);
|
|
928
|
+
// Add to Visual Studio project if a projectPath is known
|
|
929
|
+
let projectMessage = '';
|
|
930
|
+
const effectiveProjectPath = resolvedProjectPath ||
|
|
931
|
+
(await getConfigManager().getProjectPath()) ||
|
|
932
|
+
undefined;
|
|
933
|
+
if (effectiveProjectPath) {
|
|
934
|
+
try {
|
|
935
|
+
const projectManager = new ProjectFileManager();
|
|
936
|
+
const wasAdded = await projectManager.addToProject(effectiveProjectPath, 'form', finalName, normalizedPath);
|
|
937
|
+
projectMessage = wasAdded
|
|
938
|
+
? `\n✅ Added to Visual Studio project:\n📋 Project: ${effectiveProjectPath}`
|
|
939
|
+
: `\n✅ Already in Visual Studio project:\n📋 Project: ${effectiveProjectPath}`;
|
|
940
|
+
console.log(`[generateSmartForm] addToProject result: ${wasAdded ? 'added' : 'already present'}`);
|
|
941
|
+
}
|
|
942
|
+
catch (projErr) {
|
|
943
|
+
projectMessage = `\n⚠️ File created but could not be added to project: ${projErr instanceof Error ? projErr.message : String(projErr)}`;
|
|
944
|
+
console.error(`[generateSmartForm] addToProject error:`, projErr);
|
|
945
|
+
}
|
|
946
|
+
}
|
|
947
|
+
else {
|
|
948
|
+
projectMessage = `\n⚠️ addToProject skipped — no projectPath found in .mcp.json or tool args.`;
|
|
949
|
+
}
|
|
950
|
+
return {
|
|
951
|
+
content: [
|
|
952
|
+
{
|
|
953
|
+
type: 'text',
|
|
954
|
+
text: [
|
|
955
|
+
`✅ Form **${finalName}** created directly on the Windows VM.`,
|
|
956
|
+
``,
|
|
957
|
+
`📁 File: ${normalizedPath}`,
|
|
958
|
+
`📦 Model: ${resolvedModel}`,
|
|
959
|
+
`📊 DataSources: ${dataSources.length}, Controls: ${controls.length}`,
|
|
960
|
+
cloneNotes,
|
|
961
|
+
projectMessage,
|
|
962
|
+
``,
|
|
963
|
+
`⛔ DO NOT call \`d365fo_file(action="create")\` — the file is already written to disk at the path above. Calling d365fo_file would create a DUPLICATE at a different path which causes build conflicts.`,
|
|
964
|
+
`⛔ DO NOT call \`generate\` again — task is COMPLETE.`,
|
|
965
|
+
``,
|
|
966
|
+
`Next steps for the user:`,
|
|
967
|
+
`1. Reload the project in Visual Studio (or close/reopen solution)`,
|
|
968
|
+
`2. Build the project to synchronize the form`,
|
|
969
|
+
`3. Refresh AOT to see the new object`,
|
|
970
|
+
].join('\n'),
|
|
971
|
+
},
|
|
972
|
+
],
|
|
973
|
+
};
|
|
974
|
+
}
|
|
975
|
+
/**
|
|
976
|
+
* The most common Design-level PatternVersion this environment uses for a form
|
|
977
|
+
* pattern, from mined form_patterns data. Returns null when no mined data exists.
|
|
978
|
+
*/
|
|
979
|
+
export function resolveEnvPatternVersion(db, patternXmlName) {
|
|
980
|
+
try {
|
|
981
|
+
const row = db.prepare(`
|
|
982
|
+
SELECT pattern_version, COUNT(*) AS n
|
|
983
|
+
FROM form_patterns
|
|
984
|
+
WHERE node_path = 'Design' AND pattern = ? AND pattern_version IS NOT NULL AND pattern_version != ''
|
|
985
|
+
GROUP BY pattern_version
|
|
986
|
+
ORDER BY n DESC
|
|
987
|
+
LIMIT 1
|
|
988
|
+
`).get(patternXmlName);
|
|
989
|
+
return row?.pattern_version ?? null;
|
|
990
|
+
}
|
|
991
|
+
catch {
|
|
992
|
+
return null;
|
|
993
|
+
}
|
|
994
|
+
}
|
|
995
|
+
// extractModelFromProject and findProjectInSolution moved to ../utils/projectUtils.ts
|
|
996
|
+
//# sourceMappingURL=generateSmartForm.js.map
|