Skip to content

bisos-web/csPlayer-webUi

Repository files navigation

BISOS Command Service CLI Web UI - csPlayer Design Document

About csLineInvoker Web User Interface

A unified dashboard orchestrating multiple command-line and infrastructure services through an iframe-based architecture. Provides seamless integration between csLineInvoker (command execution), Airflow (workflow orchestration), and Grafana (metrics visualization) through a centralized Gatsby-based dashboard.

Built with Gatsby 5, React 18, Tailwind CSS 3.4.17, PostMessage API, and a Pub/Sub event system for cross-service communication.

Table of Contents

Project Overview

Vision

The BISOS Command Service CLI Web UI is a unified dashboard for managing, monitoring, and orchestrating multiple command-line services and infrastructure tools. It provides a single point of access to:

  • csLineInvoker (WebCliGui): Execute and monitor command-line tasks across servers
  • Airflow: Schedule and orchestrate complex workflows
  • Grafana: Visualize and monitor system metrics

The vision is to create a cohesive ecosystem where these independent services work together seamlessly through an orchestration layer.

Architecture Approach

Instead of merging multiple frontend projects, we take a modular iframe orchestration approach:

  1. Independent Services: Each service (csLineInvoker, Airflow, Grafana) remains independent
    • Maintains its own codebase, dependencies, technology stack
    • Runs on separate ports (25002, 8080, 3000)
    • Can be updated/deployed independently
  2. Orchestration Host: Gatsby-based dashboard (csLineInvoker-webUi) serves as the orchestrator
    • Runs on port 25001
    • Embeds each service in its own iframe
    • Manages cross-service communication via PostMessage API
  3. Trusted Ecosystem: All services are internal, under user control
    • No signature validation needed
    • Simplified PostMessage security model
    • Focus on functional communication, not security perimeter

Key Technologies

  • Gatsby 5.x: Static site generator for dashboard
  • React 18.x: Component framework
  • Tailwind CSS 3.4.17: Utility-first styling
  • PostMessage API: Cross-iframe communication
  • Pub/Sub Pattern: Message bus for event routing
  • Node.js 22.21.1: Runtime environment
  • Environment Variables: Runtime configuration via .env files

Configuration

Port Number and Domain Assignments – bisos.banna

Port numbers and domains for this application are assigned through bisos.banna (BISOS Assigned Names and Numbers Authority).

To obation the relevant port numbers:

pip install bisos.banna
pipx install bisos.banna
bannaInfo.cs -i bannaTcpPortsList | pyLiteralToBash.cs -i stdinToBlack

Development Port Numbers

Relevant assigned port numbers are:

{
    "csPlayerPerf_dev": TcpPortNuInfo(
        portNu=23501,
        portName="csPlayerPerf_dev",
        portDescription="Backend API performer service (development)",
    ),
    "csPlayerUi_dev": TcpPortNuInfo(
        portNu=25001,
        portName="csPlayerUi_dev",
        portDescription="Reveal Gatsby site wrapping csLineInvoker and others (development)",
    ),
    "csLineInvoker_dev": TcpPortNuInfo(
        portNu=25002,
        portName="csLineInvoker_dev",
        portDescription="Line invoker service (development)",
    ),
}

Production .here Fake Domains

Relevant assigned .here domains as they apear in /etc/hosts are:

127.0.0.100  csPlayerPerf.here
127.0.0.101  csLineInvoker.here
127.0.0.102  csPlayerUi.here

Service URLs Configuration

Overview

Service URLs are configured via environment variables using Gatsby’s built-in dotenv support. This allows different URLs for development and production without code changes.

Environment Files

Gatsby automatically loads environment-specific files:

  • .env.development - Used by `npm run develop` (development mode)
  • .env.production - Used by `npm run build` (production mode)
  • .env - Fallback if environment-specific file not found

Variable Naming Convention

All service URL variables use the GATSBY_ prefix (required by Gatsby to expose variables to the browser):

GATSBY_CSLINE_INV_URL=http://csLineInvoker.here        # Invoker: Command submission UI
GATSBY_CSPLAYER_PERF_URL=http://csLineInvokerPerf.here      # Performer: Command execution engine
GATSBY_AIRFLOW_URL=http://localhost:8080               # Workflow orchestration
GATSBY_GRAFANA_URL=http://localhost:3000               # Metrics visualization

