studio

package
v0.3.0 Latest Latest
Warning

This package is not in the latest version of its module.

Go to latest
Published: Jun 11, 2026 License: Apache-2.0 Imports: 24 Imported by: 0

Documentation

Overview

Package studio implements VORTEX Studio (build plan M12): a browser-based IDE and operations console served from the binary. It manages an external code-server (VS Code in the browser) process, a WebSocket terminal, a browser database GUI, and a Git panel — all mounted under /studio/ by the management API.

This file manages the code-server subprocess lifecycle. code-server is a separate binary (not embedded); when it is not installed, Studio degrades gracefully rather than failing the whole server.

Index

Constants

This section is empty.

Variables

View Source
var ErrCodeServerNotInstalled = errors.New("studio: code-server binary not installed")

ErrCodeServerNotInstalled indicates the code-server binary was not found in any known location. It is non-fatal: Studio runs without the IDE panel.

Functions

func KindForPort

func KindForPort(port int) string

KindForPort guesses a database kind from a well-known port (best effort).

Types

type CodeServer

type CodeServer struct {
	// contains filtered or unexported fields
}

CodeServer manages a code-server subprocess and proxies HTTP/WebSocket traffic to it.

func NewCodeServer

func NewCodeServer(cfg CodeServerConfig) (*CodeServer, error)

NewCodeServer constructs a manager. It returns ErrCodeServerNotInstalled when the binary is missing (callers treat this as a non-fatal degraded mode), or an error when the workspace directory does not exist.

func (*CodeServer) IsRunning

func (c *CodeServer) IsRunning() bool

IsRunning reports whether the subprocess is currently running.

func (*CodeServer) ProxyHandler

func (c *CodeServer) ProxyHandler() http.Handler

ProxyHandler returns an http.Handler that reverse-proxies all requests to the code-server backend, preserving WebSocket upgrades (used by code-server for live updates).

func (*CodeServer) Start

func (c *CodeServer) Start(ctx context.Context) error

Start launches the code-server subprocess and waits (up to 10s) for its port to accept connections.

func (*CodeServer) Stop

func (c *CodeServer) Stop() error

Stop sends SIGTERM (or the platform equivalent via Process.Kill on Windows) and waits up to 10s for the process to exit, force-killing if needed.

type CodeServerConfig

type CodeServerConfig struct {
	BinaryPath   string // path to code-server; auto-detected when empty
	WorkspaceDir string // directory to open
	Port         int    // internal bind port (default 8080)
	Auth         string // "none" — VORTEX handles auth at the edge
	CertFile     string // optional; VORTEX serves TLS, code-server stays plaintext
	DataDir      string // code-server --user-data-dir
	Logger       *slog.Logger
}

CodeServerConfig configures the code-server lifecycle manager.

type DBAuditLogger

type DBAuditLogger interface {
	Append(ctx context.Context, actor, action, resource string, detail map[string]any) error
}

DBAuditLogger records DB Studio query activity. Satisfied by *audit.Log.

type DBRoute

type DBRoute struct {
	Name       string // route name from vortex.cue
	Kind       string // "postgres" | "mysql" | "redis" | "mongodb"
	ListenAddr string // address of the mTLS TCP listener to connect through
}

DBRoute describes a database exposed via a VORTEX mTLS TCP route.

type DBStudio

type DBStudio struct {
	// contains filtered or unexported fields
}

DBStudio serves the browser database GUI under /studio/db/.

func NewDBStudio

func NewDBStudio(cfg DBStudioConfig) (*DBStudio, error)

NewDBStudio constructs the DB studio.

func (*DBStudio) Handler

func (d *DBStudio) Handler() http.Handler

Handler returns the DB studio HTTP handler mounted at /studio/db/.

type DBStudioConfig

