OAuth enabled but no valid token found. Starting authentication...
Found expired OAuth token, attempting refresh... Token refresh successful ## CHANGES - Share achievements as images with exclusive peak stats captured 🏆 - Track keyboard shortcut usage and level up mastery in status bar ⌨️ - Edit Auto Run docs fullscreen with expanded editor and progress footer 🖥️ - Right-click tabs for new context management menu actions 🧭 - Merge contexts via new modal, with token estimates and cleaning 🔀 - Send context to other agents with searchable modal and cleaning options 🛰️ - Export any tab conversation as self-contained themed HTML file 📄 - Added dedicated History panel with search, filters, graph view, resume 🕒 - Validate Auto Run completions in History with review workflow toggles ✅ - Support fixed remote-access ports with clear security guidance 🔒
@@ -31,3 +31,46 @@ Since Auto Runs can execute in parallel across multiple Maestro sessions, achiev
|
||||
But let's be real — getting to Level 11 is going to take some serious hacking. You'll need a well-orchestrated fleet of agents running around the clock, carefully crafted playbooks that loop indefinitely, and the infrastructure to keep it all humming. It's the ultimate test of your Maestro skills.
|
||||
|
||||
The achievement panel shows your current rank, progress to the next level, and total accumulated time. Each rank includes flavor text and information about a legendary conductor who exemplifies that level of mastery.
|
||||
|
||||
## Sharing Your Achievements
|
||||
|
||||
Generate a shareable image of your achievements to celebrate milestones or compare progress with other Maestro users. The share image captures **unique statistics not tracked anywhere else** in the app.
|
||||
|
||||

|
||||
|
||||
**To generate a share image:**
|
||||
1. Open the Achievements panel
|
||||
2. Click **Share** in the header
|
||||
3. Choose **Copy to Clipboard** or **Save as Image**
|
||||
|
||||
### Stats Captured in Share Images
|
||||
|
||||
The share image includes comprehensive usage statistics:
|
||||
|
||||
| Stat | Description |
|
||||
|------|-------------|
|
||||
| **Sessions** | Total number of AI sessions created |
|
||||
| **Total Tokens** | Cumulative tokens processed across all sessions |
|
||||
| **Total AutoRun** | Cumulative Auto Run execution time |
|
||||
| **Longest AutoRun** | Your personal record for longest continuous Auto Run |
|
||||
| **Hands-on Time** | Time spent actively interacting with Maestro |
|
||||
| **Registered Agents** | Peak number of agents you've configured |
|
||||
| **Parallel AutoRuns** | Peak simultaneous Auto Runs achieved |
|
||||
| **Parallel Queries** | Peak simultaneous AI queries in flight |
|
||||
| **Queue Depth** | Peak message queue depth reached |
|
||||
|
||||
These peak usage stats are tracked automatically and persist across sessions. They represent your high-water marks — evidence of your most intensive Maestro orchestrations.
|
||||
|
||||
## Keyboard Mastery
|
||||
|
||||
Separate from Conductor ranks, Maestro tracks your **keyboard mastery** based on shortcut usage. As you discover and use more keyboard shortcuts, you level up through 5 mastery levels:
|
||||
|
||||
| Level | Title | Shortcuts Used |
|
||||
|:-----:|-------|----------------|
|
||||
| 0 | Novice | 0-19% |
|
||||
| 1 | Apprentice | 20-39% |
|
||||
| 2 | Journeyman | 40-59% |
|
||||
| 3 | Expert | 60-79% |
|
||||
| 4 | Master | 80-100% |
|
||||
|
||||
Your current keyboard mastery level is shown in the status bar. Hover over the keyboard icon to see which shortcuts you've used and which remain to be discovered. See [Keyboard Shortcuts](./keyboard-shortcuts) for the full shortcut reference.
|
||||
|
||||
@@ -110,6 +110,24 @@ Each completed task is logged to the History panel with:
|
||||
- `Enter` - View full response
|
||||
- `Esc` - Close detail view and return to list
|
||||
|
||||
## Expanded Editor View
|
||||
|
||||
For editing complex Auto Run documents, use the **Expanded Editor** — a fullscreen modal that provides more screen real-estate.
|
||||
|
||||
**To open the Expanded Editor:**
|
||||
- Click the **expand icon** (↗️) in the top-right corner of the Auto Run panel
|
||||
|
||||

