@akiojin/unity-mcp-server 2.16.0 → 2.25.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 (135) hide show
  1. package/LICENSE +0 -0
  2. package/README.md +153 -100
  3. package/bin/unity-mcp-server +7 -1
  4. package/package.json +30 -7
  5. package/src/core/codeIndex.js +0 -0
  6. package/src/core/codeIndexDb.js +0 -0
  7. package/src/core/config.js +47 -14
  8. package/src/core/indexWatcher.js +84 -15
  9. package/src/core/jobManager.js +178 -0
  10. package/src/core/projectInfo.js +21 -67
  11. package/src/core/server.js +15 -2
  12. package/src/core/unityConnection.js +0 -0
  13. package/src/handlers/addressables/AddressablesAnalyzeToolHandler.js +170 -0
  14. package/src/handlers/addressables/AddressablesBuildToolHandler.js +145 -0
  15. package/src/handlers/addressables/AddressablesManageToolHandler.js +266 -0
  16. package/src/handlers/analysis/AnalyzeSceneContentsToolHandler.js +1 -1
  17. package/src/handlers/analysis/FindByComponentToolHandler.js +2 -2
  18. package/src/handlers/analysis/GetAnimatorStateToolHandler.js +1 -1
  19. package/src/handlers/analysis/GetComponentValuesToolHandler.js +2 -2
  20. package/src/handlers/analysis/GetGameObjectDetailsToolHandler.js +1 -1
  21. package/src/handlers/analysis/GetInputActionsStateToolHandler.js +1 -1
  22. package/src/handlers/analysis/GetObjectReferencesToolHandler.js +2 -2
  23. package/src/handlers/asset/{AssetDatabaseToolHandler.js → AssetDatabaseManageToolHandler.js} +2 -2
  24. package/src/handlers/asset/{AssetDependencyToolHandler.js → AssetDependencyAnalyzeToolHandler.js} +2 -2
  25. package/src/handlers/asset/{AssetImportSettingsToolHandler.js → AssetImportSettingsManageToolHandler.js} +2 -2
  26. package/src/handlers/asset/{CreateMaterialToolHandler.js → AssetMaterialCreateToolHandler.js} +2 -2
  27. package/src/handlers/asset/{ModifyMaterialToolHandler.js → AssetMaterialModifyToolHandler.js} +2 -2
  28. package/src/handlers/asset/{CreatePrefabToolHandler.js → AssetPrefabCreateToolHandler.js} +2 -2
  29. package/src/handlers/asset/{ExitPrefabModeToolHandler.js → AssetPrefabExitModeToolHandler.js} +2 -2
  30. package/src/handlers/asset/{InstantiatePrefabToolHandler.js → AssetPrefabInstantiateToolHandler.js} +2 -2
  31. package/src/handlers/asset/{ModifyPrefabToolHandler.js → AssetPrefabModifyToolHandler.js} +2 -2
  32. package/src/handlers/asset/{OpenPrefabToolHandler.js → AssetPrefabOpenToolHandler.js} +2 -2
  33. package/src/handlers/asset/{SavePrefabToolHandler.js → AssetPrefabSaveToolHandler.js} +2 -2
  34. package/src/handlers/base/BaseToolHandler.js +0 -0
  35. package/src/handlers/compilation/{GetCompilationStateToolHandler.js → CompilationGetStateToolHandler.js} +2 -2
  36. package/src/handlers/component/{AddComponentToolHandler.js → ComponentAddToolHandler.js} +2 -2
  37. package/src/handlers/component/ComponentFieldSetToolHandler.js +419 -0
  38. package/src/handlers/component/{GetComponentTypesToolHandler.js → ComponentGetTypesToolHandler.js} +2 -2
  39. package/src/handlers/component/{ListComponentsToolHandler.js → ComponentListToolHandler.js} +2 -2
  40. package/src/handlers/component/{ModifyComponentToolHandler.js → ComponentModifyToolHandler.js} +2 -2
  41. package/src/handlers/component/{RemoveComponentToolHandler.js → ComponentRemoveToolHandler.js} +2 -2
  42. package/src/handlers/console/{ClearConsoleToolHandler.js → ConsoleClearToolHandler.js} +2 -2
  43. package/src/handlers/console/{ReadConsoleToolHandler.js → ConsoleReadToolHandler.js} +83 -64
  44. package/src/handlers/editor/{LayerManagementToolHandler.js → EditorLayersManageToolHandler.js} +2 -2
  45. package/src/handlers/editor/{SelectionToolHandler.js → EditorSelectionManageToolHandler.js} +2 -2
  46. package/src/handlers/editor/{TagManagementToolHandler.js → EditorTagsManageToolHandler.js} +2 -2
  47. package/src/handlers/editor/{ToolManagementToolHandler.js → EditorToolsManageToolHandler.js} +2 -2
  48. package/src/handlers/editor/{WindowManagementToolHandler.js → EditorWindowsManageToolHandler.js} +2 -2
  49. package/src/handlers/gameobject/{CreateGameObjectToolHandler.js → GameObjectCreateToolHandler.js} +3 -3
  50. package/src/handlers/gameobject/{DeleteGameObjectToolHandler.js → GameObjectDeleteToolHandler.js} +3 -3
  51. package/src/handlers/gameobject/{FindGameObjectToolHandler.js → GameObjectFindToolHandler.js} +3 -3
  52. package/src/handlers/gameobject/{GetHierarchyToolHandler.js → GameObjectGetHierarchyToolHandler.js} +3 -3
  53. package/src/handlers/gameobject/{ModifyGameObjectToolHandler.js → GameObjectModifyToolHandler.js} +3 -3
  54. package/src/handlers/index.js +331 -293
  55. package/src/handlers/input/{AddInputActionToolHandler.js → InputActionAddToolHandler.js} +2 -2
  56. package/src/handlers/input/{CreateActionMapToolHandler.js → InputActionMapCreateToolHandler.js} +2 -2
  57. package/src/handlers/input/{RemoveActionMapToolHandler.js → InputActionMapRemoveToolHandler.js} +2 -2
  58. package/src/handlers/input/{RemoveInputActionToolHandler.js → InputActionRemoveToolHandler.js} +2 -2
  59. package/src/handlers/input/{AddInputBindingToolHandler.js → InputBindingAddToolHandler.js} +2 -2
  60. package/src/handlers/input/{CreateCompositeBindingToolHandler.js → InputBindingCompositeCreateToolHandler.js} +2 -2
  61. package/src/handlers/input/{RemoveAllBindingsToolHandler.js → InputBindingRemoveAllToolHandler.js} +2 -2
  62. package/src/handlers/input/{RemoveInputBindingToolHandler.js → InputBindingRemoveToolHandler.js} +2 -2
  63. package/src/handlers/input/{ManageControlSchemesToolHandler.js → InputControlSchemesManageToolHandler.js} +2 -2
  64. package/src/handlers/input/{GamepadSimulationHandler.js → InputGamepadSimulateToolHandler.js} +3 -3
  65. package/src/handlers/input/{KeyboardSimulationHandler.js → InputKeyboardSimulateToolHandler.js} +3 -3
  66. package/src/handlers/input/{MouseSimulationHandler.js → InputMouseSimulateToolHandler.js} +3 -3
  67. package/src/handlers/input/{InputSystemHandler.js → InputSystemControlToolHandler.js} +4 -4
  68. package/src/handlers/input/{TouchSimulationHandler.js → InputTouchSimulateToolHandler.js} +3 -3
  69. package/src/handlers/menu/{ExecuteMenuItemToolHandler.js → MenuItemExecuteToolHandler.js} +2 -2
  70. package/src/handlers/package/PackageManagerToolHandler.js +1 -1
  71. package/src/handlers/package/RegistryConfigToolHandler.js +1 -1
  72. package/src/handlers/playmode/{GetEditorStateToolHandler.js → PlaymodeGetStateToolHandler.js} +3 -3
  73. package/src/handlers/playmode/{PauseToolHandler.js → PlaymodePauseToolHandler.js} +4 -4
  74. package/src/handlers/playmode/{PlayToolHandler.js → PlaymodePlayToolHandler.js} +4 -4
  75. package/src/handlers/playmode/{StopToolHandler.js → PlaymodeStopToolHandler.js} +4 -4
  76. package/src/handlers/playmode/{WaitForEditorStateToolHandler.js → PlaymodeWaitForStateToolHandler.js} +3 -3
  77. package/src/handlers/scene/GetSceneInfoToolHandler.js +1 -1
  78. package/src/handlers/scene/{CreateSceneToolHandler.js → SceneCreateToolHandler.js} +2 -2
  79. package/src/handlers/scene/{ListScenesToolHandler.js → SceneListToolHandler.js} +2 -2
  80. package/src/handlers/scene/{LoadSceneToolHandler.js → SceneLoadToolHandler.js} +2 -2
  81. package/src/handlers/scene/{SaveSceneToolHandler.js → SceneSaveToolHandler.js} +2 -2
  82. package/src/handlers/screenshot/{AnalyzeScreenshotToolHandler.js → ScreenshotAnalyzeToolHandler.js} +2 -2
  83. package/src/handlers/screenshot/{CaptureScreenshotToolHandler.js → ScreenshotCaptureToolHandler.js} +2 -2
  84. package/src/handlers/script/{BuildCodeIndexToolHandler.js → CodeIndexBuildToolHandler.js} +127 -17
  85. package/src/handlers/script/CodeIndexStatusToolHandler.js +129 -0
  86. package/src/handlers/script/CodeIndexUpdateToolHandler.js +234 -0
  87. package/src/handlers/script/{ScriptCreateClassFileToolHandler.js → ScriptCreateClassToolHandler.js} +2 -2
  88. package/src/handlers/script/ScriptEditSnippetToolHandler.js +272 -0
  89. package/src/handlers/script/ScriptEditStructuredToolHandler.js +1 -1
  90. package/src/handlers/script/ScriptPackagesListToolHandler.js +0 -0
  91. package/src/handlers/script/ScriptReadToolHandler.js +0 -0
  92. package/src/handlers/script/ScriptRefactorRenameToolHandler.js +0 -0
  93. package/src/handlers/script/ScriptRefsFindToolHandler.js +0 -0
  94. package/src/handlers/script/ScriptRemoveSymbolToolHandler.js +0 -0
  95. package/src/handlers/script/ScriptSearchToolHandler.js +0 -0
  96. package/src/handlers/script/ScriptSymbolFindToolHandler.js +0 -0
  97. package/src/handlers/script/ScriptSymbolsGetToolHandler.js +0 -0
  98. package/src/handlers/settings/{GetProjectSettingsToolHandler.js → SettingsGetToolHandler.js} +2 -2
  99. package/src/handlers/settings/{UpdateProjectSettingsToolHandler.js → SettingsUpdateToolHandler.js} +2 -2
  100. package/src/handlers/system/{GetCommandStatsToolHandler.js → SystemGetCommandStatsToolHandler.js} +2 -3
  101. package/src/handlers/system/{PingToolHandler.js → SystemPingToolHandler.js} +3 -3
  102. package/src/handlers/system/{RefreshAssetsToolHandler.js → SystemRefreshAssetsToolHandler.js} +3 -3
  103. package/src/handlers/test/{GetTestStatusToolHandler.js → TestGetStatusToolHandler.js} +2 -2
  104. package/src/handlers/test/{RunTestsToolHandler.js → TestRunToolHandler.js} +2 -2
  105. package/src/handlers/ui/{ClickUIElementToolHandler.js → UIClickElementToolHandler.js} +2 -2
  106. package/src/handlers/ui/{FindUIElementsToolHandler.js → UIFindElementsToolHandler.js} +2 -2
  107. package/src/handlers/ui/{GetUIElementStateToolHandler.js → UIGetElementStateToolHandler.js} +2 -2
  108. package/src/handlers/ui/{SetUIElementValueToolHandler.js → UISetElementValueToolHandler.js} +2 -2
  109. package/src/handlers/ui/{SimulateUIInputToolHandler.js → UISimulateInputToolHandler.js} +2 -2
  110. package/src/handlers/video/{CaptureVideoForToolHandler.js → VideoCaptureForToolHandler.js} +8 -8
  111. package/src/handlers/video/{CaptureVideoStartToolHandler.js → VideoCaptureStartToolHandler.js} +2 -2
  112. package/src/handlers/video/{CaptureVideoStatusToolHandler.js → VideoCaptureStatusToolHandler.js} +2 -2
  113. package/src/handlers/video/{CaptureVideoStopToolHandler.js → VideoCaptureStopToolHandler.js} +3 -3
  114. package/src/lsp/CSharpLspUtils.js +95 -14
  115. package/src/lsp/LspProcessManager.js +0 -0
  116. package/src/lsp/LspRpcClient.js +14 -0
  117. package/src/tools/analysis/analyzeSceneContents.js +3 -3
  118. package/src/tools/analysis/findByComponent.js +3 -3
  119. package/src/tools/analysis/getAnimatorState.js +6 -6
  120. package/src/tools/analysis/getComponentValues.js +3 -3
  121. package/src/tools/analysis/getGameObjectDetails.js +3 -3
  122. package/src/tools/analysis/getInputActionsState.js +4 -4
  123. package/src/tools/analysis/getObjectReferences.js +3 -3
  124. package/src/tools/input/inputActionsEditor.js +18 -18
  125. package/src/tools/scene/createScene.js +3 -3
  126. package/src/tools/scene/getSceneInfo.js +3 -3
  127. package/src/tools/scene/listScenes.js +3 -3
  128. package/src/tools/scene/loadScene.js +3 -3
  129. package/src/tools/scene/saveScene.js +3 -3
  130. package/src/tools/system/ping.js +5 -5
  131. package/src/tools/video/recordFor.js +2 -2
  132. package/src/tools/video/recordPlayMode.js +0 -0
  133. package/src/utils/csharpParse.js +0 -0
  134. package/src/utils/validators.js +0 -0
  135. package/src/handlers/script/ScriptIndexStatusToolHandler.js +0 -61
package/LICENSE CHANGED
File without changes
package/README.md CHANGED
@@ -74,105 +74,158 @@ Add to your `claude_desktop_config.json`:
74
74
  }
75
75
  ```
76
76
 
77
- ## Available Tools (70 Tools)
78
-
79
- ### System & Core Tools (2 tools)
80
- - `ping` - Test connection to Unity Editor and verify server status
81
- - `refresh_assets` - Refresh Unity assets and trigger recompilation
82
-
83
- ### GameObject Management (5 tools)
84
- - `create_gameobject` - Create GameObjects with primitives, transforms, tags, and layers
85
- - `find_gameobject` - Find GameObjects by name, tag, layer with pattern matching
86
- - `modify_gameobject` - Modify GameObject properties (transform, name, active state, parent)
87
- - `delete_gameobject` - Delete single or multiple GameObjects with child handling
88
- - `get_hierarchy` - Get scene hierarchy with components and depth control
89
-
90
- ### Component System (5 tools)
91
- - `add_component` - Add Unity components to GameObjects with initial properties
92
- - `remove_component` - Remove components from GameObjects with safety checks
93
- - `modify_component` - Modify component properties with nested property support
94
- - `list_components` - List all components on a GameObject with type information
95
- - `get_component_types` - Discover available component types with filtering
96
-
97
- ### Scene Management (5 tools)
98
- - `create_scene` - Create new scenes with build settings integration
99
- - `load_scene` - Load scenes in Single or Additive mode
100
- - `save_scene` - Save current scene with Save As functionality
101
- - `list_scenes` - List all scenes in project with filtering options
102
- - `get_scene_info` - Get detailed scene information including GameObject counts
103
-
104
- ### Scene Analysis (7 tools)
105
- - `get_gameobject_details` - Deep inspection of GameObjects with component details
106
- - `analyze_scene_contents` - Comprehensive scene statistics and performance metrics
107
- - `get_component_values` - Get all properties and values of specific components
108
- - `find_by_component` - Find GameObjects by component type with scope filtering
109
- - `get_object_references` - Analyze references between objects and assets
110
- - `get_animator_state` - Get current Animator state, parameters, and transitions
111
- - `get_animator_runtime_info` - Get runtime Animator info (Play mode only)
112
-
113
- ### Asset Management (11 tools)
114
- - `create_prefab` - Create prefabs from GameObjects or templates
115
- - `modify_prefab` - Modify existing prefabs with property changes
116
- - `instantiate_prefab` - Instantiate prefabs in scenes with transform options
117
- - `open_prefab` - Open prefabs in Unity's prefab mode for editing
118
- - `exit_prefab_mode` - Exit prefab mode with save/discard options
119
- - `save_prefab` - Save prefab changes or apply instance overrides
120
- - `create_material` - Create new materials with shader and properties
121
- - `modify_material` - Modify material properties and shaders
122
- - `manage_asset_import_settings` - Manage asset import settings and presets
123
- - `manage_asset_database` - Asset database operations (find, move, copy, delete)
124
- - `analyze_asset_dependencies` - Analyze asset dependencies and find unused assets
125
-
126
- ### Script Management (6 tools)
127
- - `create_script` - Create new C# scripts with templates (MonoBehaviour, ScriptableObject, etc.)
128
- - `read_script` - Read script file contents with syntax highlighting
129
- - `update_script` - Modify existing scripts with validation
130
- - `delete_script` - Delete script files with dependency checking
131
- - `list_scripts` - List all scripts in project with filtering and metadata
132
- - `validate_script` - Validate script syntax and Unity compatibility
133
-
134
- ### Play Mode Controls (4 tools)
135
- - `play_game` - Start Unity play mode for testing
136
- - `pause_game` - Pause or resume Unity play mode
137
- - `stop_game` - Stop Unity play mode and return to edit mode
138
- - `get_editor_state` - Get current editor state and compilation status
139
-
140
- ### UI Automation (5 tools)
141
- - `find_ui_elements` - Locate UI elements by type, tag, or name
142
- - `click_ui_element` - Simulate clicking on UI elements (buttons, toggles)
143
- - `get_ui_element_state` - Get UI element properties and interaction state
144
- - `set_ui_element_value` - Set values for input fields, sliders, dropdowns
145
- - `simulate_ui_input` - Execute complex UI interaction sequences
146
-
147
- ### Input System Simulation (5 tools)
148
- - `simulate_keyboard` - Simulate keyboard input with key combos and text typing
149
- - `simulate_mouse` - Simulate mouse movement, clicks, drags, and scrolling
150
- - `simulate_gamepad` - Simulate gamepad buttons, sticks, triggers, and d-pad
151
- - `simulate_touch` - Simulate touch gestures (tap, swipe, pinch, multi-touch)
152
- - `get_current_input_state` - Get current state of all input devices
153
-
154
- ### Editor Operations (5 tools)
155
- - `execute_menu_item` - Execute Unity menu items programmatically
156
- - `clear_console` - Clear Unity console logs with filtering options
157
- - `read_console` - Read console logs with advanced filtering and search
158
- - `capture_screenshot` - Take screenshots of Game View or Scene View
159
- - `analyze_screenshot` - Analyze screenshot content with image analysis
160
-
161
- ### Editor Control & Automation (6 tools)
162
- - `manage_tags` - Manage Unity project tags (add, remove, list)
163
- - `manage_layers` - Manage Unity project layers with index conversion
164
- - `manage_selection` - Manage Editor selection (get, set, clear)
165
- - `manage_windows` - Manage Editor windows (list, focus, get state)
166
- - `manage_tools` - Manage Editor tools and plugins
167
- - `get_compilation_state` - Get current compilation state and errors
168
-
169
- ### Project Settings Management (2 tools)
170
- - `get_project_settings` - Read Unity project settings with granular control
171
- - Player, Graphics, Quality, Physics, Audio, Time settings
172
- - Build settings, Tags and layers configuration
173
- - `update_project_settings` - Safely update project settings
174
- - Requires explicit confirmation for safety
175
- - Supports partial updates to specific categories
77
+ ## Code Index Workflow
78
+
79
+ コードの自動編集を安定させるには、以下の 3 ステップでコードインデックスを運用してください。重いフルテストを回す必要はありません。
80
+
81
+ 1. **初回または大幅変更後に `code_index_build`**
82
+ プロジェクト内の `Assets/` と `Packages/` の C# をすべてスキャンし、`.unity/cache/code-index/code-index.db` にシンボルを格納します。
83
+ 2. **ファイル更新後は `code_index_update`**
84
+ 編集したファイルだけを配列で渡すと、LSP から最新シンボルを再取得してインデックスを差分更新します。長時間待ちになる `code_index_build` の再実行を避けられます。
85
+ 3. **シンボル取得時は `script_symbol_find`**
86
+ インデックスが利用可能なら高速に、未構築でも LSP にフォールバックして定義位置を取得できます。`script_edit_*` ツールに渡す `symbolName` 構築に活用してください。
87
+
88
+ > **Tip:** `code_index_update` JSON パラメータ `paths` に絶対パス/相対パスの配列を渡すだけで完了します。内部で存在チェックと LSP リトライを行うため、Unity を起動したままでも短時間で終わります。
89
+
90
+ ### インデックス状態を検証したいとき
91
+
92
+ ビルド中・未構築・完了後といったステータスを再現したい場合は、`code_index_build` `delayStartMs` `throttleMs` を付けて進捗を意図的に保ちます。さらに、`npm run simulate:code-index` を実行すると以下が自動化されます。
93
+
94
+ - 既存インデックスのリセット(`--reset`)
95
+ - `code_index_build` のバックグラウンド実行(任意の `--delayStart=MS` / `--throttle=MS`)
96
+ - 指定間隔での `code_index_status` ポーリング(`--poll=MS`)
97
+
98
+ 出力される JSON を追うことで、`ready: false` `true` へ遷移する様子や `buildJob.status` の変化を簡単に確認できます。
99
+
100
+ ## Available Tools (Standardized Names)
101
+
102
+ ### System & Core Tools
103
+ - `system_ping` — Test connection to Unity Editor and verify server status
104
+ - `system_refresh_assets` Refresh Unity assets and trigger recompilation
105
+ - `system_get_command_stats` Retrieve recent MCP command usage metrics
106
+
107
+ ### GameObject Management
108
+ - `gameobject_create` Create GameObjects with primitives, transforms, tags, and layers
109
+ - `gameobject_find` Find GameObjects by name, tag, or layer with pattern matching
110
+ - `gameobject_modify` Modify GameObject properties (transform, name, active state, parent)
111
+ - `gameobject_delete` Delete single or multiple GameObjects with child handling
112
+ - `gameobject_get_hierarchy` — Inspect scene hierarchy with component details
113
+
114
+ ### Component System
115
+ - `component_add` Add Unity components to GameObjects with initial properties
116
+ - `component_remove` Remove components from GameObjects with safety checks
117
+ - `component_modify` Modify component properties with nested support
118
+ - `component_field_set` Update serialized fields (including private `[SerializeField]` values, arrays, and nested structs)
119
+ - `component_list` List all components on a GameObject with type information
120
+ - `component_get_types` Discover available component types with filtering
121
+
122
+ ### Scene Management
123
+ - `scene_create` Create new scenes with build-settings integration
124
+ - `scene_load` Load scenes in Single or Additive mode
125
+ - `scene_save` — Save the active scene (supports Save As)
126
+ - `scene_list` List scenes in the project with filtering options
127
+ - `scene_info_get` Retrieve detailed scene information including GameObject counts
128
+
129
+ ### Analysis & Diagnostics
130
+ - `analysis_scene_contents_analyze` Gather scene statistics and performance metrics
131
+ - `analysis_component_find` Locate GameObjects by component type with scope filtering
132
+ - `analysis_component_values_get` Inspect component properties and values
133
+ - `analysis_gameobject_details_get` — Deep inspection of GameObjects and components
134
+ - `analysis_object_references_get` Trace references between objects and assets
135
+ - `analysis_animator_state_get` Inspect Animator layers, parameters, and transitions
136
+ - `analysis_animator_runtime_info_get` Retrieve runtime Animator diagnostics (Play Mode)
137
+
138
+ ### Asset Management
139
+ - `asset_prefab_create` — Create prefabs from GameObjects or blank templates
140
+ - `asset_prefab_instantiate` Instantiate prefabs with custom transforms
141
+ - `asset_prefab_modify` Apply property overrides to existing prefabs
142
+ - `asset_prefab_open` Open prefabs in Prefab Mode for editing
143
+ - `asset_prefab_exit_mode` Exit Prefab Mode with save/discard handling
144
+ - `asset_prefab_save` Save prefab changes or apply instance overrides
145
+ - `asset_material_create` Create materials with shader and property setup
146
+ - `asset_material_modify` — Update material properties and shaders
147
+ - `asset_import_settings_manage` Inspect or modify asset-import settings and presets
148
+ - `asset_database_manage` Perform asset database operations (find, move, copy, delete)
149
+ - `asset_dependency_analyze` Audit asset dependencies and identify unused assets
150
+
151
+ ### Script & Code Tools
152
+ - `script_read` Read script file contents with syntax-aware formatting
153
+ - `script_search` — Search C# sources by substring/regex/glob filters
154
+ - `script_symbols_get` Enumerate symbols within a specific C# file
155
+ - `script_symbol_find` Locate symbol definitions across the project
156
+ - `script_refs_find` List references/usages for a symbol via C# LSP
157
+ - `script_edit_snippet` Apply small text edits within C# files
158
+ - `script_edit_structured` Perform structured symbol edits via C# LSP extensions
159
+ - `script_create_class` Generate a new C# class file from parameters
160
+ - `script_remove_symbol` — Delete symbols (types/members) with reference checks
161
+ - `script_refactor_rename` Rename symbols project-wide via LSP
162
+ - `script_packages_list` List installed packages relevant to scripting
163
+ - `code_index_status` Report status of the persistent code index
164
+
165
+ ### Code Index Utilities
166
+ - `code_index_build` フルスキャンでシンボルインデックスを再構築(開発時は `delayStartMs` `throttleMs` で進捗観測用に速度調整可能)
167
+ - `code_index_update` 変更した C# ファイルのみ差分再インデックス
168
+
169
+ ### Play Mode Controls
170
+ - `playmode_play` Enter Play Mode
171
+ - `playmode_pause` Pause or resume Play Mode
172
+ - `playmode_stop` Exit Play Mode back to Edit Mode
173
+ - `playmode_get_state` Inspect current play/edit/compilation state
174
+ - `playmode_wait_for_state` Await a target play/edit state
175
+
176
+ ### UI Automation
177
+ - `ui_find_elements` — Locate UI elements by type, tag, or name
178
+ - `ui_click_element` — Simulate clicking UI buttons, toggles, etc.
179
+ - `ui_get_element_state` — Inspect UI element properties and interactability
180
+ - `ui_set_element_value` — Modify UI input values (sliders, fields, dropdowns)
181
+ - `ui_simulate_input` — Execute complex multi-step UI interaction sequences
182
+
183
+ ### Input System Utilities
184
+ - `input_system_control` — Dispatch keyboard/mouse/gamepad/touch operations
185
+ - `input_keyboard_simulate` — Simulate keyboard input with combos or text
186
+ - `input_mouse_simulate` — Simulate mouse movement, clicks, drags, and scrolling
187
+ - `input_gamepad_simulate` — Simulate gamepad buttons, sticks, and triggers
188
+ - `input_touch_simulate` — Simulate touch gestures (tap, swipe, pinch)
189
+ - `input_action_add` — Add actions to an Input Action map
190
+ - `input_action_remove` — Remove actions from an Input Action map
191
+ - `input_action_map_create` — Create new Input Action maps
192
+ - `input_action_map_remove` — Delete existing Input Action maps
193
+ - `input_binding_add` — Add bindings to an action (including composites)
194
+ - `input_binding_remove` — Remove a specific binding from an action
195
+ - `input_binding_remove_all` — Clear all bindings from an action
196
+ - `input_binding_composite_create` — Create composite bindings (e.g., 2D vectors)
197
+ - `input_control_schemes_manage` — Manage control schemes and device lists
198
+ - `input_actions_state_get` — Inspect current Input Actions asset configuration
199
+ - `input_actions_asset_analyze` — Produce structured summaries of Input Actions assets
200
+
201
+ ### Editor & Console Utilities
202
+ - `menu_item_execute` — Trigger Unity Editor menu items programmatically
203
+ - `console_clear` — Clear Unity console logs with filtering options
204
+ - `console_read` — Stream Unity console output with advanced filters
205
+ - `editor_tags_manage` — Manage project tags (add/remove/list)
206
+ - `editor_layers_manage` — Manage project layers with index conversion
207
+ - `editor_selection_manage` — Inspect or mutate the current editor selection
208
+ - `editor_windows_manage` — Enumerate or focus Unity editor windows
209
+ - `editor_tools_manage` — Manage editor tools and plugins
210
+ - `compilation_get_state` — Inspect current compilation state and errors
211
+
212
+ ### Project Settings & Packages
213
+ - `settings_get` — Read Unity project settings with granular control
214
+ - `settings_update` — Safely update project settings (requires confirmation)
215
+ - `package_manage` — List or manage Unity packages via Package Manager
216
+ - `package_registry_config` — Configure package registries/scopes
217
+
218
+ ### Asset Visualization & Capture
219
+ - `screenshot_capture` — Capture Game/Scene view screenshots
220
+ - `screenshot_analyze` — Run image analysis on captured screenshots
221
+ - `video_capture_start` — Begin recording the Game view to video
222
+ - `video_capture_stop` — Stop the current video recording
223
+ - `video_capture_status` — Inspect capture status / metadata
224
+ - `video_capture_for` — Record for a fixed duration before auto-stop
225
+
226
+ ### Testing & Diagnostics
227
+ - `test_run` — Run Unity tests (EditMode/PlayMode)
228
+ - `test_get_status` — Query test runner progress/results
176
229
 
177
230
  ## Requirements
178
231
 
@@ -199,7 +252,7 @@ npm install -g @akiojin/unity-mcp-server
199
252
 
200
253
  ## Repository
201
254
 
202
- Full source code and documentation: https://github.com/akiojin/unity-mcp-server
255
+ Full source code and documentation: <https://github.com/akiojin/unity-mcp-server>
203
256
 
204
257
  ## License
205
258
 
@@ -1,2 +1,8 @@
1
1
  #!/usr/bin/env node
2
- import '../src/core/server.js';
2
+ import { startServer } from '../src/core/server.js';
3
+
4
+ startServer().catch((error) => {
5
+ console.error('Fatal error:', error);
6
+ console.error('Stack trace:', error?.stack);
7
+ process.exit(1);
8
+ });
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@akiojin/unity-mcp-server",
3
- "version": "2.16.0",
3
+ "version": "2.25.0",
4
4
  "description": "MCP server and Unity Editor bridge — enables AI assistants to control Unity for AI-assisted workflows",
5
5
  "type": "module",
6
6
  "main": "src/core/server.js",
@@ -13,18 +13,24 @@
13
13
  "build:index": "node src/tools/buildCodeIndex.js",
14
14
  "test": "node --test tests/unit/**/*.test.js tests/integration/*.test.js",
15
15
  "test:unit": "NODE_ENV=test node --test tests/unit/**/*.test.js",
16
- "test:integration": "NODE_ENV=test node --test tests/integration/*.test.js",
16
+ "test:integration": "NODE_ENV=test node scripts/run-non-unity-tests.mjs",
17
17
  "test:e2e": "NODE_ENV=test node --test tests/e2e/*.test.js",
18
18
  "test:coverage": "c8 --reporter=lcov --reporter=text --reporter=html node --test tests/unit/**/*.test.js tests/integration/*.test.js",
19
19
  "test:coverage:full": "c8 --reporter=lcov --reporter=text --reporter=html node --test tests/**/*.test.js",
20
20
  "test:watch": "node --watch --test tests/unit/**/*.test.js",
21
21
  "test:watch:all": "node --watch --test tests/**/*.test.js",
22
22
  "test:performance": "node --test tests/performance/*.test.js",
23
- "test:ci": "c8 --reporter=lcov --check-coverage=false node --test tests/unit/core/config.test.js tests/unit/handlers/PingToolHandler.test.js tests/unit/handlers/CreateGameObjectToolHandler.test.js",
23
+ "test:ci": "CI=true NODE_ENV=test node --test tests/unit/core/codeIndex.test.js tests/unit/core/codeIndexDb.test.js tests/unit/core/config.test.js tests/unit/core/indexWatcher.test.js tests/unit/core/projectInfo.test.js tests/unit/core/server.test.js tests/unit/handlers/script/CodeIndexStatusToolHandler.test.js",
24
24
  "test:ci:all": "c8 --reporter=lcov node --test tests/unit/**/*.test.js",
25
+ "simulate:code-index": "node scripts/simulate-code-index-status.mjs",
25
26
  "test:verbose": "VERBOSE_TEST=true node --test tests/**/*.test.js",
27
+ "prepare": "cd .. && husky || true",
26
28
  "prepublishOnly": "npm run test:ci",
27
- "postinstall": "chmod +x bin/unity-mcp-server || true"
29
+ "postinstall": "chmod +x bin/unity-mcp-server || true",
30
+ "test:ci:unity": "timeout 60 node --test tests/unit/core/codeIndex.test.js tests/unit/core/codeIndexDb.test.js tests/unit/core/config.test.js tests/unit/core/indexWatcher.test.js tests/unit/core/projectInfo.test.js tests/unit/core/server.test.js || exit 0",
31
+ "test:unity": "node tests/run-unity-integration.mjs",
32
+ "test:nounity": "npm run test:integration",
33
+ "test:ci:integration": "CI=true NODE_ENV=test node --test tests/integration/code-index-background.test.js"
28
34
  },
29
35
  "keywords": [
30
36
  "mcp",
@@ -42,10 +48,11 @@
42
48
  "license": "MIT",
43
49
  "dependencies": {
44
50
  "@modelcontextprotocol/sdk": "^0.6.1",
45
- "better-sqlite3": "^9.4.3"
51
+ "better-sqlite3": "^9.4.3",
52
+ "find-up": "^6.3.0"
46
53
  },
47
54
  "engines": {
48
- "node": ">=18.0.0"
55
+ "node": ">=18 <21"
49
56
  },
50
57
  "repository": {
51
58
  "type": "git",
@@ -67,7 +74,23 @@
67
74
  "access": "public"
68
75
  },
69
76
  "devDependencies": {
77
+ "@commitlint/cli": "^18.6.1",
78
+ "@commitlint/config-conventional": "^18.6.3",
79
+ "@semantic-release/changelog": "^6.0.3",
80
+ "@semantic-release/commit-analyzer": "^11.1.0",
81
+ "@semantic-release/exec": "^6.0.3",
82
+ "@semantic-release/git": "^10.0.1",
83
+ "@semantic-release/release-notes-generator": "^12.1.0",
70
84
  "c8": "^10.1.3",
71
- "nodemon": "^3.1.7"
85
+ "eslint": "^8.57.1",
86
+ "eslint-config-standard": "^17.1.0",
87
+ "eslint-plugin-import": "^2.31.0",
88
+ "eslint-plugin-n": "^16.6.2",
89
+ "eslint-plugin-promise": "^6.6.0",
90
+ "husky": "^9.1.7",
91
+ "markdownlint-cli": "^0.43.0",
92
+ "nodemon": "^3.1.7",
93
+ "prettier": "^3.4.2",
94
+ "semantic-release": "^22.0.12"
72
95
  }
73
96
  }
File without changes
File without changes
@@ -1,5 +1,6 @@
1
1
  import fs from 'fs';
2
2
  import path from 'path';
3
+ import { findUpSync } from 'find-up';
3
4
 
4
5
  /**
5
6
  * Shallow merge utility (simple objects only)
@@ -92,25 +93,44 @@ const baseConfig = {
92
93
  * 1) UNITY_MCP_CONFIG (explicit file path)
93
94
  * 2) ./.unity/config.json (project-local)
94
95
  * 3) ~/.unity/config.json (user-global)
95
- * If none found, return {} and rely on env/defaults.
96
+ * If none found, create ./.unity/config.json with defaults.
96
97
  */
97
- function loadExternalConfig() {
98
- const explicitPath = process.env.UNITY_MCP_CONFIG;
98
+ function ensureDefaultProjectConfig(baseDir) {
99
+ const dir = path.resolve(baseDir, '.unity');
100
+ const file = path.join(dir, 'config.json');
101
+
102
+ try {
103
+ if (!fs.existsSync(dir)) {
104
+ fs.mkdirSync(dir, { recursive: true });
105
+ }
99
106
 
100
- // Find nearest <workspace>/.unity/config.json by walking up from process.cwd()
101
- const findProjectConfigUp = () => {
102
- let dir = process.cwd();
103
- let prev = '';
104
- for (let i = 0; i < 3 && dir && dir !== prev; i++) {
105
- const p = path.resolve(dir, '.unity', 'config.json');
106
- if (fs.existsSync(p)) return p;
107
- prev = dir;
108
- dir = path.dirname(dir);
107
+ if (!fs.existsSync(file)) {
108
+ const inferredRoot = fs.existsSync(path.join(baseDir, 'Assets')) ? baseDir : '';
109
+ const defaultConfig = {
110
+ unity: {
111
+ unityHost: 'localhost',
112
+ mcpHost: 'localhost',
113
+ port: 6400,
114
+ },
115
+ project: {
116
+ root: inferredRoot ? inferredRoot.replace(/\\/g, '/') : '',
117
+ },
118
+ };
119
+ fs.writeFileSync(file, `${JSON.stringify(defaultConfig, null, 2)}\n`, 'utf8');
109
120
  }
121
+ return file;
122
+ } catch (error) {
110
123
  return null;
111
- };
124
+ }
125
+ }
112
126
 
113
- const projectPath = findProjectConfigUp();
127
+ function loadExternalConfig() {
128
+ const explicitPath = process.env.UNITY_MCP_CONFIG;
129
+
130
+ const projectPath = findUpSync((directory) => {
131
+ const candidate = path.resolve(directory, '.unity', 'config.json');
132
+ return fs.existsSync(candidate) ? candidate : undefined;
133
+ }, { cwd: process.cwd() });
114
134
  const homeDir = process.env.HOME || process.env.USERPROFILE || '';
115
135
  const userPath = homeDir ? path.resolve(homeDir, '.unity', 'config.json') : null;
116
136
 
@@ -128,6 +148,19 @@ function loadExternalConfig() {
128
148
  return { __configLoadError: `${p}: ${e.message}` };
129
149
  }
130
150
  }
151
+ const fallbackPath = ensureDefaultProjectConfig(process.cwd());
152
+ if (fallbackPath && fs.existsSync(fallbackPath)) {
153
+ try {
154
+ const raw = fs.readFileSync(fallbackPath, 'utf8');
155
+ const json = JSON.parse(raw);
156
+ const out = json && typeof json === 'object' ? json : {};
157
+ out.__configPath = fallbackPath;
158
+ out.__configGenerated = true;
159
+ return out;
160
+ } catch (e) {
161
+ return { __configLoadError: `${fallbackPath}: ${e.message}` };
162
+ }
163
+ }
131
164
  return {};
132
165
  }
133
166
 
@@ -1,10 +1,13 @@
1
1
  import { logger, config } from './config.js';
2
+ import { JobManager } from './jobManager.js';
2
3
 
3
4
  export class IndexWatcher {
4
5
  constructor(unityConnection) {
5
6
  this.unityConnection = unityConnection;
6
7
  this.timer = null;
7
8
  this.running = false;
9
+ this.jobManager = JobManager.getInstance();
10
+ this.currentWatcherJobId = null;
8
11
  }
9
12
 
10
13
  start() {
@@ -13,6 +16,9 @@ export class IndexWatcher {
13
16
  const interval = Math.max(2000, Number(config.indexing.intervalMs || 15000));
14
17
  logger.info(`[index] watcher enabled (interval=${interval}ms)`);
15
18
  this.timer = setInterval(() => this.tick(), interval);
19
+ if (typeof this.timer.unref === 'function') {
20
+ this.timer.unref();
21
+ }
16
22
  // Initial kick
17
23
  this.tick();
18
24
  }
@@ -28,25 +34,88 @@ export class IndexWatcher {
28
34
  if (this.running) return;
29
35
  this.running = true;
30
36
  try {
31
- const { BuildCodeIndexToolHandler } = await import('../handlers/script/BuildCodeIndexToolHandler.js');
32
- const handler = new BuildCodeIndexToolHandler(this.unityConnection);
33
- const params = {
34
- concurrency: config.indexing.concurrency || 8,
35
- retry: config.indexing.retry || 2,
36
- reportEvery: config.indexing.reportEvery || 500,
37
- };
38
- const res = await handler.handle(params);
39
- const ok = res?.result?.success;
40
- if (ok) {
41
- logger.info(`[index] updated=${res.result.updatedFiles || 0} removed=${res.result.removedFiles || 0} total=${res.result.totalIndexedSymbols || 0}`);
42
- } else if (res?.result?.error) {
43
- logger.warn(`[index] update failed: ${res.result.error}`);
37
+ // Check if manual build is already running (jobs starting with 'build-')
38
+ const allJobs = this.jobManager.getAllJobs();
39
+ const manualBuildRunning = allJobs.some(job =>
40
+ job.id.startsWith('build-') && job.status === 'running'
41
+ );
42
+
43
+ if (manualBuildRunning) {
44
+ logger.info('[index] watcher: skipping auto-build (manual build in progress)');
45
+ return;
44
46
  }
47
+
48
+ // Check if our watcher job is still running
49
+ if (this.currentWatcherJobId) {
50
+ const watcherJob = this.jobManager.get(this.currentWatcherJobId);
51
+ if (watcherJob && watcherJob.status === 'running') {
52
+ logger.info('[index] watcher: previous auto-build still running, skipping');
53
+ return;
54
+ }
55
+ // Previous watcher job completed or cleaned up
56
+ this.currentWatcherJobId = null;
57
+ }
58
+
59
+ // Start new watcher build job
60
+ const jobId = `watcher-${Date.now()}`;
61
+ this.currentWatcherJobId = jobId;
62
+
63
+ const { CodeIndexBuildToolHandler } = await import('../handlers/script/CodeIndexBuildToolHandler.js');
64
+ const handler = new CodeIndexBuildToolHandler(this.unityConnection);
65
+
66
+ // Create the build job through JobManager
67
+ this.jobManager.create(jobId, async (job) => {
68
+ const params = {
69
+ concurrency: config.indexing.concurrency || 8,
70
+ retry: config.indexing.retry || 2,
71
+ reportEvery: config.indexing.reportEvery || 500,
72
+ };
73
+ return await handler._executeBuild(params, job);
74
+ });
75
+
76
+ logger.info(`[index] watcher: started auto-build job ${jobId}`);
77
+
78
+ // Monitor job completion in background
79
+ // (Job result will be logged when it completes/fails)
80
+ this._monitorJob(jobId);
81
+
45
82
  } catch (e) {
46
- logger.warn(`[index] update exception: ${e.message}`);
83
+ logger.warn(`[index] watcher exception: ${e.message}`);
47
84
  } finally {
48
85
  this.running = false;
49
86
  }
50
87
  }
51
- }
52
88
 
89
+ /**
90
+ * Monitor job completion for logging
91
+ * @private
92
+ */
93
+ async _monitorJob(jobId) {
94
+ // Check job status periodically
95
+ const checkInterval = setInterval(() => {
96
+ const job = this.jobManager.get(jobId);
97
+ if (!job) {
98
+ // Job cleaned up
99
+ clearInterval(checkInterval);
100
+ return;
101
+ }
102
+
103
+ if (job.status === 'completed') {
104
+ logger.info(`[index] watcher: auto-build completed - updated=${job.result?.updatedFiles || 0} removed=${job.result?.removedFiles || 0} total=${job.result?.totalIndexedSymbols || 0}`);
105
+ clearInterval(checkInterval);
106
+ } else if (job.status === 'failed') {
107
+ logger.warn(`[index] watcher: auto-build failed - ${job.error}`);
108
+ clearInterval(checkInterval);
109
+ }
110
+ }, 1000);
111
+ if (typeof checkInterval.unref === 'function') {
112
+ checkInterval.unref();
113
+ }
114
+
115
+ // Cleanup interval after 10 minutes (longer than job cleanup)
116
+ const cleanupTimeout = setTimeout(() => clearInterval(checkInterval), 600000);
117
+ if (typeof cleanupTimeout.unref === 'function') {
118
+ cleanupTimeout.unref();
119
+ }
120
+ }
121
+ }