type DBStudioConfig struct {
	Routes   []DBRoute
	ReadOnly bool // when true, only read queries (SELECT/SHOW/...) are allowed
	AuditLog DBAuditLogger
	Executor QueryExecutor // nil → queries return a "not configured" result
	Logger   *slog.Logger
}

DBStudioConfig configures the browser DB GUI.

type GitAuditLogger

type GitAuditLogger interface {
	Append(ctx context.Context, actor, action, resource string, detail map[string]any) error
}

GitAuditLogger records destructive Git operations. Satisfied by *audit.Log.

type GitPanel

type GitPanel struct {
	// contains filtered or unexported fields
}

GitPanel serves Git operations under /studio/git/ via the git binary.

func NewGitPanel

func NewGitPanel(cfg GitPanelConfig) (*GitPanel, error)

NewGitPanel constructs the panel. It returns an error if the git binary is missing or RepoPath is not a git repository.

func (*GitPanel) Handler

func (g *GitPanel) Handler() http.Handler

Handler returns the Git panel HTTP handler.

type GitPanelConfig

type GitPanelConfig struct {
	RepoPath string
	AuditLog GitAuditLogger
	Logger   *slog.Logger
}

GitPanelConfig configures the Git panel.

type QueryExecutor

type QueryExecutor interface {
	Query(ctx context.Context, route DBRoute, query string) (QueryResult, error)
	Schema(ctx context.Context, route DBRoute) (QueryResult, error)
}

QueryExecutor runs a query against a database route and returns its result. It is an interface so the actual driver (added when a DB driver dependency is approved) is decoupled from the HTTP/validation layer; tests inject a fake.

type QueryResult

type QueryResult struct {
	Columns []string `json:"columns"`
	Rows    [][]any  `json:"rows"`
	Error   string   `json:"error,omitempty"`
}

QueryResult is the outcome of a query execution.

type TerminalAuditLogger

type TerminalAuditLogger interface {
	Append(ctx context.Context, actor, action, resource string, detail map[string]any) error
}

TerminalAuditLogger records terminal session lifecycle events. Satisfied by *audit.Log; kept as an interface so this package stays decoupled.

type TerminalConfig

type TerminalConfig struct {
	Shell       string        // default: /bin/bash (Unix) or cmd.exe (Windows)
	WorkDir     string        // working directory for spawned shells
	MaxSessions int           // default 5
	IdleTimeout time.Duration // default 30m
	AuditLog    TerminalAuditLogger
	Logger      *slog.Logger
	// Authorize, when set, gates new sessions; it returns true to allow. When
	// nil, the manager allows any request that reaches it (the API layer is
	// expected to enforce auth before delegating here).
	Authorize func(r *http.Request) bool
}

TerminalConfig configures the browser terminal manager.

type TerminalManager

type TerminalManager struct {
	// contains filtered or unexported fields
}

TerminalManager serves browser terminals over WebSocket.

func NewTerminalManager

func NewTerminalManager(cfg TerminalConfig) *TerminalManager

NewTerminalManager constructs a manager with defaults applied.

func (*TerminalManager) CloseSessions

func (m *TerminalManager) CloseSessions() error

CloseSessions terminates all active terminal sessions.

func (*TerminalManager) Handler

func (m *TerminalManager) Handler() http.Handler

Handler returns the WebSocket terminal endpoint. It authenticates (when an Authorize hook is set), enforces the session cap, performs the WebSocket handshake, and pipes the WebSocket to a shell subprocess.

func (*TerminalManager) SessionCount

func (m *TerminalManager) SessionCount() int

SessionCount returns the number of active sessions.

type TerminalSession

type TerminalSession struct {
	ID        string
	StartedAt time.Time
	// contains filtered or unexported fields
}

TerminalSession is one active shell session bound to a WebSocket. Its fields are guarded by mu because the serving goroutine and CloseSessions/SessionCount callers touch it concurrently.

Jump to

Keyboard shortcuts

? : This menu
/ : Search site
f or F : Jump to
y or Y : Canonical URL