|
||||
|
||||
The Expanded Editor provides:
|
||||
- **Edit/Preview toggle** — Switch between editing markdown and previewing rendered output
|
||||
- **Document selector** — Switch between documents without closing the modal
|
||||
- **Run controls** — Start, stop, and monitor batch runs from the expanded view
|
||||
- **Task progress** — See "X of Y tasks completed" and token count at the bottom
|
||||
- **Full toolbar** — Create new documents, refresh, and open folder
|
||||
|
||||
Click **Collapse** or press `Esc` to return to the sidebar panel view.
|
||||
|
||||
## Auto-Save
|
||||
|
||||
Documents auto-save after 5 seconds of inactivity, and immediately when switching documents. Full undo/redo support with `Cmd+Z` / `Cmd+Shift+Z`.
|
||||
|
||||
@@ -4,6 +4,41 @@ description: Compact, merge, and transfer conversation context between sessions
|
||||
icon: layers
|
||||
---
|
||||
|
||||
## Tab Menu
|
||||
|
||||
Right-click any tab to access the full range of context management options:
|
||||
|
||||

|
||||
|
||||
| Action | Description |
|
||||
|--------|-------------|
|
||||
| **Copy Session ID** | Copy the Claude Code session ID to clipboard |
|
||||
| **Star Session** | Bookmark this session for quick access |
|
||||
| **Rename Tab** | Give the tab a descriptive name |
|
||||
| **Mark as Unread** | Add unread indicator to the tab |
|
||||
| **Context: Copy to Clipboard** | Copy the full conversation to clipboard |
|
||||
| **Context: Compact** | Compress context while preserving key information |
|
||||
| **Context: Merge Into** | Merge this context into another session |
|
||||
| **Context: Send to Agent** | Transfer context to a different agent |
|
||||
|
||||
## Tab Export
|
||||
|
||||
Export any tab conversation as a self-contained HTML file:
|
||||
|
||||
1. Right-click the tab → **Context: Copy to Clipboard**
|
||||
2. Or use **Command Palette** (`Cmd+K`) → "Export tab to HTML"
|
||||
|
||||
The exported HTML file includes:
|
||||
- **Full conversation history** with all messages
|
||||
- **Your current theme colors** — the export adopts your active Maestro theme
|
||||
- **Maestro branding** with links to the website and GitHub
|
||||
- **Session metadata** — agent type, working directory, timestamps, token usage
|
||||
- **Rendered markdown** — code blocks, tables, and formatting preserved
|
||||
|
||||
This is useful for sharing conversations, creating documentation, or archiving important sessions.
|
||||
|
||||
---
|
||||
|
||||
Context management lets you combine or transfer conversation history between sessions and agents, enabling powerful workflows where you can:
|
||||
|
||||
- **Compact & continue** — Compress your context to stay within token limits while preserving key information
|
||||
@@ -33,10 +68,19 @@ When your conversation approaches context limits, you can compress it while pres
|
||||
|
||||
Combine context from multiple sessions or tabs into one:
|
||||
|
||||
1. **Right-click** a tab → **"Merge With..."**, or use **Command Palette** (`Cmd+K` / `Ctrl+K`) → "Merge with another session"
|
||||
2. Search for or select the target session/tab
|
||||
1. **Right-click** a tab → **"Context: Merge Into"**, or use **Command Palette** (`Cmd+K` / `Ctrl+K`) → "Merge with another session"
|
||||
2. Search for or select the target session/tab from the modal
|
||||
3. Review the merge preview showing estimated token count
|
||||
4. Click **"Merge Contexts"**
|
||||
4. Optionally enable **Clean context** to remove duplicates and reduce size
|
||||
5. Click **"Merge Into"**
|
||||
|
||||

