unreal-engine-mcp-server 0.4.6 → 0.5.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.
Files changed (438) hide show
  1. package/.env.example +26 -0
  2. package/.env.production +38 -7
  3. package/.eslintrc.json +0 -54
  4. package/.eslintrc.override.json +8 -0
  5. package/.github/ISSUE_TEMPLATE/bug_report.yml +94 -0
  6. package/.github/ISSUE_TEMPLATE/config.yml +8 -0
  7. package/.github/ISSUE_TEMPLATE/feature_request.yml +56 -0
  8. package/.github/copilot-instructions.md +478 -45
  9. package/.github/dependabot.yml +19 -0
  10. package/.github/labeler.yml +24 -0
  11. package/.github/labels.yml +70 -0
  12. package/.github/pull_request_template.md +42 -0
  13. package/.github/release-drafter.yml +148 -0
  14. package/.github/workflows/auto-merge.yml +38 -0
  15. package/.github/workflows/ci.yml +38 -0
  16. package/.github/workflows/dependency-review.yml +17 -0
  17. package/.github/workflows/gemini-issue-triage.yml +172 -0
  18. package/.github/workflows/greetings.yml +23 -0
  19. package/.github/workflows/labeler.yml +16 -0
  20. package/.github/workflows/links.yml +80 -0
  21. package/.github/workflows/pr-size-labeler.yml +137 -0
  22. package/.github/workflows/publish-mcp.yml +12 -7
  23. package/.github/workflows/release-drafter.yml +23 -0
  24. package/.github/workflows/release.yml +112 -0
  25. package/.github/workflows/semantic-pull-request.yml +35 -0
  26. package/.github/workflows/smoke-test.yml +36 -0
  27. package/.github/workflows/stale.yml +28 -0
  28. package/CHANGELOG.md +269 -22
  29. package/CONTRIBUTING.md +140 -0
  30. package/README.md +166 -72
  31. package/claude_desktop_config_example.json +7 -6
  32. package/dist/automation/bridge.d.ts +50 -0
  33. package/dist/automation/bridge.js +452 -0
  34. package/dist/automation/connection-manager.d.ts +23 -0
  35. package/dist/automation/connection-manager.js +107 -0
  36. package/dist/automation/handshake.d.ts +11 -0
  37. package/dist/automation/handshake.js +89 -0
  38. package/dist/automation/index.d.ts +3 -0
  39. package/dist/automation/index.js +3 -0
  40. package/dist/automation/message-handler.d.ts +12 -0
  41. package/dist/automation/message-handler.js +149 -0
  42. package/dist/automation/request-tracker.d.ts +25 -0
  43. package/dist/automation/request-tracker.js +98 -0
  44. package/dist/automation/types.d.ts +130 -0
  45. package/dist/automation/types.js +2 -0
  46. package/dist/cli.js +32 -5
  47. package/dist/config.d.ts +27 -0
  48. package/dist/config.js +60 -0
  49. package/dist/constants.d.ts +12 -0
  50. package/dist/constants.js +12 -0
  51. package/dist/graphql/resolvers.d.ts +268 -0
  52. package/dist/graphql/resolvers.js +743 -0
  53. package/dist/graphql/schema.d.ts +5 -0
  54. package/dist/graphql/schema.js +437 -0
  55. package/dist/graphql/server.d.ts +26 -0
  56. package/dist/graphql/server.js +115 -0
  57. package/dist/graphql/types.d.ts +7 -0
  58. package/dist/graphql/types.js +2 -0
  59. package/dist/handlers/resource-handlers.d.ts +20 -0
  60. package/dist/handlers/resource-handlers.js +180 -0
  61. package/dist/index.d.ts +31 -18
  62. package/dist/index.js +119 -604
  63. package/dist/prompts/index.js +4 -4
  64. package/dist/resources/actors.d.ts +17 -12
  65. package/dist/resources/actors.js +56 -76
  66. package/dist/resources/assets.d.ts +6 -14
  67. package/dist/resources/assets.js +115 -147
  68. package/dist/resources/levels.d.ts +13 -13
  69. package/dist/resources/levels.js +25 -34
  70. package/dist/server/resource-registry.d.ts +20 -0
  71. package/dist/server/resource-registry.js +37 -0
  72. package/dist/server/tool-registry.d.ts +23 -0
  73. package/dist/server/tool-registry.js +322 -0
  74. package/dist/server-setup.d.ts +21 -0
  75. package/dist/server-setup.js +111 -0
  76. package/dist/services/health-monitor.d.ts +34 -0
  77. package/dist/services/health-monitor.js +105 -0
  78. package/dist/services/metrics-server.d.ts +11 -0
  79. package/dist/services/metrics-server.js +105 -0
  80. package/dist/tools/actors.d.ts +147 -9
  81. package/dist/tools/actors.js +350 -311
  82. package/dist/tools/animation.d.ts +135 -4
  83. package/dist/tools/animation.js +510 -411
  84. package/dist/tools/assets.d.ts +117 -19
  85. package/dist/tools/assets.js +259 -284
  86. package/dist/tools/audio.d.ts +102 -42
  87. package/dist/tools/audio.js +272 -685
  88. package/dist/tools/base-tool.d.ts +17 -0
  89. package/dist/tools/base-tool.js +46 -0
  90. package/dist/tools/behavior-tree.d.ts +94 -0
  91. package/dist/tools/behavior-tree.js +39 -0
  92. package/dist/tools/blueprint/helpers.d.ts +29 -0
  93. package/dist/tools/blueprint/helpers.js +182 -0
  94. package/dist/tools/blueprint.d.ts +228 -118
  95. package/dist/tools/blueprint.js +685 -832
  96. package/dist/tools/consolidated-tool-definitions.d.ts +5475 -1627
  97. package/dist/tools/consolidated-tool-definitions.js +829 -482
  98. package/dist/tools/consolidated-tool-handlers.d.ts +2 -1
  99. package/dist/tools/consolidated-tool-handlers.js +211 -1009
  100. package/dist/tools/debug.d.ts +143 -85
  101. package/dist/tools/debug.js +234 -180
  102. package/dist/tools/dynamic-handler-registry.d.ts +11 -0
  103. package/dist/tools/dynamic-handler-registry.js +101 -0
  104. package/dist/tools/editor.d.ts +139 -18
  105. package/dist/tools/editor.js +239 -244
  106. package/dist/tools/engine.d.ts +10 -4
  107. package/dist/tools/engine.js +13 -5
  108. package/dist/tools/environment.d.ts +36 -0
  109. package/dist/tools/environment.js +267 -0
  110. package/dist/tools/foliage.d.ts +105 -14
  111. package/dist/tools/foliage.js +219 -331
  112. package/dist/tools/handlers/actor-handlers.d.ts +3 -0
  113. package/dist/tools/handlers/actor-handlers.js +232 -0
  114. package/dist/tools/handlers/animation-handlers.d.ts +3 -0
  115. package/dist/tools/handlers/animation-handlers.js +185 -0
  116. package/dist/tools/handlers/argument-helper.d.ts +16 -0
  117. package/dist/tools/handlers/argument-helper.js +80 -0
  118. package/dist/tools/handlers/asset-handlers.d.ts +3 -0
  119. package/dist/tools/handlers/asset-handlers.js +496 -0
  120. package/dist/tools/handlers/audio-handlers.d.ts +3 -0
  121. package/dist/tools/handlers/audio-handlers.js +166 -0
  122. package/dist/tools/handlers/blueprint-handlers.d.ts +4 -0
  123. package/dist/tools/handlers/blueprint-handlers.js +358 -0
  124. package/dist/tools/handlers/common-handlers.d.ts +14 -0
  125. package/dist/tools/handlers/common-handlers.js +56 -0
  126. package/dist/tools/handlers/editor-handlers.d.ts +3 -0
  127. package/dist/tools/handlers/editor-handlers.js +119 -0
  128. package/dist/tools/handlers/effect-handlers.d.ts +3 -0
  129. package/dist/tools/handlers/effect-handlers.js +171 -0
  130. package/dist/tools/handlers/environment-handlers.d.ts +3 -0
  131. package/dist/tools/handlers/environment-handlers.js +170 -0
  132. package/dist/tools/handlers/graph-handlers.d.ts +3 -0
  133. package/dist/tools/handlers/graph-handlers.js +90 -0
  134. package/dist/tools/handlers/input-handlers.d.ts +3 -0
  135. package/dist/tools/handlers/input-handlers.js +21 -0
  136. package/dist/tools/handlers/inspect-handlers.d.ts +3 -0
  137. package/dist/tools/handlers/inspect-handlers.js +383 -0
  138. package/dist/tools/handlers/level-handlers.d.ts +3 -0
  139. package/dist/tools/handlers/level-handlers.js +237 -0
  140. package/dist/tools/handlers/lighting-handlers.d.ts +3 -0
  141. package/dist/tools/handlers/lighting-handlers.js +144 -0
  142. package/dist/tools/handlers/performance-handlers.d.ts +3 -0
  143. package/dist/tools/handlers/performance-handlers.js +130 -0
  144. package/dist/tools/handlers/pipeline-handlers.d.ts +3 -0
  145. package/dist/tools/handlers/pipeline-handlers.js +110 -0
  146. package/dist/tools/handlers/sequence-handlers.d.ts +3 -0
  147. package/dist/tools/handlers/sequence-handlers.js +376 -0
  148. package/dist/tools/handlers/system-handlers.d.ts +4 -0
  149. package/dist/tools/handlers/system-handlers.js +506 -0
  150. package/dist/tools/input.d.ts +19 -0
  151. package/dist/tools/input.js +89 -0
  152. package/dist/tools/introspection.d.ts +103 -40
  153. package/dist/tools/introspection.js +425 -568
  154. package/dist/tools/landscape.d.ts +97 -36
  155. package/dist/tools/landscape.js +280 -409
  156. package/dist/tools/level.d.ts +130 -10
  157. package/dist/tools/level.js +639 -675
  158. package/dist/tools/lighting.d.ts +77 -38
  159. package/dist/tools/lighting.js +441 -943
  160. package/dist/tools/logs.d.ts +45 -0
  161. package/dist/tools/logs.js +210 -0
  162. package/dist/tools/materials.d.ts +91 -24
  163. package/dist/tools/materials.js +190 -118
  164. package/dist/tools/niagara.d.ts +149 -39
  165. package/dist/tools/niagara.js +232 -182
  166. package/dist/tools/performance.d.ts +27 -12
  167. package/dist/tools/performance.js +204 -122
  168. package/dist/tools/physics.d.ts +32 -77
  169. package/dist/tools/physics.js +171 -582
  170. package/dist/tools/property-dictionary.d.ts +13 -0
  171. package/dist/tools/property-dictionary.js +82 -0
  172. package/dist/tools/sequence.d.ts +73 -48
  173. package/dist/tools/sequence.js +196 -748
  174. package/dist/tools/tool-definition-utils.d.ts +59 -0
  175. package/dist/tools/tool-definition-utils.js +35 -0
  176. package/dist/tools/ui.d.ts +66 -34
  177. package/dist/tools/ui.js +134 -214
  178. package/dist/types/env.d.ts +0 -3
  179. package/dist/types/env.js +0 -7
  180. package/dist/types/tool-interfaces.d.ts +898 -0
  181. package/dist/types/tool-interfaces.js +2 -0
  182. package/dist/types/tool-types.d.ts +195 -11
  183. package/dist/types/tool-types.js +0 -4
  184. package/dist/unreal-bridge.d.ts +24 -131
  185. package/dist/unreal-bridge.js +364 -1506
  186. package/dist/utils/command-validator.d.ts +9 -0
  187. package/dist/utils/command-validator.js +67 -0
  188. package/dist/utils/elicitation.d.ts +1 -1
  189. package/dist/utils/elicitation.js +12 -15
  190. package/dist/utils/error-handler.d.ts +2 -51
  191. package/dist/utils/error-handler.js +11 -87
  192. package/dist/utils/ini-reader.d.ts +3 -0
  193. package/dist/utils/ini-reader.js +69 -0
  194. package/dist/utils/logger.js +9 -6
  195. package/dist/utils/normalize.d.ts +3 -0
  196. package/dist/utils/normalize.js +56 -0
  197. package/dist/utils/response-factory.d.ts +7 -0
  198. package/dist/utils/response-factory.js +33 -0
  199. package/dist/utils/response-validator.d.ts +3 -24
  200. package/dist/utils/response-validator.js +130 -81
  201. package/dist/utils/result-helpers.d.ts +4 -5
  202. package/dist/utils/result-helpers.js +15 -16
  203. package/dist/utils/safe-json.js +5 -11
  204. package/dist/utils/unreal-command-queue.d.ts +24 -0
  205. package/dist/utils/unreal-command-queue.js +120 -0
  206. package/dist/utils/validation.d.ts +0 -40
  207. package/dist/utils/validation.js +1 -78
  208. package/dist/wasm/index.d.ts +70 -0
  209. package/dist/wasm/index.js +535 -0
  210. package/docs/GraphQL-API.md +888 -0
  211. package/docs/Migration-Guide-v0.5.0.md +692 -0
  212. package/docs/Roadmap.md +53 -0
  213. package/docs/WebAssembly-Integration.md +628 -0
  214. package/docs/editor-plugin-extension.md +370 -0
  215. package/docs/handler-mapping.md +242 -0
  216. package/docs/native-automation-progress.md +128 -0
  217. package/docs/testing-guide.md +423 -0
  218. package/mcp-config-example.json +6 -6
  219. package/package.json +60 -27
  220. package/plugins/McpAutomationBridge/Config/FilterPlugin.ini +8 -0
  221. package/plugins/McpAutomationBridge/McpAutomationBridge.uplugin +64 -0
  222. package/plugins/McpAutomationBridge/Source/McpAutomationBridge/McpAutomationBridge.Build.cs +189 -0
  223. package/plugins/McpAutomationBridge/Source/McpAutomationBridge/Private/McpAutomationBridgeGlobals.cpp +22 -0
  224. package/plugins/McpAutomationBridge/Source/McpAutomationBridge/Private/McpAutomationBridgeGlobals.h +30 -0
  225. package/plugins/McpAutomationBridge/Source/McpAutomationBridge/Private/McpAutomationBridgeHelpers.h +1983 -0
  226. package/plugins/McpAutomationBridge/Source/McpAutomationBridge/Private/McpAutomationBridgeModule.cpp +72 -0
  227. package/plugins/McpAutomationBridge/Source/McpAutomationBridge/Private/McpAutomationBridgeSettings.cpp +46 -0
  228. package/plugins/McpAutomationBridge/Source/McpAutomationBridge/Private/McpAutomationBridgeSubsystem.cpp +581 -0
  229. package/plugins/McpAutomationBridge/Source/McpAutomationBridge/Private/McpAutomationBridge_AnimationHandlers.cpp +2394 -0
  230. package/plugins/McpAutomationBridge/Source/McpAutomationBridge/Private/McpAutomationBridge_AssetQueryHandlers.cpp +300 -0
  231. package/plugins/McpAutomationBridge/Source/McpAutomationBridge/Private/McpAutomationBridge_AssetWorkflowHandlers.cpp +2807 -0
  232. package/plugins/McpAutomationBridge/Source/McpAutomationBridge/Private/McpAutomationBridge_AudioHandlers.cpp +1087 -0
  233. package/plugins/McpAutomationBridge/Source/McpAutomationBridge/Private/McpAutomationBridge_BehaviorTreeHandlers.cpp +488 -0
  234. package/plugins/McpAutomationBridge/Source/McpAutomationBridge/Private/McpAutomationBridge_BlueprintCreationHandlers.cpp +643 -0
  235. package/plugins/McpAutomationBridge/Source/McpAutomationBridge/Private/McpAutomationBridge_BlueprintCreationHandlers.h +31 -0
  236. package/plugins/McpAutomationBridge/Source/McpAutomationBridge/Private/McpAutomationBridge_BlueprintGraphHandlers.cpp +1184 -0
  237. package/plugins/McpAutomationBridge/Source/McpAutomationBridge/Private/McpAutomationBridge_BlueprintHandlers.cpp +5652 -0
  238. package/plugins/McpAutomationBridge/Source/McpAutomationBridge/Private/McpAutomationBridge_BlueprintHandlers_List.cpp +152 -0
  239. package/plugins/McpAutomationBridge/Source/McpAutomationBridge/Private/McpAutomationBridge_ControlHandlers.cpp +2614 -0
  240. package/plugins/McpAutomationBridge/Source/McpAutomationBridge/Private/McpAutomationBridge_DebugHandlers.cpp +42 -0
  241. package/plugins/McpAutomationBridge/Source/McpAutomationBridge/Private/McpAutomationBridge_EditorFunctionHandlers.cpp +1237 -0
  242. package/plugins/McpAutomationBridge/Source/McpAutomationBridge/Private/McpAutomationBridge_EffectHandlers.cpp +1701 -0
  243. package/plugins/McpAutomationBridge/Source/McpAutomationBridge/Private/McpAutomationBridge_EnvironmentHandlers.cpp +2145 -0
  244. package/plugins/McpAutomationBridge/Source/McpAutomationBridge/Private/McpAutomationBridge_FoliageHandlers.cpp +954 -0
  245. package/plugins/McpAutomationBridge/Source/McpAutomationBridge/Private/McpAutomationBridge_InputHandlers.cpp +209 -0
  246. package/plugins/McpAutomationBridge/Source/McpAutomationBridge/Private/McpAutomationBridge_InsightsHandlers.cpp +41 -0
  247. package/plugins/McpAutomationBridge/Source/McpAutomationBridge/Private/McpAutomationBridge_LandscapeHandlers.cpp +1164 -0
  248. package/plugins/McpAutomationBridge/Source/McpAutomationBridge/Private/McpAutomationBridge_LevelHandlers.cpp +762 -0
  249. package/plugins/McpAutomationBridge/Source/McpAutomationBridge/Private/McpAutomationBridge_LightingHandlers.cpp +634 -0
  250. package/plugins/McpAutomationBridge/Source/McpAutomationBridge/Private/McpAutomationBridge_LogHandlers.cpp +136 -0
  251. package/plugins/McpAutomationBridge/Source/McpAutomationBridge/Private/McpAutomationBridge_MaterialGraphHandlers.cpp +494 -0
  252. package/plugins/McpAutomationBridge/Source/McpAutomationBridge/Private/McpAutomationBridge_NiagaraGraphHandlers.cpp +278 -0
  253. package/plugins/McpAutomationBridge/Source/McpAutomationBridge/Private/McpAutomationBridge_NiagaraHandlers.cpp +625 -0
  254. package/plugins/McpAutomationBridge/Source/McpAutomationBridge/Private/McpAutomationBridge_PerformanceHandlers.cpp +401 -0
  255. package/plugins/McpAutomationBridge/Source/McpAutomationBridge/Private/McpAutomationBridge_PipelineHandlers.cpp +67 -0
  256. package/plugins/McpAutomationBridge/Source/McpAutomationBridge/Private/McpAutomationBridge_ProcessRequest.cpp +735 -0
  257. package/plugins/McpAutomationBridge/Source/McpAutomationBridge/Private/McpAutomationBridge_PropertyHandlers.cpp +2634 -0
  258. package/plugins/McpAutomationBridge/Source/McpAutomationBridge/Private/McpAutomationBridge_RenderHandlers.cpp +189 -0
  259. package/plugins/McpAutomationBridge/Source/McpAutomationBridge/Private/McpAutomationBridge_SCSHandlers.cpp +917 -0
  260. package/plugins/McpAutomationBridge/Source/McpAutomationBridge/Private/McpAutomationBridge_SCSHandlers.h +39 -0
  261. package/plugins/McpAutomationBridge/Source/McpAutomationBridge/Private/McpAutomationBridge_SequenceHandlers.cpp +2670 -0
  262. package/plugins/McpAutomationBridge/Source/McpAutomationBridge/Private/McpAutomationBridge_SequencerHandlers.cpp +519 -0
  263. package/plugins/McpAutomationBridge/Source/McpAutomationBridge/Private/McpAutomationBridge_TestHandlers.cpp +38 -0
  264. package/plugins/McpAutomationBridge/Source/McpAutomationBridge/Private/McpAutomationBridge_UiHandlers.cpp +668 -0
  265. package/plugins/McpAutomationBridge/Source/McpAutomationBridge/Private/McpAutomationBridge_WorldPartitionHandlers.cpp +346 -0
  266. package/plugins/McpAutomationBridge/Source/McpAutomationBridge/Private/McpBridgeWebSocket.cpp +1330 -0
  267. package/plugins/McpAutomationBridge/Source/McpAutomationBridge/Private/McpBridgeWebSocket.h +149 -0
  268. package/plugins/McpAutomationBridge/Source/McpAutomationBridge/Private/McpConnectionManager.cpp +783 -0
  269. package/plugins/McpAutomationBridge/Source/McpAutomationBridge/Public/McpAutomationBridgeSettings.h +115 -0
  270. package/plugins/McpAutomationBridge/Source/McpAutomationBridge/Public/McpAutomationBridgeSubsystem.h +796 -0
  271. package/plugins/McpAutomationBridge/Source/McpAutomationBridge/Public/McpConnectionManager.h +117 -0
  272. package/scripts/check-unreal-connection.mjs +19 -0
  273. package/scripts/clean-tmp.js +23 -0
  274. package/scripts/patch-wasm.js +26 -0
  275. package/scripts/run-all-tests.mjs +131 -0
  276. package/scripts/smoke-test.ts +94 -0
  277. package/scripts/sync-mcp-plugin.js +143 -0
  278. package/scripts/test-no-plugin-alternates.mjs +113 -0
  279. package/scripts/validate-server.js +46 -0
  280. package/scripts/verify-automation-bridge.js +200 -0
  281. package/server.json +57 -21
  282. package/src/automation/bridge.ts +558 -0
  283. package/src/automation/connection-manager.ts +130 -0
  284. package/src/automation/handshake.ts +99 -0
  285. package/src/automation/index.ts +2 -0
  286. package/src/automation/message-handler.ts +167 -0
  287. package/src/automation/request-tracker.ts +123 -0
  288. package/src/automation/types.ts +107 -0
  289. package/src/cli.ts +33 -6
  290. package/src/config.ts +73 -0
  291. package/src/constants.ts +12 -0
  292. package/src/graphql/resolvers.ts +1010 -0
  293. package/src/graphql/schema.ts +452 -0
  294. package/src/graphql/server.ts +154 -0
  295. package/src/graphql/types.ts +7 -0
  296. package/src/handlers/resource-handlers.ts +186 -0
  297. package/src/index.ts +152 -649
  298. package/src/prompts/index.ts +4 -4
  299. package/src/resources/actors.ts +58 -76
  300. package/src/resources/assets.ts +147 -134
  301. package/src/resources/levels.ts +28 -33
  302. package/src/server/resource-registry.ts +47 -0
  303. package/src/server/tool-registry.ts +354 -0
  304. package/src/server-setup.ts +148 -0
  305. package/src/services/health-monitor.ts +132 -0
  306. package/src/services/metrics-server.ts +142 -0
  307. package/src/tools/actors.ts +417 -322
  308. package/src/tools/animation.ts +671 -461
  309. package/src/tools/assets.ts +353 -289
  310. package/src/tools/audio.ts +323 -766
  311. package/src/tools/base-tool.ts +52 -0
  312. package/src/tools/behavior-tree.ts +45 -0
  313. package/src/tools/blueprint/helpers.ts +189 -0
  314. package/src/tools/blueprint.ts +787 -965
  315. package/src/tools/consolidated-tool-definitions.ts +993 -500
  316. package/src/tools/consolidated-tool-handlers.ts +272 -1122
  317. package/src/tools/debug.ts +292 -187
  318. package/src/tools/dynamic-handler-registry.ts +151 -0
  319. package/src/tools/editor.ts +309 -246
  320. package/src/tools/engine.ts +14 -3
  321. package/src/tools/environment.ts +287 -0
  322. package/src/tools/foliage.ts +314 -379
  323. package/src/tools/handlers/actor-handlers.ts +271 -0
  324. package/src/tools/handlers/animation-handlers.ts +237 -0
  325. package/src/tools/handlers/argument-helper.ts +142 -0
  326. package/src/tools/handlers/asset-handlers.ts +532 -0
  327. package/src/tools/handlers/audio-handlers.ts +194 -0
  328. package/src/tools/handlers/blueprint-handlers.ts +380 -0
  329. package/src/tools/handlers/common-handlers.ts +87 -0
  330. package/src/tools/handlers/editor-handlers.ts +123 -0
  331. package/src/tools/handlers/effect-handlers.ts +220 -0
  332. package/src/tools/handlers/environment-handlers.ts +183 -0
  333. package/src/tools/handlers/graph-handlers.ts +116 -0
  334. package/src/tools/handlers/input-handlers.ts +28 -0
  335. package/src/tools/handlers/inspect-handlers.ts +450 -0
  336. package/src/tools/handlers/level-handlers.ts +252 -0
  337. package/src/tools/handlers/lighting-handlers.ts +147 -0
  338. package/src/tools/handlers/performance-handlers.ts +132 -0
  339. package/src/tools/handlers/pipeline-handlers.ts +127 -0
  340. package/src/tools/handlers/sequence-handlers.ts +415 -0
  341. package/src/tools/handlers/system-handlers.ts +564 -0
  342. package/src/tools/input.ts +101 -0
  343. package/src/tools/introspection.ts +493 -584
  344. package/src/tools/landscape.ts +394 -489
  345. package/src/tools/level.ts +752 -694
  346. package/src/tools/lighting.ts +583 -984
  347. package/src/tools/logs.ts +219 -0
  348. package/src/tools/materials.ts +231 -121
  349. package/src/tools/niagara.ts +293 -168
  350. package/src/tools/performance.ts +320 -168
  351. package/src/tools/physics.ts +268 -613
  352. package/src/tools/property-dictionary.ts +98 -0
  353. package/src/tools/sequence.ts +255 -815
  354. package/src/tools/tool-definition-utils.ts +35 -0
  355. package/src/tools/ui.ts +207 -283
  356. package/src/types/env.ts +0 -10
  357. package/src/types/tool-interfaces.ts +250 -0
  358. package/src/types/tool-types.ts +250 -13
  359. package/src/unreal-bridge.ts +460 -1550
  360. package/src/utils/command-validator.ts +75 -0
  361. package/src/utils/elicitation.ts +10 -7
  362. package/src/utils/error-handler.ts +14 -90
  363. package/src/utils/ini-reader.ts +86 -0
  364. package/src/utils/logger.ts +8 -3
  365. package/src/utils/normalize.ts +60 -0
  366. package/src/utils/response-factory.ts +39 -0
  367. package/src/utils/response-validator.ts +176 -56
  368. package/src/utils/result-helpers.ts +21 -19
  369. package/src/utils/safe-json.ts +14 -11
  370. package/src/utils/unreal-command-queue.ts +152 -0
  371. package/src/utils/validation.ts +4 -1
  372. package/src/wasm/index.ts +838 -0
  373. package/test-server.mjs +100 -0
  374. package/tests/run-unreal-tool-tests.mjs +242 -14
  375. package/tests/test-animation.mjs +44 -0
  376. package/tests/test-asset-advanced.mjs +82 -0
  377. package/tests/test-asset-errors.mjs +35 -0
  378. package/tests/test-audio.mjs +219 -0
  379. package/tests/test-automation-timeouts.mjs +98 -0
  380. package/tests/test-behavior-tree.mjs +261 -0
  381. package/tests/test-blueprint-events.mjs +35 -0
  382. package/tests/test-blueprint-graph.mjs +79 -0
  383. package/tests/test-blueprint.mjs +577 -0
  384. package/tests/test-client-mode.mjs +86 -0
  385. package/tests/test-console-command.mjs +56 -0
  386. package/tests/test-control-actor.mjs +425 -0
  387. package/tests/test-control-editor.mjs +80 -0
  388. package/tests/test-extra-tools.mjs +38 -0
  389. package/tests/test-graphql.mjs +322 -0
  390. package/tests/test-inspect.mjs +72 -0
  391. package/tests/test-landscape.mjs +60 -0
  392. package/tests/test-manage-asset.mjs +438 -0
  393. package/tests/test-manage-level.mjs +70 -0
  394. package/tests/test-materials.mjs +356 -0
  395. package/tests/test-niagara.mjs +185 -0
  396. package/tests/test-no-inline-python.mjs +122 -0
  397. package/tests/test-plugin-handshake.mjs +82 -0
  398. package/tests/test-render.mjs +33 -0
  399. package/tests/test-runner.mjs +933 -0
  400. package/tests/test-search-assets.mjs +66 -0
  401. package/tests/test-sequence.mjs +68 -0
  402. package/tests/test-system.mjs +57 -0
  403. package/tests/test-wasm.mjs +193 -0
  404. package/tests/test-world-partition.mjs +215 -0
  405. package/tsconfig.json +3 -3
  406. package/wasm/Cargo.lock +363 -0
  407. package/wasm/Cargo.toml +42 -0
  408. package/wasm/LICENSE +21 -0
  409. package/wasm/README.md +253 -0
  410. package/wasm/src/dependency_resolver.rs +377 -0
  411. package/wasm/src/lib.rs +153 -0
  412. package/wasm/src/property_parser.rs +271 -0
  413. package/wasm/src/transform_math.rs +396 -0
  414. package/wasm/tests/integration.rs +109 -0
  415. package/.github/workflows/smithery-build.yml +0 -29
  416. package/dist/tools/build_environment_advanced.d.ts +0 -65
  417. package/dist/tools/build_environment_advanced.js +0 -633
  418. package/dist/tools/rc.d.ts +0 -110
  419. package/dist/tools/rc.js +0 -437
  420. package/dist/tools/visual.d.ts +0 -40
  421. package/dist/tools/visual.js +0 -282
  422. package/dist/utils/http.d.ts +0 -6
  423. package/dist/utils/http.js +0 -151
  424. package/dist/utils/python-output.d.ts +0 -18
  425. package/dist/utils/python-output.js +0 -290
  426. package/dist/utils/python.d.ts +0 -2
  427. package/dist/utils/python.js +0 -4
  428. package/dist/utils/stdio-redirect.d.ts +0 -2
  429. package/dist/utils/stdio-redirect.js +0 -20
  430. package/docs/unreal-tool-test-cases.md +0 -572
  431. package/smithery.yaml +0 -29
  432. package/src/tools/build_environment_advanced.ts +0 -732
  433. package/src/tools/rc.ts +0 -515
  434. package/src/tools/visual.ts +0 -281
  435. package/src/utils/http.ts +0 -187
  436. package/src/utils/python-output.ts +0 -351
  437. package/src/utils/python.ts +0 -3
  438. package/src/utils/stdio-redirect.ts +0 -18
