webserver

package
v0.0.25 Latest Latest
Warning

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

Go to latest
Published: Apr 23, 2026 License: MIT Imports: 27 Imported by: 0

Documentation

Overview

Package webserver provides a web-based terminal interface for pi-go. It exposes the pi-go agent via a browser with xterm.js, authenticated through a pairing code flow. It exposes the pi-go agent via a browser with xterm.js, authenticated through a pairing code flow.

Index

Constants

This section is empty.

Variables

This section is empty.

Functions

func BuildPairQRCode

func BuildPairQRCode(code, token, serverHost, pairURL string) ([]byte, error)

BuildPairQRCode builds a QR PNG for a pairing code/token and server context.

func GenerateQRCode

func GenerateQRCode(data string) ([]byte, error)

GenerateQRCode generates a QR code image for the pairing data. Returns PNG data or an error.

func ParseQRData

func ParseQRData(data string) (code, token string, err error)

ParseQRData parses QR code data and extracts code and token.

func ValidateCode

func ValidateCode(code string) bool

ValidateCode checks if a code is valid (6 digits).

Types

type ApprovedPair

type ApprovedPair struct {
	Token      string
	Project    string
	ApprovedAt time.Time
}

ApprovedPair represents an approved pairing token.

type Config

type Config struct {
	Addr           string
	PairingTimeout time.Duration
	StaticDir      string
	Project        string
	Model          string
	BaseURL        string
	Headers        []string
	Insecure       bool
	Logger         *slog.Logger // if nil, a no-op logger is used
}

Config holds server configuration.

type PairResponse

type PairResponse struct {
	Code  string `json:"code"`
	Token string `json:"token"`
	QR    string `json:"qr"` // base64 encoded PNG image
}

PairResponse represents the API response for pairing.

type PairStatus

type PairStatus string

PairStatus represents the status of a pairing request.

const (
	PairStatusPending  PairStatus = "pending"
	PairStatusApproved PairStatus = "approved"
	PairStatusExpired  PairStatus = "expired"
	PairStatusUnknown  PairStatus = "unknown"
)

type PairingManager

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

PairingManager handles pairing code generation, approval, and expiry.

func NewPairingManager

func NewPairingManager(timeout time.Duration) *PairingManager

NewPairingManager creates a new PairingManager with the specified timeout.

func (*PairingManager) Approve

func (pm *PairingManager) Approve(code string) (string, error)

Approve approves a pairing code and returns the associated token.

func (*PairingManager) CheckStatus

func (pm *PairingManager) CheckStatus(token string) (PairStatus, error)

CheckStatus returns the current status of a pairing token.

func (*PairingManager) CleanupExpired

func (pm *PairingManager) CleanupExpired()

CleanupExpired removes expired pending codes.

func (*PairingManager) CreatePair

func (pm *PairingManager) CreatePair(project string) (code, token string, qrData []byte, err error)

CreatePair generates a new 6-digit pairing code and returns the code, token, and QR data.

func (*PairingManager) CreatePairWithContext

func (pm *PairingManager) CreatePairWithContext(project, serverHost, pairURL string) (code, token string, qrData []byte, err error)

CreatePairWithContext generates a pair and embeds server context in the QR payload.

func (*PairingManager) GetProject

func (pm *PairingManager) GetProject(token string) (string, error)

GetProject returns the project path for an approved token.

func (*PairingManager) IsApproved

func (pm *PairingManager) IsApproved(token string) bool

IsApproved checks if a token has been approved.

type PendingPair

type PendingPair struct {
	Code      string
	CreatedAt time.Time
	ExpiresAt time.Time
	Project   string
	Token     string // browser token to approve
}

PendingPair represents a pending pairing request.

type PtyBridge

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

PtyBridge manages a long-lived PTY process that survives WebSocket reconnects.

func NewPtyBridge

func NewPtyBridge(project, model, baseURL string, headers []string, insecure bool, logger *slog.Logger) *PtyBridge

NewPtyBridge creates a new PTY bridge for the given project, model, base URL, optional extra HTTP headers (key=value), and insecure TLS toggle. All of these are forwarded to the spawned pi subprocess via command-line flags.

func (*PtyBridge) Alive

func (pb *PtyBridge) Alive() bool

Alive reports whether the PTY process is still running.

func (*PtyBridge) AttachWebSocket

func (pb *PtyBridge) AttachWebSocket(conn *websocket.Conn, sessionID string)

AttachWebSocket connects a WebSocket to this PTY bridge. Blocks until the WebSocket disconnects or the PTY process exits. After return the PTY is still alive; call Close() to kill it.

func (*PtyBridge) Close

func (pb *PtyBridge) Close() error

Close terminates the PTY bridge and underlying process.

func (*PtyBridge) HandleWebSocket

func (pb *PtyBridge) HandleWebSocket(conn *websocket.Conn, sessionID string)

