t1k:cocos:playable:tooling-gotchas
| Field | Value |
|---|---|
| Module | playable |
| Version | 2.14.4 |
| Effort | low |
| Tools | — |
Keywords: console logs, gotcha, import, manage_asset, manage_debug, manage_prefab, script, write tool
How to invoke
Section titled “How to invoke”/t1k:cocos:playable:tooling-gotchasCocos Playable — Tooling Gotchas
Section titled “Cocos Playable — Tooling Gotchas”Known failure modes when using Cocos MCP tools and Claude Code’s Write tool to author scripts and scenes for playable ads. Each entry maps to a reference fragment with full evidence and the correct fix.
Gotcha Index
Section titled “Gotcha Index”| ID | Tool | Symptom | Reference |
|---|---|---|---|
| 1 | Cocos MCP | Scene/asset writes land in wrong repo | cocos-mcp-targets-open-project |
| 2 | Write tool | New script file not imported; @ccclass not registered | write-tool-files-not-imported |
| 3 | Prefab JSON | Need to bind a component with no editor / no MCP server | prefab-component-attach-by-hand |
| 4 | Node / rendering | Runtime-created node under a Canvas renders nothing, no error | runtime-created-nodes |
| 5 | Cocos MCP | manage_component add reports “not found after addition” — it WAS added; and a component-ref set_property rejects the component uuid | manage-component-custom-script |
| 6 | Cocos MCP | manage_prefab update returns “Editor rejected apply-prefab” but the apply DID land — and it carries the user’s unsaved overrides with it | manage-prefab-update-false-error |
| 7 | Cocos MCP | manage_debug get_console_logs returns an empty log list on every call — the capture is unimplemented, so it can never go red | manage-debug-console-logs-empty |
| 8 | Cocos MCP | manage_component set_property/set_properties_batch crashes writing a Node[]/component-array property (even a single-element one) — but manage_node itself creates child nodes fine | manage-component-array-properties |
| 9 | Cocos MCP | manage_scene_query soft_reload and manage_scene action=open report success but keep serving the editor’s cached scene after an out-of-band .scene edit — the next editor save silently erases the edit | scene-reload-stale-cache |
| 10 | Editor save | Reopening and saving a scene rewrites UI camera _priority/_clearFlags with no intentional edit, breaking UI render order/clearing | scene-reopen-save-camera-rewrite |
| 11 | Cocos MCP | cc.MeshRenderer with an empty material array: sharedMaterials.0 is refused and sharedMaterials.length reports success without growing — set _materials.length then _materials.<i> | manage-component-mesh-renderer-empty-material |
| 12 | Prefab JSON | Direct edit on a node inside a nested cc.PrefabInstance is reverted at load — the instance re-syncs from its source asset and re-applies propertyOverrides, so the override table (or cc.MountedChildrenInfo.nodes for new nodes) is the only thing that sticks | prefab-instance-override-table |
Quick Decision Guide
Section titled “Quick Decision Guide”About to call an MCP scene/asset action (manage_scene, manage_node, manage_component, manage_asset)?
Call manage_project action=get_info first and confirm the open project matches the current repo. Compare the returned path — uuid is not a valid check, because a project cloned from a template inherits the template’s uuid.
About to create a new TypeScript script in a new subfolder?
Use manage_asset action=create url=db://assets/scripts/MyScript.ts — NOT the Write tool. The Write tool produces a file; the editor needs a managed import to generate .meta and register @ccclass.
About to bind a component to a prefab?
Use manage_prefab action=update — that is the normal path. Fall back to editing the prefab JSON by hand only when the editor is closed, the MCP server is unavailable, or the script has no .ts.meta uuid yet.
manage_prefab action=update came back with “Editor rejected apply-prefab”?
Do NOT retry — the apply may already have landed. grep the target .prefab for the child’s uuid to settle it, then check which other prefab instances the apply carried in from the user’s unsaved edits.
About to add a custom @ccclass script to a scene node?
manage_component action=add reports "not found on node after addition" even on success — a custom script is listed by its compressed cid (first 5 chars of the script uuid), not its class name. Never retry the add; verify with get_info using the cid. And a @property(SomeComponent) reference takes the node uuid, not the component uuid.
About to verify an editor-side change with manage_debug get_console_logs?
Don’t — its console buffer has no writer, so it returns {"total":0,"logs":[]} whether the editor is clean or throwing. Use get_project_logs / search_project_logs, which read temp/logs/project.log. That file rotates on editor restart, so mark the line count before the operation and read the tail in the same session.
About to write a Node[]/component-array @property (e.g. SplineController.controlPoints, an AudioClip[]) via manage_component?
manage_node itself is fine — create the child nodes in the prefab normally. It is only set_property/set_properties_batch writing the ARRAY that crashes, even with one element. Do not fall back to constructing nodes at runtime to route around it (prefab-only-construction-cocos.md forbids that) — author the children in the prefab and populate the array from node.children at spawn instead.
Edited a .scene file out of band and need the editor to pick it up?
manage_scene_query action=soft_reload and manage_scene action=open both report success without actually re-reading the file — the editor keeps serving its cached copy, and its next save silently erases your edit. Use manage_asset action=reimport and verify by reading the property values back, not by trusting the success string.
About to reopen and save a scene just to tidy it up (e.g. remove an orphaned serialized key)?
Don’t. A reopen-and-save can silently rewrite unrelated properties — observed on a UI camera’s _priority/_clearFlags, breaking render order/clearing with a diff that looks like two innocuous integers. Cocos ignores unknown serialized keys, so leaving a harmless orphan key alone is safer than reopening-and-saving to remove it.
About to set a material on a cc.MeshRenderer whose material array is empty (a node just created via manage_node)?
sharedMaterials.0 will be refused (“not found”) and sharedMaterials.length reports success without growing the array. Size the private backing field first, then write each slot: set _materials.length (propertyType number), then _materials.<i> (propertyType material).
About to edit a nested prefab-instance value directly in the .prefab JSON?
A node that belongs to a nested cc.PrefabInstance is re-synced from its source asset and then re-applies its propertyOverrides at load — a value written straight onto the node object is silently reverted. Flip the override entry (propertyPath + targetInfo.localID = the target node cc.PrefabInfo.fileId or component cc.CompPrefabInfo.fileId), or add the node via cc.MountedChildrenInfo.nodes. A file-level re-read proves nothing — instantiate the prefab (manage_node action=create) or query live nodes (manage_scene_query action=query_by_asset) to verify.
Details
Section titled “Details”- MCP project targeting — get_info before every write
- Write tool scripts not auto-imported — use manage_asset create
- Attaching a component to a prefab by hand when MCP is unavailable
- Runtime-created nodes default to the wrong layer and are invisible under a Canvas
- manage_component with custom @ccclass scripts — cid lookup, node-uuid refs
- manage_prefab update reports a false failure after a successful apply
- manage_debug get_console_logs is a false green — use the project-log actions
- manage_component array-of-reference properties crash the bridge — node creation itself is fine
- Scene reload reports success but serves stale cache — reimport is the only real reload
- Reopen-and-save silently rewrites UI camera properties
- cc.MeshRenderer with an empty material array — write _materials.length then _materials.
- Nested cc.PrefabInstance obeys its override table, not the node objects