|
||||
|
||||
The modal shows:
|
||||
- **Paste ID** tab — Enter a specific session ID directly
|
||||
- **Open Tabs** tab — Browse all open tabs across all agents
|
||||
- **Token estimate** — Shows source size and estimated size after cleaning
|
||||
- **Agent grouping** — Tabs organized by agent with tab counts
|
||||
|
||||
The merged context creates a new tab in the target session with conversation history from both sources. Use this to consolidate related conversations or bring context from an older session into a current one.
|
||||
|
||||
@@ -48,25 +92,35 @@ The merged context creates a new tab in the target session with conversation his
|
||||
- You can merge tabs within the same session or across different sessions
|
||||
- Large merges (100k+ tokens) will show a warning but still proceed
|
||||
- Self-merge (same tab to itself) is prevented
|
||||
- Enable "Clean context" for large merges to reduce token count
|
||||
|
||||
## Sending to Another Agent
|
||||
|
||||
Transfer your context to a different AI agent:
|
||||
|
||||
1. **Right-click** a tab → **"Send to Agent..."**, or use **Command Palette** (`Cmd+K` / `Ctrl+K`) → "Send to another agent"
|
||||
2. Select the target agent (only available/installed agents are shown)
|
||||
3. Optionally enable **context grooming** to optimize the context for the target agent
|
||||
4. A new session opens with the transferred context
|
||||
1. **Right-click** a tab → **"Context: Send to Agent"**, or use **Command Palette** (`Cmd+K` / `Ctrl+K`) → "Send to another agent"
|
||||
2. Search for or select the target agent from the list
|
||||
3. Review the token estimate and cleaning options
|
||||
4. Click **"Send to Session"**
|
||||
|
||||
**Context Grooming:**
|
||||
When transferring between different agent types, the context can be automatically "groomed" to:
|
||||
- Remove agent-specific artifacts and formatting
|
||||
- Condense verbose output while preserving key information
|
||||
- Optimize for the target agent's capabilities
|
||||

|
||||
|
||||
Grooming is enabled by default but can be skipped for faster transfers.
|
||||
The modal shows:
|
||||
- **Searchable agent list** with status indicators (Idle, Busy, etc.)
|
||||
- **Agent paths** to distinguish between agents with similar names
|
||||
- **Token estimate** — Shows source size and estimated size after cleaning
|
||||
- **Clean context option** — Remove duplicates and reduce size before transfer
|
||||
|
||||
**Context Cleaning:**
|
||||
When transferring between agents, the context can be automatically cleaned to:
|
||||
- Remove duplicate messages and verbose output
|
||||
- Condense while preserving key information
|
||||
- Optimize token usage for the target session
|
||||
|
||||
Cleaning is enabled by default but can be disabled for verbatim transfers.
|
||||
|
||||
**Use Cases:**
|
||||
- Start a task in Claude Code, then hand off to Codex for a different perspective
|
||||
- Transfer a debugging session to an agent with different tool access
|
||||
- Move context to an agent pointing at a different project directory
|
||||
- Share context with a worktree sub-agent working on the same codebase
|
||||
|
||||
@@ -57,9 +57,11 @@
|
||||
"general-usage",
|
||||
"keyboard-shortcuts",
|
||||
"slash-commands",
|
||||
"speckit-commands",
|
||||
"git-worktrees",
|
||||
"group-chat",
|
||||
"autorun-playbooks",
|
||||
"history",
|
||||
"context-management",
|
||||
"achievements"
|
||||
]
|
||||
|
||||
@@ -33,6 +33,25 @@ Browse project files with syntax highlighting, markdown preview, and image viewi
|
||||
|
||||

|
||||
|
||||
## Prompt Composer
|
||||
|
||||
For complex prompts that need more editing space, use the **Prompt Composer** — a fullscreen editing modal.
|
||||
|
||||
**To open the Prompt Composer:**
|
||||
- Click the **pencil icon** (✏️) in the bottom-left corner of the AI input box
|
||||
|
||||

|
||||
|
||||
The Prompt Composer provides:
|
||||
- **Full-screen editing space** for complex, multi-paragraph prompts
|
||||
- **Character and token count** displayed in the footer
|
||||
- **All input controls** — History toggle, Read-only mode, Thinking toggle, and send shortcut indicator
|
||||
- **Image attachment support** via the image icon in the footer
|
||||
|
||||

|
||||
|
||||
When you're done editing, click **Send** or press the displayed shortcut to send your message. The composer closes automatically and your prompt is sent to the AI.
|
||||
|
||||
## Output Filtering
|
||||
|
||||
Search and filter AI output with include/exclude modes, regex support, and per-response local filters.
|
||||
|
||||
126
docs/history.md
Normal file
@@ -0,0 +1,126 @@
|
||||
---
|
||||
title: History
|
||||
description: Track all agent activity with searchable, filterable history including Auto Run completions and user annotations.
|
||||
icon: clock
|
||||
---
|
||||
|
||||
The History panel provides a timestamped log of all agent activity — both automated (Auto Run) and manual (user interactions). Use it to review past work, resume sessions, and validate completed tasks.
|
||||
|
||||