Configuration Files Content

**Development (.env.development):**

GATSBY_CSLINE_INV_URL=http://localhost:25002
GATSBY_CSPLAYER_PERF_URL=http://localhost:23501
GATSBY_AIRFLOW_URL=http://localhost:8080
GATSBY_GRAFANA_URL=http://localhost:3000

**Production (.env.production):**

GATSBY_CSLINE_INV_URL=http://csLineInvoker.here
GATSBY_CSPLAYER_PERF_URL=http://csPlayerPerf.here
GATSBY_AIRFLOW_URL=http://localhost:8080
GATSBY_GRAFANA_URL=http://localhost:3000

Service Configuration Utility

Location: src/utils/serviceConfig.js

The configuration utility centralizes URL management and provides fallback defaults:

import { getServiceUrl } from "../utils/serviceConfig"

// Get specific service URL
const cslineInvokerUrl = getServiceUrl('cslineInvoker')
const csplayerPerformerUrl = getServiceUrl('csplayerPerformer')
const airflowUrl = getServiceUrl('airflow')
const grafanaUrl = getServiceUrl('grafana')

// Debug: view all URLs in browser console
window.__serviceUrls()

Usage in Components

All iframe pages now use the service configuration utility:

  • src/pages/csPlayer.js - Invoker UI (cslineInvoker)
  • src/pages/csLineInvokerBackEnd.js - Performer API (csplayerPerformer)
  • src/pages/modPlayerFacter.js - Invoker variant (cslineInvoker)
  • src/pages/modPlayerSoncli.js - Invoker variant (cslineInvoker)
  • src/pages/airflow.js - Airflow service
  • src/pages/grafana.js - Grafana service

Invoker/Performer Abstraction

RPC/Web Services Perspective

The csLineInvoker ecosystem uses the Invoker/Performer abstraction pattern from RPC and Web Services architecture:

  • CSLINE_INV (Invoker): Client-facing UI that builds and invokes commands
    • Narrow scope: command-line focused
    • User interface for command building and submission
    • Multiple instances possible (modPlayerFacter, modPlayerSoncli, csLineInvoker)
  • CSPLAYER_PERF (Performer): Execution engine with broader scope
    • Server-side command executor
    • Serves multiple invokers and clients
    • Single point of command execution
    • Can be scaled independently from invokers

Architecture Diagram

┌──────────────────────────────────────────────────────────────┐
│         CSPLAYER_PERF (Performer)                            │
│    Single execution engine with broader scope                │
│                                                              │
│  Executes commands for:                                     │
│  - CSLINE_INV (current invoker)                             │
│  - Other invokers (potential)                               │
│  - Direct API calls                                         │
│  - Batch operations                                         │
└──────────────────────────────────────────────────────────────┘
         ▲                                    ▲
         │                                    │
    ┌────┴──────────┐              ┌─────────┴────────┐
    │  CSLINE_INV   │              │  Other Invokers  │
    │   (narrow     │              │   (potential)    │
    │   scope)      │              │                  │
    └───────────────┘              └──────────────────┘

Development Setup and Usage

csPlayerPerf – Django CS Player Performer

mkdir -p /bisos/git/bxRepos/cliGui
git clone git@github:cliGui/webCliGui.git
cd /bisos/git/bxRepos/cliGui/webCliGui/server
# Set things up and enable the libraries
python manage.py runserver 23001
# visit http://localhost:23501/admin

csLineInvoker – React App – Command-Line Constructor and Executer

cd /bisos/git/bxRepos/cliGui/webCliGui
npm run watch
# visit http://localhost:25002

csPlayer – Gatsby-React App – CS Player Wrapper

mkdir -p /bisos/git/bxRepos/bisos-web
git clone git@github:bisos-web/csPlayer-webUi
cd /bisos/git/bxRepos/bisos-web/csPlayer-webUi
# Set things up 
npm run develop 
# visit http://localhost:25001

From within the csPlayer app you should now be able to navigate to csLineInvoker and csPlayerPerf.

Architecture

System Design

