Skip to content

[FEATURE] Add Debugging Panel to Inspect App State, Variables, and Errors #523

Open
@amrutha97

Description

@amrutha97

Goal
Introduce a Debugging Panel component in the Preswald frontend that displays the live app state, tracked variables, and error messages to assist developers in real-time debugging and iteration.


📌 Motivation

Preswald abstracts away much of the complexity in app state management and component interactions. However, when things go wrong (e.g. a workflow fails, a component isn't rendering, or variable values are unexpected), there's currently no visibility into the internal state of the app. This makes debugging opaque and time-consuming.

A built-in debugging panel will:

  • Surface variables and their current values
  • Show error messages and stack traces in context
  • Display execution flow and component states
  • Improve developer confidence and iteration speed

✅ Acceptance Criteria

  • Add a toggleable Debug Panel (DebugPanel.jsx) in the frontend (floating bottom-right or sidebar)
  • Display:
    • Tracked variables (e.g. from Service.get_state())
    • Component hierarchy and props
    • Error messages and stack traces (from WebSocket/API layer)
    • Current DAG execution status (optional)
  • Provide a debug=True flag in preswald.toml or environment variable to enable/disable panel
  • Capture and display exceptions in workflows, Python code, or frontend component resolution
  • Ensure minimal performance impact when disabled
  • Style for readability and collapsibility (e.g. Tailwind + accordion view)

🛠 Implementation Plan

1. Backend – Surface State and Errors

In preswald/service.py, expose get_state_snapshot():

def get_state_snapshot(cls):
    return {
        "components": cls.get_instance().components,
        "variables": cls.get_instance().variable_store,
        "errors": cls.get_instance().error_log,
        "execution_graph": cls.get_instance().workflow_graph.serialize(),
    }

Update server_service.py to stream state snapshots and errors over WebSocket via special __debug__ channel when debug=True.


2. Frontend – Add Debug Panel UI

Create frontend/src/components/common/DebugPanel.jsx:

import React, { useState, useEffect } from 'react';
import { Card } from '@/components/ui/card';
import { ScrollArea } from '@/components/ui/scroll-area';
import { Button } from '@/components/ui/button';

const DebugPanel = ({ state }) => {
  const [visible, setVisible] = useState(false);

  return (
    <div className="fixed bottom-4 right-4 z-50">
      <Button onClick={() => setVisible(!visible)} className="mb-2">
        {visible ? "Hide Debug" : "Show Debug"}
      </Button>
      {visible && (
        <Card className="w-[400px] h-[500px] overflow-hidden shadow-lg border bg-white dark:bg-gray-900 text-sm">
          <ScrollArea className="p-4 h-full">
            <pre className="whitespace-pre-wrap">{JSON.stringify(state, null, 2)}</pre>
          </ScrollArea>
        </Card>
      )}
    </div>
  );
};

export default DebugPanel;

Mount this component inside App.jsx only if debugMode is true.


3. WebSocket Layer – Stream State Updates

Update websocket.js to subscribe to __debug__ messages and store in global state. Example:

socket.onmessage = (event) => {
  const msg = JSON.parse(event.data);
  if (msg.channel === "__debug__") {
    window.__DEBUG_STATE__ = msg.payload;
  }
};

4. Toggle Debug Panel Based on Flag

Allow enabling via:

  • preswald.toml:
[debug]
enabled = true
  • Or ENV:
PRESWALD_DEBUG=true

Expose this flag from backend via branding/metadata payload (/api/config).


📄 Example Output

{
  "variables": {
    "threshold": 0.75,
    "selected_region": "Europe"
  },
  "components": [
    {"id": "slider-abc123", "type": "slider", "label": "Threshold"},
    {"id": "table-def456", "type": "table", "rows": 200}
  ],
  "errors": [
    {"timestamp": "2025-03-23T19:42Z", "message": "KeyError: 'value'"}
  ]
}

📚 Documentation Updates

  • Add docs/coreconcepts/debugging.mdx
  • Mention in CLI/dev tools docs
  • Add a config flag section in preswald.toml docs

🧪 Testing Plan

  • Trigger runtime Python errors in workflows
  • Confirm they surface in Debug Panel
  • Add/modify variables and ensure they update live
  • Confirm debug panel does not show in debug=false mode

🧩 Files Involved

  • preswald/service.py
  • preswald/server_service.py
  • frontend/src/components/common/DebugPanel.jsx
  • frontend/src/components/App.jsx
  • websocket.js

💡 Future Enhancements

  • Interactive state editing in debug mode (like Redux DevTools)
  • Toggle logs per component
  • DAG viewer with live execution steps
  • Attach profiler/trace mode

Metadata

Metadata

Assignees

No one assigned

    Labels

    enhancementNew feature or request

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions