|
4 | 4 |
|
5 | 5 | **User Story:** |
6 | 6 |
|
7 | | -* As an AI agent, I want to get detailed information for a specific track (by index, name, or by targeting the currently selected track, defaulting to selected if no specifier), including its parameters (volume, pan, mute, solo, arm), sends, and a list of its clips with their properties (name, color, length, loop status), so I can perform targeted analysis or suggest modifications. |
| 7 | +* As an AI agent, I want to get detailed information for a specific track (by index, name, or by targeting the currently selected track, defaulting to selected if no specifier), including its parameters (volume, pan, mute, solo, arm), sends, and a list of its clips with their properties (name, color, playback state), so I can perform targeted analysis or suggest modifications. |
8 | 8 |
|
9 | 9 | **Acceptance Criteria:** |
10 | 10 |
|
|
13 | 13 | * `track_index` (integer, optional): 0-based index of the track. |
14 | 14 | * `track_name` (string, optional): Name of the track. |
15 | 15 | * `get_selected` (boolean, optional): If true, retrieves details for the currently selected track. If no parameters (`track_index`, `track_name`, `get_selected`) are provided, this defaults to `true`. |
| 16 | +* **Parameter Rules:** |
| 17 | + * Exactly one of `track_index`, `track_name`, or `get_selected` may be provided. Supplying more than one results in an `INVALID_PARAMETER` error. |
| 18 | + * If none are provided, the tool behaves as if `get_selected=true`. |
| 19 | + * `track_name` matching is case-sensitive (consistent with `launch_clip`). |
| 20 | + * `index` refers to the project’s main 0-based track index, consistent with `list_tracks`. |
16 | 21 | * **Response Body:** A single track object containing: |
17 | 22 | * All fields from the `list_tracks` response object for this track (i.e., `index`, `name`, `type`, `is_group`, `parent_group_index`, `activated`, `color`, `is_selected`, and the `devices` array with device summaries). |
18 | 23 | * `volume` (float): Normalized volume (0.0-1.0). |
|
23 | 28 | * `soloed` (boolean): Is the track soloed. |
24 | 29 | * `armed` (boolean): Is the track armed for recording. |
25 | 30 | * `monitor_enabled` (boolean): Is monitoring enabled. |
26 | | - * `auto_monitor_enabled` (boolean): Is auto-monitoring enabled. |
| 31 | + * `auto_monitor_enabled` (boolean): Whether auto-monitor mode is active (derived via monitorMode). |
27 | 32 | * `sends` (array of objects): List of sends for the track. |
28 | 33 | * `name` (string): Name of the send channel. |
29 | 34 | * `volume` (float): Normalized send level. |
|
33 | 38 | * `slot_index` (integer): 0-based index of the clip slot. |
34 | 39 | * `scene_name` (string, nullable): Name of the scene this slot aligns with. |
35 | 40 | * `has_content` (boolean): True if the slot contains a clip. |
36 | | - * `clip_name` (string, nullable): Name of the clip. |
37 | | - * `clip_color` (string, nullable): Color of the clip. |
38 | | - * `length` (string, nullable): Length of the clip (e.g., "4.0.0"). |
39 | | - * `is_looping` (boolean, nullable): True if the clip is set to loop. |
| 41 | + * `clip_name` (string, nullable): Clip name from `ClipLauncherSlot.name()` (null if empty or unavailable). |
| 42 | + * `clip_color` (string, nullable): Color of the clip in RGB string format (e.g., "rgb(255,128,0)"). |
| 43 | + * `is_playing` (boolean, nullable): True if the clip in this slot is currently playing. |
| 44 | + * `is_recording` (boolean, nullable): True if the clip in this slot is currently recording. |
| 45 | + * `is_playback_queued` (boolean, nullable): True if playback is queued for the clip in this slot. |
40 | 46 | * The `get_track_details` tool correctly identifies the target track based on `track_index`, `track_name`, or `get_selected` (or defaults to selected). |
41 | 47 | * The tool retrieves all specified detailed information using the Bitwig API (e.g., `CursorTrack` or specific `Track` object properties, `ClipLauncherSlotBank`). |
42 | | -* The tool correctly formats clip `length` and `is_looping` status. |
| 48 | +* The tool exposes available clip state and scene data; clip length and loop status are intentionally omitted (not exposed by slot API). |
43 | 49 | * The tool handles cases where a track is not found (for by index/name) or no track is selected (if `get_selected` is true or defaulted) by returning an appropriate error response. |
44 | | -* The `api-reference.md` is updated with the `get_track_details` tool specification. |
| 50 | +* **Error Responses:** |
| 51 | + * `INVALID_PARAMETER` for invalid combinations or types of parameters. |
| 52 | + * `TRACK_NOT_FOUND` if the target track cannot be resolved (including the case when `get_selected` is used but no track is selected). |
| 53 | + * `BITWIG_API_ERROR` for Bitwig API failures. |
| 54 | +* The `api-reference.md` is updated with the `get_track_details` tool specification and notes on clip field limitations. |
45 | 55 | * Unit tests are written for the `GetTrackDetailsTool.java` logic. |
46 | 56 | * Manual testing confirms accuracy against various Bitwig project configurations and track states. |
47 | 57 |
|
48 | 58 | **Tasks:** |
49 | 59 |
|
50 | | -1. Create `GetTrackDetailsTool.java` implementing the `MCPTool` interface. |
| 60 | +1. Create `GetTrackDetailsTool.java` following the existing static specification pattern (e.g., `ListTracksTool.specification(...)`) and using the unified `McpErrorHandler` error handling. |
51 | 61 | 2. Implement logic to identify the target track: |
52 | 62 | * If `track_index` is provided, get track by index. |
53 | | - * If `track_name` is provided, find track by name. |
| 63 | + * If `track_name` is provided, find track by name (case-sensitive). |
54 | 64 | * If `get_selected` is true, or if no parameters are provided, use `CursorTrack`. |
55 | 65 | 3. Once the target track is identified, retrieve all basic information as per `list_tracks` (or reuse logic). |
56 | 66 | 4. Retrieve detailed properties: `volume`, `pan`, `muted`, `soloed`, `armed`, `monitor_enabled`, `auto_monitor_enabled`. |
57 | 67 | 5. Retrieve send information. |
58 | | -6. Access the track's `ClipLauncherSlotBank` to retrieve details for each clip slot: `slot_index`, `scene_name`, `has_content`, `clip_name`, `clip_color`, `length`, `is_looping`. |
| 68 | +6. Access the track's `ClipLauncherSlotBank` to retrieve details for each clip slot: `slot_index`, `scene_name`, `has_content`, `clip_name`, color, and playback/record/queue state flags. |
59 | 69 | 7. Construct the JSON response as specified. |
60 | | -8. Implement robust error handling (e.g., track not found, no track selected). |
61 | | -9. Update `docs/api-reference.md` with the `get_track_details` tool details. |
62 | | -10. Write JUnit tests for `GetTrackDetailsTool.java`. |
| 70 | +8. Implement robust error handling (e.g., invalid parameter combinations, track not found, no track selected). |
| 71 | +9. Update `docs/api-reference.md` with the `get_track_details` tool details and examples, including notes on clip field limitations. |
| 72 | +10. Write JUnit tests for `GetTrackDetailsTool.java` (cover all parameter paths, formatting, and empty states). |
63 | 73 | 11. Perform manual integration testing. |
0 commit comments