┌──────────────────────────────────────────────────────────────┐
│                   BISOS Dashboard (Gatsby)                   │
│                     localhost:25001                           │
│                                                              │
│  ┌────────────────────────────────────────────────────────┐ │
│  │              Orchestration Layer                       │ │
│  │                                                        │ │
│  │  ┌──────────────────────────────────────────────────┐ │ │
│  │  │  Message Bus (messageBus.js)                     │ │ │
│  │  │  - Central Pub/Sub system                        │ │ │
│  │  │  - Routes events between services                │ │ │
│  │  │  - Maintains event history                       │ │ │
│  │  │  - Exposed via window.__messageBus              │ │ │
│  │  └──────────────────────────────────────────────────┘ │ │
│  │           ▲          ▲          ▲                      │ │
│  │  ┌────────┴──────────┼──────────┴────────────────────┐ │ │
│  │  │  Iframe Adapter (iframeAdapter.js)               │ │ │
│  │  │  - PostMessage API handler                       │ │ │
│  │  │  - Iframe registration & lifecycle               │ │ │
│  │  │  - Message routing to bus                        │ │ │
│  │  │  - Exposed via window.__iframeAdapter           │ │ │
│  │  └────────┬──────────┬──────────┬────────────────────┘ │ │
│  └───────────┼──────────┼──────────┼────────────────────────┘ │
│              │          │          │                          │
└──────────────┼──────────┼──────────┼──────────────────────────┘
               │          │          │
        ┌──────▼──┐  ┌──────▼──┐  ┌──▼──────┐
        │csLineInvoker │  │ Airflow │  │ Grafana │
        │ iframe  │  │ iframe  │  │ iframe  │
        │ :25002   │  │ :8080   │  │ :3000   │
        └─────────┘  └─────────┘  └─────────┘

Component Services

ServicePortRoleTechnology
csLineInvoker25002Command execution & monitoringReact + Django
Airflow8080Workflow orchestrationPython + Flask
Grafana3000Metrics & visualizationGo + Node

Communication Model

Parent → Child (Commands)

Dashboard sends commands to embedded services:

Parent Action → messageBus.publish() → iframeAdapter → PostMessage → Service iframe

Child → Parent (Events)

Services report events back to dashboard:

Service iframe → window.parent.postMessage() → iframeAdapter → messageBus → Dashboard subscribers

Orchestration Layer

PostMessage API

Standard browser API for cross-origin, cross-frame communication. Used because:

  • Works across iframe boundaries
  • Doesn’t require shared origin
  • Native browser support (no dependencies)
  • Trusted ecosystem model (no validation needed)

Message Bus

Location

src/utils/messageBus.js (130 lines)

Key Methods

  • messageBus.subscribe(eventName, callback, service)
    • Register listener for an event
    • Returns unsubscribe function
  • messageBus.publish(eventName, data, sender)
    • Broadcast event to all subscribers
    • Logs to event history
  • messageBus.getSubscribers()
    • Debug: view all listeners
  • messageBus.getEventLog()
    • Debug: view recent events (last 100)

Exposed to Console

  • window.__messageBus: Direct message bus access
  • window.__messageBusDebug.subscribers(): View listeners
  • window.__messageBusDebug.log(): View event history
  • window.__messageBusDebug.print(): Pretty-print log

Iframe Adapter

Location

src/utils/iframeAdapter.js (180 lines)

Key Functions

  • registerIframe(serviceName, element)
    • Register an iframe with the orchestration system
    • Starts listening for PostMessage events from that iframe
  • sendToIframe(serviceName, eventName, data)
    • Send message to specific iframe via PostMessage
  • getIframeStatus()
    • Debug: check connection status of all iframes

Exposed to Console

  • window.__iframeAdapter: Direct adapter access
  • window.__iframeAdapter.status(): Check iframe connections
  • window.__iframeAdapter.registry(): View registered iframes
  • window.__iframeAdapter.send(service, event, data): Send test messages

Event System

Location

src/utils/orchestrationEvents.js (40 lines)

Purpose

Central registry of all events the system supports. Ensures consistency across parent and child implementations.

Events by Service

csLineInvoker Events