@@ -0,0 +1,735 @@
1
+ #include "Async/Async.h"
2
+ #include "HAL/PlatformTime.h"
3
+ #include "McpAutomationBridgeGlobals.h"
4
+ #include "McpAutomationBridgeHelpers.h"
5
+ #include "McpAutomationBridgeSubsystem.h"
6
+ #include "McpConnectionManager.h"
7
+ #include "Misc/ScopeExit.h"
8
+ #include "Misc/ScopeLock.h"
9
+
10
+ void UMcpAutomationBridgeSubsystem::ProcessAutomationRequest(
11
+ const FString &RequestId, const FString &Action,
12
+ const TSharedPtr<FJsonObject> &Payload,
13
+ TSharedPtr<FMcpBridgeWebSocket> RequestingSocket) {
14
+ // This large implementation was extracted from the original subsystem
15
+ // translation unit to keep the core file smaller and focused. It
16
+ // contains the main dispatcher that delegates to specialized handler
17
+ // functions (property/blueprint/sequence/asset handlers) and retains
18
+ // the queuing/scope-exit safety logic expected by callers.
19
+
20
+ // Ensure automation processing happens on the game thread
21
+ // This trace is intentionally verbose — routine requests can be high
22
+ // frequency and will otherwise flood the logs. Developers can enable
23
+ // Verbose logging to see these messages when required.
24
+ UE_LOG(LogMcpAutomationBridgeSubsystem, Verbose,
25
+ TEXT(">>> ProcessAutomationRequest ENTRY: RequestId=%s action='%s' "
26
+ "(thread=%s)"),
27
+ *RequestId, *Action,
28
+ IsInGameThread() ? TEXT("GameThread") : TEXT("SocketThread"));
29
+ UE_LOG(LogMcpAutomationBridgeSubsystem, Verbose,
30
+ TEXT("ProcessAutomationRequest invoked (thread=%s) RequestId=%s "
31
+ "action=%s activeSockets=%d pendingQueue=%d"),
32
+ IsInGameThread() ? TEXT("GameThread") : TEXT("SocketThread"),
33
+ *RequestId, *Action,
34
+ ConnectionManager.IsValid() ? ConnectionManager->GetActiveSocketCount()
35
+ : 0,
36
+ PendingAutomationRequests.Num());
37
+ if (!IsInGameThread()) {
38
+ UE_LOG(LogMcpAutomationBridgeSubsystem, Verbose,
39
+ TEXT("Scheduling ProcessAutomationRequest on GameThread: "
40
+ "RequestId=%s action=%s"),
41
+ *RequestId, *Action);
42
+ AsyncTask(ENamedThreads::GameThread,
43
+ [WeakThis = TWeakObjectPtr<UMcpAutomationBridgeSubsystem>(this),
44
+ RequestId, Action, Payload, RequestingSocket]() {
45
+ if (UMcpAutomationBridgeSubsystem *Pinned = WeakThis.Get()) {
46
+ Pinned->ProcessAutomationRequest(RequestId, Action, Payload,
47
+ RequestingSocket);
48
+ }
49
+ });
50
+ return;
51
+ }
52
+
53
+ // Guard against unsafe engine states (Saving, GC, Async Loading)
54
+ // Calling StaticFindObject (via ResolveClassByName) during these states can
55
+ // cause crashes.
56
+ if (GIsSavingPackage || IsGarbageCollecting() || IsAsyncLoading()) {
57
+ UE_LOG(LogMcpAutomationBridgeSubsystem, Verbose,
58
+ TEXT("Deferring ProcessAutomationRequest due to active "
59
+ "Serialization/GC/Loading: RequestId=%s Action=%s"),
60
+ *RequestId, *Action);
61
+
62
+ FPendingAutomationRequest P;
63
+ P.RequestId = RequestId;
64
+ P.Action = Action;
65
+ P.Payload = Payload;
66
+ P.RequestingSocket = RequestingSocket;
67
+ {
68
+ FScopeLock Lock(&PendingAutomationRequestsMutex);
69
+ PendingAutomationRequests.Add(MoveTemp(P));
70
+ bPendingRequestsScheduled = true;
71
+ }
72
+ return;
73
+ }
74
+
75
+ UE_LOG(LogMcpAutomationBridgeSubsystem, Verbose,
76
+ TEXT("Starting ProcessAutomationRequest on GameThread: RequestId=%s "
77
+ "action=%s bProcessingAutomationRequest=%s"),
78
+ *RequestId, *Action,
79
+ bProcessingAutomationRequest ? TEXT("true") : TEXT("false"));
80
+
81
+ const FString LowerAction = Action.ToLower();
82
+
83
+ if (ConnectionManager.IsValid()) {
84
+ ConnectionManager->StartRequestTelemetry(RequestId, Action);
85
+ }
86
+
87
+ // Reentrancy guard / enqueue
88
+ if (bProcessingAutomationRequest) {
89
+ FPendingAutomationRequest P;
90
+ P.RequestId = RequestId;
91
+ P.Action = Action;
92
+ P.Payload = Payload;
93
+ P.RequestingSocket = RequestingSocket;
94
+ {
95
+ FScopeLock Lock(&PendingAutomationRequestsMutex);
96
+ PendingAutomationRequests.Add(MoveTemp(P));
97
+ bPendingRequestsScheduled = true;
98
+ }
99
+ UE_LOG(LogMcpAutomationBridgeSubsystem, Verbose,
100
+ TEXT("Enqueued automation request %s for action %s (processing in "
101
+ "progress)."),
102
+ *RequestId, *Action);
103
+ return;
104
+ }
105
+
106
+ bProcessingAutomationRequest = true;
107
+ bool bDispatchHandled = false;
108
+ FString ConsumedHandlerLabel = TEXT("unknown-handler");
109
+ const double DispatchStartSeconds = FPlatformTime::Seconds();
110
+
111
+ auto HandleAndLog = [&](const TCHAR *HandlerLabel, auto &&Callable) -> bool {
112
+ const bool bResult = Callable();
113
+ if (bResult) {
114
+ bDispatchHandled = true;
115
+ ConsumedHandlerLabel = HandlerLabel;
116
+ }
117
+ return bResult;
118
+ };
119
+
120
+ {
121
+ ON_SCOPE_EXIT {
122
+ bProcessingAutomationRequest = false;
123
+ const double DispatchEndSeconds = FPlatformTime::Seconds();
124
+ const double DurationMs =
125
+ (DispatchEndSeconds - DispatchStartSeconds) * 1000.0;
126
+ if (bDispatchHandled) {
127
+ UE_LOG(LogMcpAutomationBridgeSubsystem, Verbose,
128
+ TEXT("ProcessAutomationRequest: Completed handler='%s' "
129
+ "RequestId=%s action='%s' (%.3f ms)"),
130
+ *ConsumedHandlerLabel, *RequestId, *Action, DurationMs);
131
+ } else {
132
+ UE_LOG(LogMcpAutomationBridgeSubsystem, Warning,
133
+ TEXT("ProcessAutomationRequest: No handler consumed "
134
+ "RequestId=%s action='%s' (%.3f ms)"),
135
+ *RequestId, *Action, DurationMs);
136
+ }
137
+
138
+ if (bPendingRequestsScheduled) {
139
+ bPendingRequestsScheduled = false;
140
+ ProcessPendingAutomationRequests();
141
+ }
142
+ };
143
+
144
+ try {
145
+ // Map this requestId to the requesting socket so responses can be
146
+ // delivered reliably
147
+ if (!RequestId.IsEmpty() && RequestingSocket.IsValid() &&
148
+ ConnectionManager.IsValid()) {
149
+ ConnectionManager->RegisterRequestSocket(RequestId, RequestingSocket);
150
+ }
151
+
152
+ // ---------------------------------------------------------
153
+ // Check Handler Registry (O(1) dispatch)
154
+ // ---------------------------------------------------------
155
+ if (const FAutomationHandler *Handler = AutomationHandlers.Find(Action)) {
156
+ if (HandleAndLog(*Action, [&]() {
157
+ return (*Handler)(RequestId, Action, Payload, RequestingSocket);
158
+ })) {
159
+ return;
160
+ }
161
+ }
162
+
163
+ UE_LOG(LogMcpAutomationBridgeSubsystem, Verbose,
164
+ TEXT("ProcessAutomationRequest: Starting handler dispatch for "
165
+ "action='%s'"),
166
+ *Action);
167
+
168
+ // Prioritize blueprint actions early only for blueprint-like actions to
169
+ // avoid noisy prefix logs
170
+ {
171
+ FString LowerNormalized = LowerAction;
172
+ LowerNormalized.ReplaceInline(TEXT("-"), TEXT("_"));
173
+ LowerNormalized.ReplaceInline(TEXT(" "), TEXT("_"));
174
+ const bool bLooksBlueprint =
175
+ (LowerNormalized.StartsWith(TEXT("blueprint_")) ||
176
+ LowerNormalized.StartsWith(TEXT("manage_blueprint")) ||
177
+ LowerNormalized.Contains(TEXT("_scs")) ||
178
+ LowerNormalized.Contains(TEXT("scs_")) ||
179
+ LowerNormalized.Contains(TEXT("scs")));
180
+ if (bLooksBlueprint) {
181
+ UE_LOG(LogMcpAutomationBridgeSubsystem, Verbose,
182
+ TEXT("ProcessAutomationRequest: Checking "
183
+ "HandleBlueprintAction (early)"));
184
+ if (HandleAndLog(TEXT("HandleBlueprintAction (early)"), [&]() {
185
+ return HandleBlueprintAction(RequestId, Action, Payload,
186
+ RequestingSocket);
187
+ })) {
188
+ UE_LOG(LogMcpAutomationBridgeSubsystem, Verbose,
189
+ TEXT("HandleBlueprintAction (early) consumed request"));
190
+ return;
191
+ }
192
+ }
193
+ }
194
+
195
+ // Allow small handlers to short-circuit fast (property/function)
196
+ UE_LOG(LogMcpAutomationBridgeSubsystem, Verbose,
197
+ TEXT("ProcessAutomationRequest: About to call "
198
+ "HandleExecuteEditorFunction"));
199
+ if (HandleAndLog(TEXT("HandleExecuteEditorFunction"), [&]() {
200
+ return HandleExecuteEditorFunction(RequestId, Action, Payload,
201
+ RequestingSocket);
202
+ })) {
203
+ UE_LOG(LogMcpAutomationBridgeSubsystem, Verbose,
204
+ TEXT("HandleExecuteEditorFunction consumed request"));
205
+ return;
206
+ }
207
+ UE_LOG(LogMcpAutomationBridgeSubsystem, Verbose,
208
+ TEXT("ProcessAutomationRequest: HandleExecuteEditorFunction "
209
+ "returned false"));
210
+
211
+ // Level utilities (top-level aliases)
212
+ UE_LOG(LogMcpAutomationBridgeSubsystem, Verbose,
213
+ TEXT("ProcessAutomationRequest: Checking HandleLevelAction"));
214
+ if (HandleAndLog(TEXT("HandleLevelAction"), [&]() {
215
+ return HandleLevelAction(RequestId, Action, Payload,
216
+ RequestingSocket);
217
+ })) {
218
+ UE_LOG(LogMcpAutomationBridgeSubsystem, Verbose,
219
+ TEXT("HandleLevelAction consumed request"));
220
+ return;
221
+ }
222
+
223
+ // Try asset actions early (materials, import, list, rename, etc.)
224
+ UE_LOG(
225
+ LogMcpAutomationBridgeSubsystem, Verbose,
226
+ TEXT("ProcessAutomationRequest: Checking HandleAssetAction (early)"));
227
+ if (HandleAndLog(TEXT("HandleAssetAction (early)"), [&]() {
228
+ return HandleAssetAction(RequestId, Action, Payload,
229
+ RequestingSocket);
230
+ })) {
231
+ UE_LOG(LogMcpAutomationBridgeSubsystem, Verbose,
232
+ TEXT("HandleAssetAction (early) consumed request"));
233
+ return;
234
+ }
235
+ if (HandleAndLog(TEXT("HandleSetObjectProperty"), [&]() {
236
+ return HandleSetObjectProperty(RequestId, Action, Payload,
237
+ RequestingSocket);
238
+ }))
239
+ return;
240
+ if (HandleAndLog(TEXT("HandleGetObjectProperty"), [&]() {
241
+ return HandleGetObjectProperty(RequestId, Action, Payload,
242
+ RequestingSocket);
243
+ }))
244
+ return;
245
+ // Array manipulation operations
246
+ if (HandleAndLog(TEXT("HandleArrayAppend"), [&]() {
247
+ return HandleArrayAppend(RequestId, Action, Payload,
248
+ RequestingSocket);
249
+ }))
250
+ return;
251
+ if (HandleAndLog(TEXT("HandleArrayRemove"), [&]() {
252
+ return HandleArrayRemove(RequestId, Action, Payload,
253
+ RequestingSocket);
254
+ }))
255
+ return;
256
+ if (HandleAndLog(TEXT("HandleArrayInsert"), [&]() {
257
+ return HandleArrayInsert(RequestId, Action, Payload,
258
+ RequestingSocket);
259
+ }))
260
+ return;
261
+ if (HandleAndLog(TEXT("HandleArrayGetElement"), [&]() {
262
+ return HandleArrayGetElement(RequestId, Action, Payload,
263
+ RequestingSocket);
264
+ }))
265
+ return;
266
+ if (HandleAndLog(TEXT("HandleArraySetElement"), [&]() {
267
+ return HandleArraySetElement(RequestId, Action, Payload,
268
+ RequestingSocket);
269
+ }))
270
+ return;
271
+ if (HandleAndLog(TEXT("HandleArrayClear"), [&]() {
272
+ return HandleArrayClear(RequestId, Action, Payload,
273
+ RequestingSocket);
274
+ }))
275
+ return;
276
+ // Map manipulation operations
277
+ if (HandleAndLog(TEXT("HandleMapSetValue"), [&]() {
278
+ return HandleMapSetValue(RequestId, Action, Payload,
279
+ RequestingSocket);
280
+ }))
281
+ return;
282
+ if (HandleAndLog(TEXT("HandleMapGetValue"), [&]() {
283
+ return HandleMapGetValue(RequestId, Action, Payload,
284
+ RequestingSocket);
285
+ }))
286
+ return;
287
+ if (HandleAndLog(TEXT("HandleMapRemoveKey"), [&]() {
288
+ return HandleMapRemoveKey(RequestId, Action, Payload,
289
+ RequestingSocket);
290
+ }))
291
+ return;
292
+ if (HandleAndLog(TEXT("HandleMapHasKey"), [&]() {
293
+ return HandleMapHasKey(RequestId, Action, Payload,
294
+ RequestingSocket);
295
+ }))
296
+ return;
297
+ if (HandleAndLog(TEXT("HandleMapGetKeys"), [&]() {
298
+ return HandleMapGetKeys(RequestId, Action, Payload,
299
+ RequestingSocket);
300
+ }))
301
+ return;
302
+ if (HandleAndLog(TEXT("HandleMapClear"), [&]() {
303
+ return HandleMapClear(RequestId, Action, Payload, RequestingSocket);
304
+ }))
305
+ return;
306
+ // Set manipulation operations
307
+ if (HandleAndLog(TEXT("HandleSetAdd"), [&]() {
308
+ return HandleSetAdd(RequestId, Action, Payload, RequestingSocket);
309
+ }))
310
+ return;
311
+ if (HandleAndLog(TEXT("HandleSetRemove"), [&]() {
312
+ return HandleSetRemove(RequestId, Action, Payload,
313
+ RequestingSocket);
314
+ }))
315
+ return;
316
+ if (HandleAndLog(TEXT("HandleSetContains"), [&]() {
317
+ return HandleSetContains(RequestId, Action, Payload,
318
+ RequestingSocket);
319
+ }))
320
+ return;
321
+ if (HandleAndLog(TEXT("HandleSetClear"), [&]() {
322
+ return HandleSetClear(RequestId, Action, Payload, RequestingSocket);
323
+ }))
324
+ return;
325
+ // Asset dependency graph traversal
326
+ if (HandleAndLog(TEXT("HandleGetAssetReferences"), [&]() {
327
+ return HandleGetAssetReferences(RequestId, Action, Payload,
328
+ RequestingSocket);
329
+ }))
330
+ return;
331
+ if (HandleAndLog(TEXT("HandleGetAssetDependencies"), [&]() {
332
+ return HandleGetAssetDependencies(RequestId, Action, Payload,
333
+ RequestingSocket);
334
+ }))
335
+ return;
336
+ // Asset workflow handlers
337
+ if (HandleAndLog(TEXT("HandleFixupRedirectors"), [&]() {
338
+ return HandleFixupRedirectors(RequestId, Action, Payload,
339
+ RequestingSocket);
340
+ }))
341
+ return;
342
+ if (HandleAndLog(TEXT("HandleSourceControlCheckout"), [&]() {
343
+ return HandleSourceControlCheckout(RequestId, Action, Payload,
344
+ RequestingSocket);
345
+ }))
346
+ return;
347
+ if (HandleAndLog(TEXT("HandleSourceControlSubmit"), [&]() {
348
+ return HandleSourceControlSubmit(RequestId, Action, Payload,
349
+ RequestingSocket);
350
+ }))
351
+ return;
352
+ if (HandleAndLog(TEXT("HandleBulkRenameAssets"), [&]() {
353
+ return HandleBulkRenameAssets(RequestId, Action, Payload,
354
+ RequestingSocket);
355
+ }))
356
+ return;
357
+ if (HandleAndLog(TEXT("HandleBulkDeleteAssets"), [&]() {
358
+ return HandleBulkDeleteAssets(RequestId, Action, Payload,
359
+ RequestingSocket);
360
+ }))
361
+ return;
362
+ if (HandleAndLog(TEXT("HandleGenerateThumbnail"), [&]() {
363
+ return HandleGenerateThumbnail(RequestId, Action, Payload,
364
+ RequestingSocket);
365
+ }))
366
+ return;
367
+ // Landscape operations
368
+ if (HandleAndLog(TEXT("HandleCreateLandscape"), [&]() {
369
+ return HandleCreateLandscape(RequestId, Action, Payload,
370
+ RequestingSocket);
371
+ }))
372
+ return;
373
+ if (HandleAndLog(TEXT("HandleCreateProceduralTerrain"), [&]() {
374
+ return HandleCreateProceduralTerrain(RequestId, Action, Payload,
375
+ RequestingSocket);
376
+ }))
377
+ return;
378
+ if (HandleAndLog(TEXT("HandleCreateLandscapeGrassType"), [&]() {
379
+ return HandleCreateLandscapeGrassType(RequestId, Action, Payload,
380
+ RequestingSocket);
381
+ }))
382
+ return;
383
+ if (HandleAndLog(TEXT("HandleSculptLandscape"), [&]() {
384
+ return HandleSculptLandscape(RequestId, Action, Payload,
385
+ RequestingSocket);
386
+ }))
387
+ return;
388
+ if (HandleAndLog(TEXT("HandleSetLandscapeMaterial"), [&]() {
389
+ return HandleSetLandscapeMaterial(RequestId, Action, Payload,
390
+ RequestingSocket);
391
+ }))
392
+ return;
393
+ if (HandleAndLog(TEXT("HandleEditLandscape"), [&]() {
394
+ return HandleEditLandscape(RequestId, Action, Payload,
395
+ RequestingSocket);
396
+ }))
397
+ return;
398
+ // Foliage operations
399
+ if (HandleAndLog(TEXT("HandleAddFoliageType"), [&]() {
400
+ return HandleAddFoliageType(RequestId, Action, Payload,
401
+ RequestingSocket);
402
+ }))
403
+ return;
404
+ if (HandleAndLog(TEXT("HandleCreateProceduralFoliage"), [&]() {
405
+ return HandleCreateProceduralFoliage(RequestId, Action, Payload,
406
+ RequestingSocket);
407
+ }))
408
+ return;
409
+ if (HandleAndLog(TEXT("HandlePaintFoliage"), [&]() {
410
+ return HandlePaintFoliage(RequestId, Action, Payload,
411
+ RequestingSocket);
412
+ }))
413
+ return;
414
+ if (HandleAndLog(TEXT("HandleAddFoliageInstances"), [&]() {
415
+ return HandleAddFoliageInstances(RequestId, Action, Payload,
416
+ RequestingSocket);
417
+ }))
418
+ return;
419
+ if (HandleAndLog(TEXT("HandleRemoveFoliage"), [&]() {
420
+ return HandleRemoveFoliage(RequestId, Action, Payload,
421
+ RequestingSocket);
422
+ }))
423
+ return;
424
+ if (HandleAndLog(TEXT("HandleGetFoliageInstances"), [&]() {
425
+ return HandleGetFoliageInstances(RequestId, Action, Payload,
426
+ RequestingSocket);
427
+ }))
428
+ return;
429
+ // Niagara operations
430
+ if (HandleAndLog(TEXT("HandleCreateNiagaraSystem"), [&]() {
431
+ return HandleCreateNiagaraSystem(RequestId, Action, Payload,
432
+ RequestingSocket);
433
+ }))
434
+ return;
435
+ if (HandleAndLog(TEXT("HandleCreateNiagaraRibbon"), [&]() {
436
+ return HandleCreateNiagaraRibbon(RequestId, Action, Payload,
437
+ RequestingSocket);
438
+ }))
439
+ return;
440
+ if (HandleAndLog(TEXT("HandleCreateNiagaraEmitter"), [&]() {
441
+ return HandleCreateNiagaraEmitter(RequestId, Action, Payload,
442
+ RequestingSocket);
443
+ }))
444
+ return;
445
+ if (HandleAndLog(TEXT("HandleSpawnNiagaraActor"), [&]() {
446
+ return HandleSpawnNiagaraActor(RequestId, Action, Payload,
447
+ RequestingSocket);
448
+ }))
449
+ return;
450
+ if (HandleAndLog(TEXT("HandleModifyNiagaraParameter"), [&]() {
451
+ return HandleModifyNiagaraParameter(RequestId, Action, Payload,
452
+ RequestingSocket);
453
+ }))
454
+ return;
455
+ // Animation blueprint operations
456
+ if (HandleAndLog(TEXT("HandleCreateAnimBlueprint"), [&]() {
457
+ return HandleCreateAnimBlueprint(RequestId, Action, Payload,
458
+ RequestingSocket);
459
+ }))
460
+ return;
461
+ if (HandleAndLog(TEXT("HandlePlayAnimMontage"), [&]() {
462
+ return HandlePlayAnimMontage(RequestId, Action, Payload,
463
+ RequestingSocket);
464
+ }))
465
+ return;
466
+ if (HandleAndLog(TEXT("HandleSetupRagdoll"), [&]() {
467
+ return HandleSetupRagdoll(RequestId, Action, Payload,
468
+ RequestingSocket);
469
+ }))
470
+ return;
471
+ // Material graph operations
472
+ if (HandleAndLog(TEXT("HandleAddMaterialTextureSample"), [&]() {
473
+ return HandleAddMaterialTextureSample(RequestId, Action, Payload,
474
+ RequestingSocket);
475
+ }))
476
+ return;
477
+ if (HandleAndLog(TEXT("HandleAddMaterialExpression"), [&]() {
478
+ return HandleAddMaterialExpression(RequestId, Action, Payload,
479
+ RequestingSocket);
480
+ }))
481
+ return;
482
+ if (HandleAndLog(TEXT("HandleCreateMaterialNodes"), [&]() {
483
+ return HandleCreateMaterialNodes(RequestId, Action, Payload,
484
+ RequestingSocket);
485
+ }))
486
+ return;
487
+ // Sequencer operations
488
+ if (HandleAndLog(TEXT("HandleAddSequencerKeyframe"), [&]() {
489
+ return HandleAddSequencerKeyframe(RequestId, Action, Payload,
490
+ RequestingSocket);
491
+ }))
492
+ return;
493
+ if (HandleAndLog(TEXT("HandleManageSequencerTrack"), [&]() {
494
+ return HandleManageSequencerTrack(RequestId, Action, Payload,
495
+ RequestingSocket);
496
+ }))
497
+ return;
498
+ if (HandleAndLog(TEXT("HandleAddCameraTrack"), [&]() {
499
+ return HandleAddCameraTrack(RequestId, Action, Payload,
500
+ RequestingSocket);
501
+ }))
502
+ return;
503
+ if (HandleAndLog(TEXT("HandleAddAnimationTrack"), [&]() {
504
+ return HandleAddAnimationTrack(RequestId, Action, Payload,
505
+ RequestingSocket);
506
+ }))
507
+ return;
508
+ if (HandleAndLog(TEXT("HandleAddTransformTrack"), [&]() {
509
+ return HandleAddTransformTrack(RequestId, Action, Payload,
510
+ RequestingSocket);
511
+ }))
512
+ return;
513
+
514
+ // Delegate asset/control/blueprint/sequence actions to their handlers
515
+ UE_LOG(LogMcpAutomationBridgeSubsystem, Verbose,
516
+ TEXT("ProcessAutomationRequest: Checking HandleAssetAction"));
517
+ if (HandleAndLog(TEXT("HandleAssetAction"), [&]() {
518
+ return HandleAssetAction(RequestId, Action, Payload,
519
+ RequestingSocket);
520
+ })) {
521
+ UE_LOG(LogMcpAutomationBridgeSubsystem, Verbose,
522
+ TEXT("HandleAssetAction consumed request"));
523
+ return;
524
+ }
525
+ UE_LOG(
526
+ LogMcpAutomationBridgeSubsystem, Verbose,
527
+ TEXT("ProcessAutomationRequest: Checking HandleControlActorAction"));
528
+ if (HandleAndLog(TEXT("HandleControlActorAction"), [&]() {
529
+ return HandleControlActorAction(RequestId, Action, Payload,
530
+ RequestingSocket);
531
+ })) {
532
+ UE_LOG(LogMcpAutomationBridgeSubsystem, Verbose,
533
+ TEXT("HandleControlActorAction consumed request"));
534
+ return;
535
+ }
536
+ UE_LOG(
537
+ LogMcpAutomationBridgeSubsystem, Verbose,
538
+ TEXT("ProcessAutomationRequest: Checking HandleControlEditorAction"));
539
+ if (HandleAndLog(TEXT("HandleControlEditorAction"), [&]() {
540
+ return HandleControlEditorAction(RequestId, Action, Payload,
541
+ RequestingSocket);
542
+ })) {
543
+ UE_LOG(LogMcpAutomationBridgeSubsystem, Verbose,
544
+ TEXT("HandleControlEditorAction consumed request"));
545
+ return;
546
+ }
547
+ UE_LOG(LogMcpAutomationBridgeSubsystem, Verbose,
548
+ TEXT("ProcessAutomationRequest: Checking HandleUiAction"));
549
+ if (HandleAndLog(TEXT("HandleUiAction"), [&]() {
550
+ return HandleUiAction(RequestId, Action, Payload, RequestingSocket);
551
+ })) {
552
+ UE_LOG(LogMcpAutomationBridgeSubsystem, Verbose,
553
+ TEXT("HandleUiAction consumed request"));
554
+ return;
555
+ }
556
+ UE_LOG(LogMcpAutomationBridgeSubsystem, Verbose,
557
+ TEXT("ProcessAutomationRequest: Checking HandleBlueprintAction "
558
+ "(late)"));
559
+ if (HandleAndLog(TEXT("HandleBlueprintAction (late)"), [&]() {
560
+ return HandleBlueprintAction(RequestId, Action, Payload,
561
+ RequestingSocket);
562
+ })) {
563
+ UE_LOG(LogMcpAutomationBridgeSubsystem, Verbose,
564
+ TEXT("HandleBlueprintAction (late) consumed request"));
565
+ return;
566
+ }
567
+ UE_LOG(LogMcpAutomationBridgeSubsystem, Verbose,
568
+ TEXT("ProcessAutomationRequest: Checking HandleSequenceAction"));
569
+ if (HandleAndLog(TEXT("HandleSequenceAction"), [&]() {
570
+ return HandleSequenceAction(RequestId, Action, Payload,
571
+ RequestingSocket);
572
+ })) {
573
+ UE_LOG(LogMcpAutomationBridgeSubsystem, Verbose,
574
+ TEXT("HandleSequenceAction consumed request"));
575
+ return;
576
+ }
577
+ if (HandleAndLog(TEXT("HandleEffectAction"), [&]() {
578
+ return HandleEffectAction(RequestId, Action, Payload,
579
+ RequestingSocket);
580
+ }))
581
+ return;
582
+ UE_LOG(LogMcpAutomationBridgeSubsystem, Verbose,
583
+ TEXT("ProcessAutomationRequest: Checking "
584
+ "HandleAnimationPhysicsAction"));
585
+ if (HandleAndLog(TEXT("HandleAnimationPhysicsAction"), [&]() {
586
+ return HandleAnimationPhysicsAction(RequestId, Action, Payload,
587
+ RequestingSocket);
588
+ })) {
589
+ UE_LOG(LogMcpAutomationBridgeSubsystem, Verbose,
590
+ TEXT("HandleAnimationPhysicsAction consumed request"));
591
+ return;
592
+ }
593
+ if (HandleAndLog(TEXT("HandleAudioAction"), [&]() {
594
+ return HandleAudioAction(RequestId, Action, Payload,
595
+ RequestingSocket);
596
+ }))
597
+ return;
598
+ if (HandleAndLog(TEXT("HandleLightingAction"), [&]() {
599
+ return HandleLightingAction(RequestId, Action, Payload,
600
+ RequestingSocket);
601
+ }))
602
+ return;
603
+ if (HandleAndLog(TEXT("HandlePerformanceAction"), [&]() {
604
+ return HandlePerformanceAction(RequestId, Action, Payload,
605
+ RequestingSocket);
606
+ }))
607
+ return;
608
+ if (HandleAndLog(TEXT("HandleBuildEnvironmentAction"), [&]() {
609
+ return HandleBuildEnvironmentAction(RequestId, Action, Payload,
610
+ RequestingSocket);
611
+ }))
612
+ return;
613
+ if (HandleAndLog(TEXT("HandleControlEnvironmentAction"), [&]() {
614
+ return HandleControlEnvironmentAction(RequestId, Action, Payload,
615
+ RequestingSocket);
616
+ }))
617
+ return;
618
+
619
+ // Additional consolidated tool handlers
620
+ if (HandleAndLog(TEXT("HandleSystemControlAction"), [&]() {
621
+ return HandleSystemControlAction(RequestId, Action, Payload,
622
+ RequestingSocket);
623
+ }))
624
+ return;
625
+ if (HandleAndLog(TEXT("HandleConsoleCommandAction"), [&]() {
626
+ return HandleConsoleCommandAction(RequestId, Action, Payload,
627
+ RequestingSocket);
628
+ }))
629
+ return;
630
+ if (HandleAndLog(TEXT("HandleInspectAction"), [&]() {
631
+ return HandleInspectAction(RequestId, Action, Payload,
632
+ RequestingSocket);
633
+ }))
634
+ return;
635
+
636
+ // 1. Editor Authoring & Graph Editing
637
+ if (HandleAndLog(TEXT("HandleBlueprintGraphAction"), [&]() {
638
+ return HandleBlueprintGraphAction(RequestId, Action, Payload,
639
+ RequestingSocket);
640
+ }))
641
+ return;
642
+ if (HandleAndLog(TEXT("HandleNiagaraGraphAction"), [&]() {
643
+ return HandleNiagaraGraphAction(RequestId, Action, Payload,
644
+ RequestingSocket);
645
+ }))
646
+ return;
647
+ if (HandleAndLog(TEXT("HandleMaterialGraphAction"), [&]() {
648
+ return HandleMaterialGraphAction(RequestId, Action, Payload,
649
+ RequestingSocket);
650
+ }))
651
+ return;
652
+ if (HandleAndLog(TEXT("HandleBehaviorTreeAction"), [&]() {
653
+ return HandleBehaviorTreeAction(RequestId, Action, Payload,
654
+ RequestingSocket);
655
+ }))
656
+ return;
657
+ if (HandleAndLog(TEXT("HandleWorldPartitionAction"), [&]() {
658
+ return HandleWorldPartitionAction(RequestId, Action, Payload,
659
+ RequestingSocket);
660
+ }))
661
+ return;
662
+ if (HandleAndLog(TEXT("HandleRenderAction"), [&]() {
663
+ return HandleRenderAction(RequestId, Action, Payload,
664
+ RequestingSocket);
665
+ }))
666
+ return;
667
+
668
+ // 2. Execution & Build / Test Pipeline
669
+ if (HandleAndLog(TEXT("HandlePipelineAction"), [&]() {
670
+ return HandlePipelineAction(RequestId, Action, Payload,
671
+ RequestingSocket);
672
+ }))
673
+ return;
674
+ if (HandleAndLog(TEXT("HandleTestAction"), [&]() {
675
+ return HandleTestAction(RequestId, Action, Payload,
676
+ RequestingSocket);
677
+ }))
678
+ return;
679
+
680
+ // 3. Observability, Logs, Debugging & History
681
+ if (HandleAndLog(TEXT("HandleLogAction"), [&]() {
682
+ return HandleLogAction(RequestId, Action, Payload,
683
+ RequestingSocket);
684
+ }))
685
+ return;
686
+ if (HandleAndLog(TEXT("HandleDebugAction"), [&]() {
687
+ return HandleDebugAction(RequestId, Action, Payload,
688
+ RequestingSocket);
689
+ }))
690
+ return;
691
+ if (HandleAndLog(TEXT("HandleAssetQueryAction"), [&]() {
692
+ return HandleAssetQueryAction(RequestId, Action, Payload,
693
+ RequestingSocket);
694
+ }))
695
+ return;
696
+ if (HandleAndLog(TEXT("HandleInsightsAction"), [&]() {
697
+ return HandleInsightsAction(RequestId, Action, Payload,
698
+ RequestingSocket);
699
+ }))
700
+ return;
701
+
702
+ // Unhandled action
703
+ bDispatchHandled = true;
704
+ ConsumedHandlerLabel = TEXT("SendAutomationError (unknown action)");
705
+ SendAutomationError(
706
+ RequestingSocket, RequestId,
707
+ FString::Printf(TEXT("Unknown automation action: %s"), *Action),
708
+ TEXT("UNKNOWN_ACTION"));
709
+ } catch (const std::exception &E) {
710
+ UE_LOG(LogMcpAutomationBridgeSubsystem, Error,
711
+ TEXT("Unhandled exception processing automation request %s: %s"),
712
+ *RequestId, ANSI_TO_TCHAR(E.what()));
713
+ bDispatchHandled = true;
714
+ ConsumedHandlerLabel = TEXT("Exception handler");
715
+ SendAutomationError(
716
+ RequestingSocket, RequestId,
717
+ FString::Printf(TEXT("Internal error: %s"), ANSI_TO_TCHAR(E.what())),
718
+ TEXT("INTERNAL_ERROR"));
719
+ } catch (...) {
720
+ UE_LOG(
721
+ LogMcpAutomationBridgeSubsystem, Error,
722
+ TEXT("Unhandled unknown exception processing automation request %s"),
723
+ *RequestId);
724
+ bDispatchHandled = true;
725
+ ConsumedHandlerLabel = TEXT("Exception handler (unknown)");
726
+ SendAutomationError(RequestingSocket, RequestId,
727
+ TEXT("Internal error (unknown)."),
728
+ TEXT("INTERNAL_ERROR"));
729
+ }
730
+ }
731
+ }
732
+
733
+ // ProcessPendingAutomationRequests() intentionally implemented in the
734
+ // primary subsystem translation unit (McpAutomationBridgeSubsystem.cpp)
735
+ // to ensure the linker emits the symbol into the module's object file.