|
||||
|
||||
## Entry Types
|
||||
|
||||
History entries are categorized by source:
|
||||
|
||||
| Type | Label | Description |
|
||||
|------|-------|-------------|
|
||||
| **AUTO** | 🤖 AUTO | Entries created by Auto Run task completions |
|
||||
| **USER** | 👤 USER | Entries created manually by the user |
|
||||
|
||||
### Auto Entries
|
||||
|
||||
Auto entries are created automatically when Auto Run completes a task. Each entry includes:
|
||||
- **Summary** of what the agent accomplished
|
||||
- **Session ID** (clickable to jump to that conversation)
|
||||
- **Duration** and **cost** of the task
|
||||
- **Timestamp** of completion
|
||||
|
||||
### User Entries
|
||||
|
||||
User entries are created in two ways:
|
||||
|
||||
1. **History Toggle** — Enable the **History** pill in the AI input box. Every prompt-response cycle automatically creates a user history entry.
|
||||
|
||||
2. **`/history` Command** — Run `/history` to create a synopsis entry covering all activity since the last time you ran the command. This is useful for periodic summaries without logging every single interaction.
|
||||
|
||||
**Toggle the default History behavior** in Settings → toggle "Save to History by default".
|
||||
|
||||
## Filtering History
|
||||
|
||||
### By Type
|
||||
|
||||
Use the **AUTO** and **USER** filter buttons at the top of the History panel to show or hide each entry type:
|
||||
- Click **AUTO** to toggle Auto Run entries
|
||||
- Click **USER** to toggle user-created entries
|
||||
- Both can be active simultaneously
|
||||
|
||||
### By Keyword
|
||||
|
||||
Type in the search box to filter entries by keyword. The search matches against:
|
||||
- Entry summaries
|
||||
- Session IDs
|
||||
- Any text content in the entry
|
||||
|
||||
### By Time Range
|
||||
|
||||
The **Graph View** at the top shows activity distribution over time. **Right-click the graph** to change the time range:
|
||||
- Last 24 hours
|
||||
- Last 7 days
|
||||
- Last 30 days
|
||||
- All time
|
||||
|
||||
The graph bars are clickable — click a time period to jump to entries from that window.
|
||||
|
||||
## Entry Details
|
||||
|
||||
Click any history entry to open the **Detail View**:
|
||||
|
||||

|
||||
|
||||
The detail view shows:
|
||||
- **Full entry header** with type badge, session ID, timestamp, and validation status
|
||||
- **Context usage** — tokens consumed and context window percentage
|
||||
- **Token breakdown** — input tokens, output tokens
|
||||
- **Duration** and **cost**
|
||||
- **Full summary text** of what was accomplished
|
||||
- **RESUME button** — Jump directly to the AI session to continue from where Maestro left off
|
||||
|
||||
### Navigation
|
||||
|
||||
- **Prev / Next** buttons to navigate between entries
|
||||
- **Close** button to return to the list view
|
||||
- **Delete** button to remove the entry
|
||||
|
||||
## Validating Entries
|
||||
|
||||
The **Validated** flag helps you track which Auto Run tasks have been human-reviewed.
|
||||
|
||||

|
||||
|
||||
**To mark an entry as validated:**
|
||||
1. Open the entry detail view
|
||||
2. Click the **VALIDATED** toggle in the header
|
||||
|
||||