Parent → csLineInvoker Commands:

  • csLineInvoker:filterChanged - User changed filters
  • csLineInvoker:refreshTasks - Refresh task list
  • csLineInvoker:executeCommand - Execute command

csLineInvoker → Parent Events:

  • csLineInvoker:taskExecuted - Task completed successfully
  • csLineInvoker:taskFailed - Task failed with error
  • csLineInvoker:statusUpdated - Status changed (idle → executing)

Airflow Events (Ready to Add)

Parent → Airflow Commands:

  • airflow:triggerDag - Trigger workflow
  • airflow:pauseDag - Pause workflow

Airflow → Parent Events:

  • airflow:dagTriggered - Workflow triggered
  • airflow:dagStatusChanged - Workflow status changed

Grafana Events (Ready to Add)

Parent → Grafana Commands:

  • grafana:updateDashboard - Switch dashboard
  • grafana:updateTimeRange - Change time range

Grafana → Parent Events:

  • grafana:panelDataLoaded - Panel data ready

Service Integration

csLineInvoker (WebCliGui) Integration

Status: Phase 1 - Parent Ready, Awaiting Child Integration

The parent (Gatsby dashboard) is fully set up to communicate with csLineInvoker. The csLineInvoker iframe needs to be integrated.

Parent-Side Implementation (Complete ✓)

Location: src/pages/csPlayer.js

Child-Side Implementation (Template Provided)

Location: src/templates/csLineInvokerClient.template.js (Ready to copy to webCliGui)

Key functions to implement in csLineInvoker/webCliGui:

  • initializeOrchestration() - Call on app startup
  • sendToParent(eventName, data) - Send events to parent
  • onMessageFromParent(eventName, callback) - Listen for commands

Integration Checklist

  • [ ] Copy csLineInvokerClient.template.js to webCliGui
  • [ ] Import initializeOrchestration() in main app component
  • [ ] Call initializeOrchestration() in useEffect on app load
  • [ ] Replace task completion handlers to use sendToParent()
  • [ ] Test: Parent should show ready: true in window.__iframeAdapter.status()

Airflow Integration

Status: Phase 2 - Ready to Begin

The infrastructure supports Airflow integration with identical pattern to csLineInvoker.

Parent-Side (Template Ready)

Similar to csLineInvoker:

  1. Create or enhance src/pages/airflow.js
  2. Register iframe: registerIframe('airflow', iframeElement)
  3. Subscribe to events: messageBus.subscribe(ORCHESTRATION_EVENTS.AIRFLOW_*)

Child-Side (Template Reusable)

Airflow will use same pattern as csLineInvoker:

  1. Copy csLineInvokerClient.template.js pattern to Airflow UI
  2. Call initializeOrchestration() on startup
  3. Send events when workflows trigger/complete

Grafana Integration

Status: Phase 3 - Ready to Plan

Like Airflow, Grafana follows the same integration pattern.

Considerations

  • Grafana UI is read-heavy (monitoring focus)
  • Communication primarily Parent → Grafana (dashboard switching, time range changes)
  • Events from Grafana less frequent than csLineInvoker/Airflow

Implementation Status

Phase 1: Complete ✓

Infrastructure Built

  • [x] Message bus system (messageBus.js)
  • [x] Iframe adapter (iframeAdapter.js)
  • [x] Event registry (orchestrationEvents.js)
  • [x] csLineInvoker page integrated (src/pages/csPlayer.js)
  • [x] Airflow page created (src/pages/airflow.js)
  • [x] Grafana page created (src/pages/grafana.js)
  • [x] Explore landing page (src/pages/explore.js)

Documentation Created

  • [x] API reference (ORCHESTRATION.md)
  • [x] Setup guide (ORCHESTRATION_SETUP.md)
  • [x] Testing guide (TESTING_GUIDE.md)
  • [x] File manifest (FILE_MANIFEST.md)
  • [x] Design document (README.org)

Build Quality

  • [x] Zero compilation errors
  • [x] Zero JavaScript errors
  • [x] Gatsby dev server running stable

Phase 2: Pending

csLineInvoker Integration

  • [ ] Integrate csLineInvokerClient code into webCliGui
  • [ ] Call initializeOrchestration() on app startup
  • [ ] Update task handlers to send events via sendToParent()
  • [ ] Test full parent-child communication

