Subclass Modal with snapshotValues() for: value source editor, audio source editor, add device, profile editor, capture template, stream editor, and PP template modals. Close/cancel now triggers discard confirmation when form has unsaved changes. Document the convention in CLAUDE.md. Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
5.7 KiB
Claude Instructions for WLED Screen Controller
CRITICAL: Git Commit and Push Policy
🚨 NEVER CREATE COMMITS WITHOUT EXPLICIT USER APPROVAL 🚨
🚨 NEVER PUSH TO REMOTE WITHOUT EXPLICIT USER APPROVAL 🚨
Strict Rules
- DO NOT create commits automatically after making changes
- DO NOT commit without being explicitly instructed by the user
- DO NOT push to remote repository without explicit instruction
- ALWAYS WAIT for the user to review changes and ask you to commit
- ALWAYS ASK if you're unsure whether to commit
Workflow
- Make code changes as requested
- STOP - Inform user that changes are complete
- WAIT - User reviews the changes
- ONLY IF user explicitly says "commit" or "create a commit":
- Stage the files with
git add - Create the commit with a descriptive message
- STOP - Do NOT push
- Stage the files with
- ONLY IF user explicitly says "push" or "commit and push":
- Push to remote repository
What Counts as Explicit Approval
✅ YES - These mean you can commit:
- "commit"
- "create a commit"
- "commit these changes"
- "git commit"
✅ YES - These mean you can push:
- "push"
- "commit and push"
- "push to remote"
- "git push"
❌ NO - These do NOT mean you should commit:
- "that looks good"
- "thanks"
- "perfect"
- User silence after you make changes
- Completing a feature/fix
Example Bad Behavior (DON'T DO THIS)
❌ User: "Fix the MSS engine test issue"
❌ Claude: [fixes the issue]
❌ Claude: [automatically commits without asking] <-- WRONG!
Example Good Behavior (DO THIS)
✅ User: "Fix the MSS engine test issue"
✅ Claude: [fixes the issue]
✅ Claude: "I've fixed the MSS engine test issue by adding auto-initialization..."
✅ [WAITS FOR USER]
✅ User: "Looks good, commit it"
✅ Claude: [now creates the commit]
IMPORTANT: Auto-Restart Server on Code Changes
Whenever server-side Python code is modified (any file under /server/src/ excluding /server/src/wled_controller/static/), automatically restart the server so the changes take effect immediately. Do NOT wait for the user to ask for a restart.
No restart needed for frontend-only changes. Files under /server/src/wled_controller/static/ (HTML, JS, CSS, JSON locale files) are served directly by FastAPI's static file handler — changes take effect on the next browser page refresh without restarting the server.
Restart procedure
Use the PowerShell restart script — it reliably stops only the server process and starts a new detached instance:
powershell -ExecutionPolicy Bypass -File "c:\Users\Alexei\Documents\wled-screen-controller\server\restart.ps1"
Do NOT use Stop-Process -Name python (kills unrelated Python processes like VS Code extensions) or bash background & jobs (get killed when the shell session ends).
Default Config & API Key
The server configuration is in /server/config/default_config.yaml. The default API key for development is development-key-change-in-production (label: dev). The server runs on port 8080 by default.
Project Structure
This is a monorepo containing:
/server- Python FastAPI backend (seeserver/CLAUDE.mdfor detailed instructions)/client- Future frontend client (if applicable)
Working with Server
For detailed server-specific instructions (restart policy, testing, etc.), see:
server/CLAUDE.md
UI Conventions for Dialogs
Hints
Every form field in a modal should have a hint. Use the .label-row wrapper with a ? toggle button:
<div class="form-group">
<div class="label-row">
<label for="my-field" data-i18n="my.label">Label:</label>
<button type="button" class="hint-toggle" onclick="toggleHint(this)" title="?">?</button>
</div>
<small class="input-hint" style="display:none" data-i18n="my.label.hint">Hint text</small>
<input type="text" id="my-field">
</div>
Add hint text to both en.json and ru.json locale files using a .hint suffix on the label key.
Select dropdowns
Do not add placeholder options like -- Select something --. Populate the <select> with real options only and let the first one be selected by default.
Modal dirty check (discard unsaved changes)
Every editor modal must have a dirty check so closing with unsaved changes shows a "Discard unsaved changes?" confirmation. Use the Modal base class pattern from js/core/modal.js:
-
Subclass Modal with
snapshotValues()returning an object of all tracked field values:class MyEditorModal extends Modal { constructor() { super('my-modal-id'); } snapshotValues() { return { name: document.getElementById('my-name').value, // ... all form fields }; } onForceClose() { // Optional: cleanup (reset flags, clear state, etc.) } } const myModal = new MyEditorModal(); -
Call
modal.snapshot()after the form is fully populated (aftermodal.open()). -
Close/cancel button calls
await modal.close()— triggers dirty check + confirmation. -
Save function calls
modal.forceClose()after successful save — skips dirty check. -
For complex/dynamic state (filter lists, schedule rows, conditions), serialize to JSON string in
snapshotValues().
The base class handles: isDirty() comparison, confirmation dialog, backdrop click, ESC key, focus trapping, and body scroll lock.
General Guidelines
- Always test changes before marking as complete
- Follow existing code style and patterns
- Update documentation when changing behavior
- Write clear, descriptive commit messages when explicitly instructed
- Never make commits or pushes without explicit user approval