|
||||
|
||||
Validated entries show a **checkmark icon** (✓✓) in the list view, making it easy to see at a glance which tasks have been reviewed.
|
||||
|
||||
**Workflow tip:** After an Auto Run batch completes, use the History panel to review each task:
|
||||
1. Open the first AUTO entry
|
||||
2. Click **RESUME** to jump to the session and verify the work
|
||||
3. If satisfied, toggle **VALIDATED**
|
||||
4. Click **Next** to review the next entry
|
||||
5. Repeat until all entries are validated
|
||||
|
||||
This ensures human oversight of automated work while maintaining the full context needed to continue any task.
|
||||
|
||||
## Resuming Sessions
|
||||
|
||||
Every history entry with a Session ID has a **RESUME** button. Clicking it:
|
||||
1. Opens the AI Terminal for that agent
|
||||
2. Loads the exact session where the work was done
|
||||
3. Positions you to continue the conversation
|
||||
|
||||
This is especially powerful for Auto Run tasks — you can pick up exactly where the agent left off, with full conversation context preserved.
|
||||
|
||||
## Keyboard Navigation
|
||||
|
||||
| Key | Action |
|
||||
|-----|--------|
|
||||
| `↑` / `↓` | Navigate between entries |
|
||||
| `Enter` | Open detail view for selected entry |
|
||||
| `Esc` | Close detail view, return to list |
|
||||
|
||||
## Storage
|
||||
|
||||
History is stored per-session in `~/Library/Application Support/Maestro/history/`. Each session maintains up to 5,000 entries. History files can be passed to AI agents as context for understanding past work patterns.
|
||||
@@ -38,6 +38,32 @@ To access Maestro from outside your local network (e.g., on mobile data or from
|
||||
5. Use the Local/Remote pill selector to switch between QR codes
|
||||
6. The tunnel stays active as long as Maestro is running - no time limits, no account required
|
||||
|
||||
## Static Port Configuration
|
||||
|
||||
By default, Maestro assigns a **random port** each time the web server starts. This is a security-by-obscurity measure — attackers can't easily guess which port to target.
|
||||
|
||||
However, if you need a **fixed port** (e.g., for firewall rules, reverse proxies, or persistent tunnel configurations), you can enable static port mode:
|
||||
|
||||
1. Click the **OFFLINE** button to open the Live overlay
|
||||
2. Toggle **Use Custom Port** to enable static port mode
|
||||
3. Enter your desired port number (1024-65535)
|
||||
4. The server restarts automatically on the new port
|
||||
|
||||
**Use cases for static ports:**
|
||||
- Punching a hole through a firewall or NAT
|
||||
- Configuring a reverse proxy (nginx, Caddy)
|
||||
- Setting up persistent SSH tunnels
|
||||
- Integration with home automation systems
|
||||
|
||||
<Warning>
|
||||
**Security Trade-off**: Using a static port removes one layer of security-by-obscurity. The randomized port and auto-generated auth token in the URL work together to protect access. With a static port, you're relying solely on the auth token for security.
|
||||
|
||||
**Recommendations when using static ports:**
|
||||
- Use Cloudflare tunnel for remote access instead of exposing ports directly
|
||||
- Ensure your network firewall is properly configured
|
||||
- Consider additional authentication at the network level
|
||||
</Warning>
|
||||
|
||||
## Screenshots
|
||||
|
||||

|
||||
|
||||
BIN
docs/screenshots/achievements-share.png
Normal file
|
After Width: | Height: | Size: 1.7 MiB |
BIN
docs/screenshots/autorun-expanded.png
Normal file
|
After Width: | Height: | Size: 433 KiB |
BIN
docs/screenshots/history-1.png
Normal file
|
After Width: | Height: | Size: 159 KiB |
BIN
docs/screenshots/history-2.png
Normal file
|
After Width: | Height: | Size: 259 KiB |
BIN
docs/screenshots/history-3.png
Normal file
|
After Width: | Height: | Size: 28 KiB |
BIN
docs/screenshots/history-4.png
Normal file
|
After Width: | Height: | Size: 158 KiB |
BIN
docs/screenshots/prompt-composer-button.png
Normal file
|
After Width: | Height: | Size: 35 KiB |
BIN
docs/screenshots/prompt-composer.png
Normal file
|
After Width: | Height: | Size: 109 KiB |
BIN
docs/screenshots/speckit-commands.png
Normal file
|
After Width: | Height: | Size: 197 KiB |
BIN
docs/screenshots/tab-menu.png
Normal file
|
After Width: | Height: | Size: 64 KiB |
BIN
docs/screenshots/tab-merge.png
Normal file
|
After Width: | Height: | Size: 252 KiB |
BIN
docs/screenshots/tab-send.png
Normal file
|
After Width: | Height: | Size: 284 KiB |
118
docs/speckit-commands.md
Normal file
@@ -0,0 +1,118 @@
|
||||
---
|
||||
title: Spec-Kit Commands
|
||||
description: Structured specification workflow for AI-assisted development using GitHub's spec-kit methodology.
|
||||
icon: file-text
|
||||
---
|
||||
|
||||
Spec-Kit is a structured specification workflow from [GitHub's spec-kit project](https://github.com/github/spec-kit) that helps teams create clear, actionable specifications before implementation. Maestro bundles these commands and keeps them updated automatically.
|
||||
|
||||

|
||||
|
||||
## Spec-Kit vs. Wizard
|
||||
|
||||
Maestro offers two paths to structured development:
|
||||
|
||||
| Feature | Spec-Kit | Onboarding Wizard |
|
||||
|---------|----------|-------------------|
|
||||
| **Approach** | Manual, command-driven workflow | Guided, conversational flow |
|
||||
| **Best For** | Experienced users, complex projects | New users, quick setup |
|
||||
| **Output** | Constitution, specs, tasks → Auto Run docs | Phase 1 Auto Run document |
|
||||
| **Control** | Full control at each step | Streamlined, opinionated |
|
||||
| **Learning Curve** | Moderate | Low |
|
||||
|
||||
**Use Spec-Kit when:**
|
||||
- You want fine-grained control over specification phases
|
||||
- You're working on complex features requiring detailed planning
|
||||
- You prefer explicit command-driven workflows
|
||||
- You want to create reusable constitutions and specifications
|
||||
|
||||
**Use the Wizard when:**
|
||||
- You're starting a new project from scratch
|
||||
- You want to get up and running quickly
|
||||
- You prefer conversational, guided experiences
|
||||
|
||||
Both approaches ultimately produce markdown documents for Auto Run execution.
|
||||
|
||||
## Viewing & Managing Commands
|
||||
|
||||
Access Spec-Kit commands via **Settings → AI Commands** tab. Here you can:
|
||||
|
||||
- **View all commands** with descriptions
|
||||
- **Check for Updates** to pull the latest prompts from GitHub
|
||||
- **Expand commands** to see their full prompts
|
||||
- **Customize prompts** (modifications are preserved across updates)
|
||||
|
||||
## Core Workflow (Recommended Order)
|
||||
|
||||
### 1. `/speckit.constitution` — Define Project Principles
|
||||
|
||||
Start here to establish your project's foundational values, constraints, and guidelines. The constitution guides all subsequent specifications and ensures consistency across features.
|
||||
|
||||
**Creates:** A constitution document with core principles, technical constraints, and team conventions.
|
||||
|
||||
### 2. `/speckit.specify` — Create Feature Specification
|
||||
|
||||
Define the feature you want to build with clear requirements, acceptance criteria, and boundaries.
|
||||
|
||||
**Creates:** A detailed feature specification with scope, requirements, and success criteria.
|
||||
|
||||
### 3. `/speckit.clarify` — Identify Gaps
|
||||
|
||||
Review your specification for ambiguities, missing details, and edge cases. The AI asks clarifying questions to strengthen the spec before implementation.
|
||||
|
||||
**Tip:** Run `/speckit.clarify` multiple times — each pass catches different gaps.
|
||||
|
||||
### 4. `/speckit.plan` — Implementation Planning
|
||||
|
||||
Convert your specification into a high-level implementation plan with phases and milestones.
|
||||
|
||||
**Creates:** A phased implementation roadmap with dependencies and risk areas.
|
||||
|
||||
### 5. `/speckit.tasks` — Generate Tasks
|
||||
|
||||
Break your plan into specific, actionable tasks with dependencies clearly mapped.
|
||||
|
||||
**Creates:** A dependency-ordered task list ready for execution.
|
||||
|
||||
### 6. `/speckit.implement` — Execute with Auto Run
|
||||
|
||||
**Maestro-specific command.** Converts your tasks into Auto Run documents that Maestro can execute autonomously. This bridges spec-kit's structured approach with Maestro's multi-agent capabilities.
|
||||
|
||||
**Creates:** Markdown documents in `Auto Run Docs/` with task checklists.
|
||||
|
||||
## Analysis & Quality Commands
|
||||
|
||||
### `/speckit.analyze` — Cross-Artifact Analysis
|
||||
|
||||
Verify consistency across your constitution, specifications, and tasks. Catches contradictions and gaps between documents.
|
||||
|
||||
### `/speckit.checklist` — Generate QA Checklist
|
||||
|
||||
Create a custom checklist for your feature based on the specification. Useful for QA, code review, and acceptance testing.
|
||||
|
||||
### `/speckit.taskstoissues` — Export to GitHub Issues
|
||||
|
||||
Convert your tasks directly into GitHub Issues. Requires `gh` CLI to be installed and authenticated.
|
||||
|
||||
## Getting Help
|
||||
|
||||
Run `/speckit.help` to get an overview of the workflow and tips for best results.
|
||||
|
||||
## Auto-Updates
|
||||
|
||||
Spec-Kit prompts are automatically synced from the [GitHub spec-kit repository](https://github.com/github/spec-kit):
|
||||
|
||||
1. Open **Settings → AI Commands**
|
||||
2. Click **Check for Updates**
|
||||
3. New commands and prompt improvements are downloaded
|
||||
4. Your custom modifications are preserved
|
||||
|
||||
The version number and last update date are shown at the top of the Spec Kit Commands section.
|
||||
|
||||
## Tips for Best Results
|
||||
|
||||
- **Start with constitution** — Even for small projects, defining principles helps maintain consistency
|
||||
- **Iterate on specifications** — Use `/speckit.clarify` multiple times to refine your spec
|
||||
- **Keep specs focused** — One feature per specification cycle works best
|
||||
- **Review before implementing** — Use `/speckit.analyze` to catch issues early
|
||||
- **Leverage parallelism** — With Maestro, run multiple spec-kit workflows simultaneously across different agents
|
||||
4
package-lock.json
generated
@@ -1,12 +1,12 @@
|
||||
{
|
||||
"name": "maestro",
|
||||
"version": "0.12.0",
|
||||
"version": "0.12.1",
|
||||
"lockfileVersion": 3,
|
||||
"requires": true,
|
||||
"packages": {
|
||||
"": {
|
||||
"name": "maestro",
|
||||
"version": "0.12.0",
|
||||
"version": "0.12.1",
|
||||
"hasInstallScript": true,
|
||||
"license": "AGPL 3.0",
|
||||
"dependencies": {
|
||||
|
||||
@@ -9127,6 +9127,33 @@ function MaestroConsoleInner() {
|
||||
});
|
||||
});
|
||||
}}
|
||||
onExportHtml={async (tabId: string) => {
|
||||
// Export tab conversation as HTML
|
||||
if (!activeSession) return;
|
||||
const tab = activeSession.aiTabs.find(t => t.id === tabId);
|
||||
if (!tab || !tab.logs || tab.logs.length === 0) return;
|
||||
|
||||
try {
|
||||
const { downloadTabExport } = await import('./utils/tabExport');
|
||||
await downloadTabExport(
|
||||
tab,
|
||||
{ name: activeSession.name, cwd: activeSession.cwd, toolType: activeSession.toolType },
|
||||
theme
|
||||
);
|
||||
addToast({
|
||||
type: 'success',
|
||||
title: 'Export Complete',
|
||||
message: 'Conversation exported as HTML.',
|
||||
});
|
||||
} catch (err) {
|
||||
console.error('Failed to export tab:', err);
|
||||
addToast({
|
||||
type: 'error',
|
||||
title: 'Export Failed',
|
||||
message: 'Failed to export conversation as HTML.',
|
||||
});
|
||||
}
|
||||
}}
|
||||
// Context warning sash settings (Phase 6)
|
||||
contextWarningsEnabled={contextManagementSettings.contextWarningsEnabled}
|
||||
contextWarningYellowThreshold={contextManagementSettings.contextWarningYellowThreshold}
|
||||
|
||||
@@ -194,6 +194,7 @@ interface MainPanelProps {
|
||||
onMergeWith?: (tabId: string) => void;
|
||||
onSendToAgent?: (tabId: string) => void;
|
||||
onCopyContext?: (tabId: string) => void;
|
||||
onExportHtml?: (tabId: string) => void;
|
||||
|
||||
// Context warning sash settings (Phase 6)
|
||||
contextWarningsEnabled?: boolean;
|
||||
@@ -250,6 +251,7 @@ export const MainPanel = React.memo(forwardRef<MainPanelHandle, MainPanelProps>(
|
||||
onMergeWith,
|
||||
onSendToAgent,
|
||||
onCopyContext,
|
||||
onExportHtml,
|
||||
// Context warning sash settings (Phase 6)
|
||||
contextWarningsEnabled = false,
|
||||
contextWarningYellowThreshold = 60,
|
||||
@@ -897,6 +899,7 @@ export const MainPanel = React.memo(forwardRef<MainPanelHandle, MainPanelProps>(
|
||||
onSendToAgent={onSendToAgent}
|
||||
onSummarizeAndContinue={onSummarizeAndContinue}
|
||||
onCopyContext={onCopyContext}
|
||||
onExportHtml={onExportHtml}
|
||||
showUnreadOnly={showUnreadOnly}
|
||||
onToggleUnreadFilter={onToggleUnreadFilter}
|
||||
onOpenTabSearch={onOpenTabSearch}
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
import React, { useState, useRef, useCallback, useEffect } from 'react';
|
||||
import { createPortal } from 'react-dom';
|
||||
import { X, Plus, Star, Copy, Edit2, Mail, Pencil, Search, GitMerge, ArrowRightCircle, Minimize2, Clipboard } from 'lucide-react';
|
||||
import { X, Plus, Star, Copy, Edit2, Mail, Pencil, Search, GitMerge, ArrowRightCircle, Minimize2, Clipboard, Download } from 'lucide-react';
|
||||
import type { AITab, Theme } from '../types';
|
||||
import { hasDraft } from '../utils/tabHelpers';
|
||||
|
||||
@@ -23,6 +23,8 @@ interface TabBarProps {
|
||||
onSummarizeAndContinue?: (tabId: string) => void;
|
||||
/** Handler to copy conversation context to clipboard */
|
||||
onCopyContext?: (tabId: string) => void;
|
||||
/** Handler to export tab as HTML */
|
||||
onExportHtml?: (tabId: string) => void;
|
||||
showUnreadOnly?: boolean;
|
||||
onToggleUnreadFilter?: () => void;
|
||||
onOpenTabSearch?: () => void;
|
||||
@@ -53,6 +55,8 @@ interface TabProps {
|
||||
onSummarizeAndContinue?: () => void;
|
||||
/** Handler to copy conversation context to clipboard */
|
||||
onCopyContext?: () => void;
|
||||
/** Handler to export tab as HTML */
|
||||
onExportHtml?: () => void;
|
||||
shortcutHint?: number | null;
|
||||
registerRef?: (el: HTMLDivElement | null) => void;
|
||||
hasDraft?: boolean;
|
||||
@@ -123,6 +127,7 @@ function Tab({
|
||||
onSendToAgent,
|
||||
onSummarizeAndContinue,
|
||||
onCopyContext,
|
||||
onExportHtml,
|
||||
shortcutHint,
|
||||
registerRef,
|
||||
hasDraft
|
||||
@@ -239,6 +244,12 @@ function Tab({
|
||||
setOverlayOpen(false);
|
||||
};
|
||||
|
||||
const handleExportHtmlClick = (e: React.MouseEvent) => {
|
||||
e.stopPropagation();
|
||||
onExportHtml?.();
|
||||
setOverlayOpen(false);
|
||||
};
|
||||
|
||||
const displayName = getTabDisplayName(tab);
|
||||
|
||||
// Browser-style tab: all tabs have borders, active tab "connects" to content
|
||||
@@ -455,6 +466,18 @@ function Tab({
|
||||
Mark as Unread
|
||||
</button>
|
||||
|
||||
{/* Export as HTML - only show if tab has logs */}
|
||||
{(tab.logs?.length ?? 0) >= 1 && onExportHtml && (
|
||||
<button
|
||||
onClick={handleExportHtmlClick}
|
||||
className="w-full flex items-center gap-2 px-2 py-1.5 rounded text-xs hover:bg-white/10 transition-colors"
|
||||
style={{ color: theme.colors.textMain }}
|
||||
>
|
||||
<Download className="w-3.5 h-3.5" style={{ color: theme.colors.textDim }} />
|
||||
Export as HTML
|
||||
</button>
|
||||
)}
|
||||
|
||||
{/* Context Management Section - divider and grouped options */}
|
||||
{(tab.agentSessionId || (tab.logs?.length ?? 0) >= 1) && (onMergeWith || onSendToAgent || onSummarizeAndContinue || onCopyContext) && (
|
||||
<div className="my-1 border-t" style={{ borderColor: theme.colors.border }} />
|
||||
@@ -535,6 +558,7 @@ export function TabBar({
|
||||
onSendToAgent,
|
||||
onSummarizeAndContinue,
|
||||
onCopyContext,
|
||||
onExportHtml,
|
||||
showUnreadOnly: showUnreadOnlyProp,
|
||||
onToggleUnreadFilter,
|
||||
onOpenTabSearch
|
||||
@@ -733,6 +757,7 @@ export function TabBar({
|
||||
onSendToAgent={onSendToAgent && tab.agentSessionId ? () => onSendToAgent(tab.id) : undefined}
|
||||
onSummarizeAndContinue={onSummarizeAndContinue && (tab.logs?.length ?? 0) >= 5 ? () => onSummarizeAndContinue(tab.id) : undefined}
|
||||
onCopyContext={onCopyContext && (tab.logs?.length ?? 0) >= 1 ? () => onCopyContext(tab.id) : undefined}
|
||||
onExportHtml={onExportHtml && (tab.logs?.length ?? 0) >= 1 ? () => onExportHtml(tab.id) : undefined}
|
||||
shortcutHint={!showUnreadOnly && originalIndex < 9 ? originalIndex + 1 : null}
|
||||
hasDraft={hasDraft(tab)}
|
||||
registerRef={(el) => {
|
||||
|
||||