Airflow Integration

  • [ ] Create parent-side integration in Airflow page
  • [ ] Develop Airflow iframe client code
  • [ ] Implement workflow trigger communication

Phase 3: Future

Grafana Integration

  • [ ] Integrate Grafana iframe with orchestration
  • [ ] Implement dashboard/time range synchronization

Development Guide

Project Structure

csLineInvoker-webUi/
├── src/
│   ├── pages/
│   │   ├── index.js                    # Homepage with service overview
│   │   ├── csPlayer.js                 # csLineInvoker iframe page (invoker, with config)
│   │   ├── csLineInvokerBackEnd.js          # Django performer API admin page (with config)
│   │   ├── modPlayerFacter.js          # Alternative invoker variant (with config)
│   │   ├── modPlayerSoncli.js          # Alternative invoker variant (with config)
│   │   ├── airflow.js                  # Airflow iframe page (with config)
│   │   ├── grafana.js                  # Grafana iframe page (with config)
│   │   ├── explore.js                  # Resource hub page
│   │   └── explore/
│   │       ├── help.js
│   │       ├── search.js
│   │       ├── accessibility.js
│   │       └── sitemap.js
│   ├── components/
│   │   ├── Header.js                   # App header
│   │   ├── Footer.js                   # App footer (Libre-Halaal branding)
│   │   ├── Layout.js                   # Root layout component
│   │   ├── Sidebar.js                  # Navigation sidebar
│   │   └── SearchBox.js                # Search component
│   ├── data/
│   │   └── menuData.js                 # Sidebar navigation structure
│   ├── utils/
│   │   ├── orchestrationEvents.js      # Event registry
│   │   ├── messageBus.js               # Pub/Sub system
│   │   ├── iframeAdapter.js            # PostMessage bridge
│   │   └── serviceConfig.js            # Service URLs configuration (NEW)
│   └── templates/
│       └── csLineInvokerClient.template.js  # csLineInvoker integration template
├── .env.development                    # Development environment variables (NEW)
├── .env.production                     # Production environment variables (NEW)
├── ORCHESTRATION.md                    # API reference
├── ORCHESTRATION_SETUP.md              # Setup guide
├── TESTING_GUIDE.md                    # Testing procedures
├── FILE_MANIFEST.md                    # File breakdown
└── README.org                          # This design document

Running the Dashboard

Prerequisites

  • Node.js 22.21.1+
  • npm 10.9.4+

Start Development Server

cd /bisos/git/auth/bxRepos/bisos-web/csLineInvoker-webUi
npm install
npm run develop

Server starts on http://localhost:25001

Build for Production

npm run build
npm run serve

Debugging

Browser Console Commands

All debug tools exposed via window object:

// Message Bus debugging
window.__messageBusDebug.subscribers()  // View all listeners
window.__messageBusDebug.log()          // View event history
window.__messageBusDebug.print()        // Pretty-print events

// Iframe Adapter debugging
window.__iframeAdapter.status()         // Check iframe connections
window.__iframeAdapter.registry()       // View registered iframes
window.__iframeAdapter.send(service, event, data)  // Send test message

UI Enhancements

iframe URL Display in Headers

Purpose

Every iframe page now displays its configured URL in the header for:

  • **Debugging**: Developers can immediately see which URL is loaded
  • **Transparency**: Users know where the content comes from
  • **Configuration visibility**: Shows which environment (dev/prod) is active
  • **Quick access**: Clickable to open in new tab if iframe fails

Implementation

All iframe pages now include a URL badge in the page header:

  • **Location**: Right-aligned in header, below description text
  • **Style**: Small, monospace font, blue color
  • **Interactivity**: Clickable link (opens in new tab), hover effect
  • **Icon**: Arrow (↗) indicates external link

Pages with URL Display

src/pages/csPlayer.js - Shows cslineInvoker URL ✓ src/pages/csLineInvokerBackEnd.js - Shows csplayerPerformer URL ✓ src/pages/modPlayerFacter.js - Shows cslineInvoker URL ✓ src/pages/modPlayerSoncli.js - Shows cslineInvoker URL ✓ src/pages/airflow.js - Shows airflow URL ✓ src/pages/grafana.js - Shows grafana URL

