with one click
explorbot-debug
// Debug failed Explorbot interactions. Analyzes Langfuse traces or log files to find why tests failed and suggests Knowledge fixes. Use when this capability is needed.
// Debug failed Explorbot interactions. Analyzes Langfuse traces or log files to find why tests failed and suggests Knowledge fixes. Use when this capability is needed.
[HINT] Download the complete skill directory including SKILL.md and all related files
| name | explorbot-debug |
| description | Debug failed Explorbot interactions. Analyzes Langfuse traces or log files to find why tests failed and suggests Knowledge fixes. Use when this capability is needed. |
| metadata | {"author":"testomatio"} |
Debug failed Explorbot test sessions by analyzing execution traces.
Goal: Get the explorbot.log and the corresponding Langfuse trace JSON.
If the user provides a Langfuse trace ID (a hex string like 0eaf1adf73deff451cbad7effaaaf8a8), fetch it directly:
bun .claude/skills/explorbot-debug/langfuse-export.ts <trace-id>
This fetches the trace and all its observations in one step. Skip to Step 1.3 Load and Correlate.
If no trace ID is provided, read the end of output/explorbot.log to determine the time range of the last session.
tail -n 1000 output/explorbot.log
Identify:
=== ExplorBot Session Started timestamp.Key log patterns to look for:
=== ExplorBot Session Started -- session start[STEP] I.amOnPage(...) -- navigationAI Navigator resolving state -- navigator AI triggered[ERROR] Attempt failed -- failed browser actionsTesting scenario: -- test startCheck if a recent Langfuse export already exists and covers the session time:
ls -lt output/langfuse-export-*.json | head -n 1
If a recent JSON file exists (created after the session start):
If NO recent JSON file exists:
# <range> can be 30m, 1h, or a trace ID
bun .claude/skills/explorbot-debug/langfuse-export.ts <range>
Note: If the script fails (e.g., due to missing credentials or network issues), proceed with Log Analysis Only.You should now have:
output/explorbot.log (Browser/System events)output/langfuse-export-....json (AI reasoning/Prompts) - Optional but recommendedCrucial Step: Correlate the logs with the JSON.
| Source | Contains |
|---|---|
| Langfuse JSON | AI prompts, AI responses, tool call inputs/outputs, token usage |
output/explorbot.log | Browser startup, navigation steps, errors, state transitions |
Match events by timestamp:
=== ExplorBot Session Started in log.navigator.loop traces in JSON with log AI Navigator resolving state.tester.loop traces in JSON with log Testing scenario:.Useful jq commands:
jq '.[].name' <file> # list trace names
jq '[.[] | select(.tags | index("researcher"))]' <file> # filter by tag
jq '.[0].observations[] | {name, startTime, level}' <file> # observation summary
jq '[.[].observations[] | select(.type == "GENERATION") | {name, model, input: (.input | length), output: (.output | length)}]' <file>
If Langfuse is not configured or no JSON available, read output/explorbot.log only.
This gives browser-level detail but no AI prompts/responses.
Analyze using both sources when available:
Look for mismatches between what the AI decided (JSON) and what actually happened (logs). For example: AI says "click succeeded" in its response, but log shows an error after the click.
Analyze the session for these failure patterns:
AI made wrong decisions because it lacked information about the page.
Symptoms:
Example: AI clicked "Delete" in wrong table row because it didn't know about container context.
AI made incorrect assumptions based on how prompts were structured.
Symptoms:
Example: AI tried to create user before logging in because prompt didn't mention auth requirement.
AI picked incorrect tool for the situation.
Symptoms:
click() when form() was neededtype() without focusing element firstpressKey() for multi-character inputExample: AI used standard type() on a rich text editor that needed special handling.
Based on the identified issues, suggest creating a Knowledge file.
---
url: /path/pattern/*
wait: 1 # optional: seconds to wait after page load
---
[Instructions for AI when visiting this page]
Recommend general patterns over specific URLs:
| Instead of | Use |
|---|---|
/users/123 | /users/* |
/projects/my-proj/settings | /projects/*/settings |
/admin/users/edit/5 | /admin/users/* |
This way knowledge applies to all similar pages.
1. Credentials (if auth needed):
Login credentials:
- email: admin@example.com
- password: secret123
2. Framework quirks:
## Framework Notes
App uses [Framework]. Avoid auto-generated IDs.
Prefer ARIA selectors or data-test attributes.
3. Rich Text Editors:
Editors like Monaco, TinyMCE, CKEditor, Quill, ProseMirror, or Block Editors often need special handling:
## Text Editor
The content editor requires special interaction:
\`\`\`
[Provide CodeceptJS code for this specific editor]
[May need: iframe switching, click to focus, clear content, etc.]
\`\`\`
Analyze the editor type and provide appropriate instructions. Common patterns:
I.switchTo() before interaction4. Custom Controls:
Dropdowns, sliders, date pickers, and custom widgets often need guidance:
## Custom Dropdown
This dropdown doesn't use standard <select>.
Click to open, then click option by text:
\`\`\`
I.click('.dropdown-trigger')
I.click('Option Text', '.dropdown-menu')
\`\`\`
## Slider Control
Slider requires drag or keyboard:
\`\`\`
I.click('.slider-handle')
I.pressKey('ArrowRight') // Increase value
\`\`\`
## Date Picker
Calendar popup needs specific interaction:
\`\`\`
I.click('.date-input')
I.click('15', '.calendar-popup') // Select day
\`\`\`
5. UI explanations:
## Form Behavior
Submit button is disabled until all required fields valid.
Error messages appear below each field.
6. Business context:
## User Roles
- Admin: can create/delete users
- Editor: can only edit content
- Viewer: read-only access
Test scenarios should respect these permissions.
7. Container disambiguation:
## Table Actions
Each row has Edit/Delete buttons. Always use container:
I.click('Delete', '.user-row-{id}')
Generate the knowledge file content and ask user to save it:
# Save to knowledge directory
cat > knowledge/<page_name>.md << 'EOF'
---
url: /your/pattern/*
---
[Generated content]
EOF
Or use Explorbot's CLI:
explorbot know "/url/pattern/*" "Your knowledge description"
After knowledge is added, suggest:
When these are detected in failed sessions, suggest adding knowledge:
| Control Type | Common Issues | Knowledge Needed |
|---|---|---|
| Rich text editors | Can't type, wrong focus | Editor-specific interaction code |
| Custom dropdowns | Can't select, element not found | Open/select sequence |
| Date/time pickers | Can't set value | Calendar interaction steps |
| Sliders/ranges | Can't change value | Drag or keyboard approach |
| File uploads | Can't attach | Input selector or drop zone |
| Autocomplete | Suggestions not selected | Type + wait + select pattern |
| Modals/dialogs | Actions outside blocked | Wait for modal, close sequence |
| Tabs/accordions | Content hidden | Click to expand first |
| Drag & drop | Can't reorder | Specific drag approach |
| Canvas elements | Can't interact | Coordinate-based clicks |
If you have browser tools available (Playwright MCP, browser agent, or similar), you can:
When you find a working approach, write it as CodeceptJS code for the knowledge file.
Available Commands:
// Clicking
I.click('Button Text'); // By text
I.click({ role: 'button', text: 'Submit' }); // By ARIA (preferred)
I.click('Submit', '.modal-content'); // With container context
I.click('#submit-btn'); // By CSS
I.click('//form//button[@type="submit"]'); // By XPath
// Filling fields
I.fillField('Username', 'john'); // By label/name/placeholder
I.fillField({ role: 'textbox', text: 'Email' }, 'test@example.com');
// Typing (into focused element)
I.type('text to enter'); // Types into active element
// Key presses
I.pressKey('Enter');
I.pressKey('Escape');
I.pressKey(['Control', 'a']); // Select all
I.pressKey(['Meta', 'a']); // Cmd+A on Mac
// Dropdowns
I.selectOption('Country', 'United States');
I.selectOption({ role: 'combobox', text: 'Select' }, 'Option');
// Iframes
I.switchTo('#editor-iframe'); // Enter iframe
I.switchTo(); // Exit iframe
Locator Priority:
{ role: 'button', text: 'Save' }'Login'I.click('Delete', '.user-row-123')'//form[@id="login"]//button'Avoid:
#ember123, #react-select-2)//div[2]/div[3]):contains, :first)I.switchTo('.editor-container iframe')
I.click('//body')
I.pressKey(['Control', 'a'])
I.type('New content here')
I.switchTo()
I.click('.dropdown-trigger')
I.click('Option Text', '.dropdown-menu')
| Issue Type | Knowledge Solution |
|---|---|
| Wrong element clicked | Add container/disambiguation rules |
| Form not submitted | Add CodeceptJS code block for flow |
| Auth required | Add credentials |
| Iframe content | Add switchTo() instructions |
| Dynamic IDs | Add "avoid these selectors" warning |
| Timing issues | Add wait: N to frontmatter |
| Business logic | Explain expected behavior |
| Custom control | Provide interaction code block |
Converted and distributed by TomeVault — claim your Tome and manage your conversions.