HandleWebSocket is a convenience wrapper: Start + AttachWebSocket + Close. Used when session persistence is not needed.

func (*PtyBridge) Resize added in v0.0.24

func (pb *PtyBridge) Resize(cols, rows int)

Resize updates the PTY size. No-op when running in pipe fallback mode.

func (*PtyBridge) Start

func (pb *PtyBridge) Start() error

Start launches the PTY child process. Must be called before AttachWebSocket.

type PtyPool

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

PtyPool manages PTY bridges keyed by session ID.

func NewPtyPool

func NewPtyPool(logger *slog.Logger) *PtyPool

NewPtyPool creates a new PTY pool.

func (*PtyPool) CloseAll

func (p *PtyPool) CloseAll()

CloseAll terminates all PTY bridges in the pool.

func (*PtyPool) GetOrCreate

func (p *PtyPool) GetOrCreate(sessionID, project, model, baseURL string, headers []string, insecure bool) (*PtyBridge, error)

GetOrCreate returns an existing live PTY bridge for the session, or creates and starts a new one.

type Server

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

Server holds HTTP handlers and dependencies.

func NewServer

func NewServer(cfg Config) *Server

NewServer creates a new web server with the given configuration.

func (*Server) Addr

func (s *Server) Addr() string

Addr returns the listen address.

func (*Server) GetProject

func (s *Server) GetProject(token string) (string, error)

GetProject returns the project for a given token.

func (*Server) Mux

func (s *Server) Mux() *http.ServeMux

Mux returns the HTTP serve mux.

func (*Server) PairingManager

func (s *Server) PairingManager() *PairingManager

PairingManager returns the pairing manager.

type ServerV2

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

ServerV2 is the main web server.

func NewServerV2

func NewServerV2(cfg Config) *ServerV2

NewServerV2 creates a new server with the given configuration.

func (*ServerV2) Addr

func (s *ServerV2) Addr() string

Addr returns the actual listen address (reflects the bound port when using :0).

func (*ServerV2) BootstrapPair

func (s *ServerV2) BootstrapPair(project string) (string, string, error)

BootstrapPair creates (or reuses) an active pair for CLI-first flow.

func (*ServerV2) PairingManager

func (s *ServerV2) PairingManager() *PairingManager

PairingManager returns the pairing manager.

func (*ServerV2) SessionManager

func (s *ServerV2) SessionManager() *SessionManager

SessionManager returns the session manager.

func (*ServerV2) Shutdown

func (s *ServerV2) Shutdown(ctx context.Context) error

Shutdown gracefully shuts down the server.

func (*ServerV2) Start

func (s *ServerV2) Start() error

Start starts the HTTP server.

type SessionManager

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

SessionManager manages per-tab sessions.

func NewSessionManager

func NewSessionManager() *SessionManager

NewSessionManager creates a new session manager.

func (*SessionManager) CleanupExpired

func (sm *SessionManager) CleanupExpired()

CleanupExpired removes expired sessions. Deprecated: Use cleanupLoop instead.

func (*SessionManager) Close

func (sm *SessionManager) Close()

Close stops the session manager and cleans up.

func (*SessionManager) CloseSession

func (sm *SessionManager) CloseSession(sessionID string) error

CloseSession marks a session as closed.

func (*SessionManager) CreateSession

func (sm *SessionManager) CreateSession(project, token string) (*WebSession, error)

CreateSession creates a new session for a browser tab.

func (*SessionManager) GetSession

func (sm *SessionManager) GetSession(sessionID string) (*WebSession, bool)

GetSession retrieves a session by ID.

func (*SessionManager) SessionCount

func (sm *SessionManager) SessionCount() int

SessionCount returns the number of active sessions.

type StatusResponse

type StatusResponse struct {
	Status    PairStatus `json:"status"`
	SessionID string     `json:"sessionID,omitempty"`
}

StatusResponse represents the API response for status check.

type WSMessage

type WSMessage struct {
	Type string `json:"type"`
	Data string `json:"data"`
}

WSMessage represents a message sent over the WebSocket.

type WebSession

type WebSession struct {
	ID        string
	Project   string
	Token     string
	CreatedAt time.Time
	ClosedAt  time.Time
	Closed    bool
}

WebSession represents an isolated browser tab session.

type WebSocketHandler

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

WebSocketHandler handles WebSocket connections for terminal.

func NewWebSocketHandler

func NewWebSocketHandler(sessionManager *SessionManager) *WebSocketHandler

NewWebSocketHandler creates a new WebSocket handler.

func (*WebSocketHandler) HandleWebSocket

func (wh *WebSocketHandler) HandleWebSocket(w http.ResponseWriter, r *http.Request)

HandleWebSocket handles a WebSocket connection.

Jump to

Keyboard shortcuts

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