Visual Example

┌────────────────────────────────────────────────────────────────┐
│  🖥️ Build and Execute CSXU Command Lines                       │
│  Build, execute and monitor...       http://csLineInvoker... ↗  │
└────────────────────────────────────────────────────────────────┘
```

The URL is right-aligned on the same line as the description text, in blue, and clickable.

* Deployment Considerations
:PROPERTIES:
:CUSTOM_ID: deployment-considerations
:END:

** Security
:PROPERTIES:
:CUSTOM_ID: security
:END:

*** Trust Model

This architecture assumes a *trusted internal ecosystem*:

- All services are controlled by the same organization
- Services are on the same network
- PostMessage uses =*= origin (intentionally simple for internal use)

*** Security NOT Included (By Design)

- Message signing/validation
- Message encryption
- Rate limiting

* Appendix
:PROPERTIES:
:CUSTOM_ID: appendix
:END:

** File Reference
:PROPERTIES:
:CUSTOM_ID: file-reference
:END:

*** Core Orchestration Files

| File                                          | Lines | Purpose                            | Status     |
|-----------------------------------------------+-------+------------------------------------+------------|
| =src/utils/orchestrationEvents.js=              |    40 | Event registry                     | ✓ Complete |
| =src/utils/messageBus.js=                       |   130 | Pub/Sub system                     | ✓ Complete |
| =src/utils/iframeAdapter.js=                    |   180 | PostMessage bridge                 | ✓ Complete |
| =src/utils/serviceConfig.js=                    |    35 | Service URLs configuration         | ✓ Complete |
| =src/templates/csLineInvokerClient.template.js= |   150 | csLineInvoker integration template | ✓ Complete |

*** Configuration Files

| File             | Purpose                  | Status     |
|------------------+--------------------------+------------|
| =.env.development= | Development service URLs | ✓ Complete |
| =.env.production=  | Production service URLs  | ✓ Complete |

*** Page Components

| File                              | Purpose                                           | Status     |
|-----------------------------------+---------------------------------------------------+------------|
| =src/pages/index.js=                | Homepage with service overview                    | ✓ Complete |
| =src/pages/csPlayer.js=             | csLineInvoker/invoker iframe (config + URL badge) | ✓ Complete |
| =src/pages/csLineInvokerBackEnd.js= | Performer API admin (config + URL badge)          | ✓ Complete |
| =src/pages/modPlayerFacter.js=      | Alternative invoker (config + URL badge)          | ✓ Complete |
| =src/pages/modPlayerSoncli.js=      | Alternative invoker (config + URL badge)          | ✓ Complete |
| =src/pages/airflow.js=              | Airflow iframe (config + URL badge)               | ✓ Complete |
| =src/pages/grafana.js=              | Grafana iframe (config + URL badge)               | ✓ Complete |
| =src/pages/testStubs.js=            | Test stubs iframe (config + URL badge)            | ✓ Complete |
| =src/pages/explore.js=              | Resource hub                                      | ✓ Complete |

** Event Registry
:PROPERTIES:
:CUSTOM_ID: event-registry
:END:

*** csLineInvoker Events

| Event                       | Direction      | Payload                     | Purpose              |
|-----------------------------+----------------+-----------------------------+----------------------|
| =csLineInvoker:filterChanged= | Parent → Child | ={environment, server, user}= | User changed filters |
| =csLineInvoker:taskExecuted=  | Child → Parent | ={taskId, output, duration}=  | Task completed       |
| =csLineInvoker:taskFailed=    | Child → Parent | ={taskId, errorMessage}=      | Task failed          |

---

Document Status: LIVING DESIGN DOCUMENT
Last Updated: January 24, 2026
Version: 1.0 (Phase 1 Complete)

About

A React Based Web User Interface to Play CSXUs of BISOS-PyCS

Resources

License

AGPL-3.0, 0BSD licenses found

Licenses found

AGPL-3.0
LICENSE
0BSD
LICENSE.nelify

Stars

Watchers

Forks

Releases

No releases published

Packages

 
 
 

Contributors