http

package
v0.1.3 Latest Latest
Warning

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

Go to latest
Published: Feb 27, 2026 License: MIT Imports: 41 Imported by: 0

Documentation

Overview

Package http provides the HTTP server handlers for cdev.

Package http implements the HTTP API server for cdev.

Package http provides HTTP handlers for cdev.

Package http implements the HTTP API server for cdev.

Package http provides OpenRPC discovery endpoint for JSON-RPC API documentation.

Package http implements the HTTP API server for cdev.

Package http implements the HTTP API server for cdev.

Package http implements the HTTP API server for cdev.

Index

Constants

This section is empty.

Variables

This section is empty.

Functions

This section is empty.

Types

type AgentSessionInfo

type AgentSessionInfo struct {
	SessionID    string `json:"session_id"`
	AgentType    string `json:"agent_type"`
	Summary      string `json:"summary,omitempty"`
	MessageCount int    `json:"message_count"`
	LastUpdated  string `json:"last_updated"`
	Branch       string `json:"branch,omitempty"`
	ProjectPath  string `json:"project_path,omitempty"`
}

AgentSessionInfo represents information about a session for any agent runtime.

type AgentSessionMessage

type AgentSessionMessage struct {
	Type      string          `json:"type"`
	UUID      string          `json:"uuid,omitempty"`
	SessionID string          `json:"session_id,omitempty"`
	Timestamp string          `json:"timestamp,omitempty"`
	GitBranch string          `json:"git_branch,omitempty"`
	Message   json.RawMessage `json:"message"`
}

AgentSessionMessage represents a single message in a session (raw message format).

type AgentSessionMessagesResponse

type AgentSessionMessagesResponse struct {
	SessionID string                `json:"session_id"`
	Messages  []AgentSessionMessage `json:"messages"`
	Total     int                   `json:"total"`
	Limit     int                   `json:"limit"`
	Offset    int                   `json:"offset"`
	HasMore   bool                  `json:"has_more"`
}

AgentSessionMessagesResponse represents the paginated messages for an agent session.

type AgentSessionsResponse

type AgentSessionsResponse struct {
	Sessions []AgentSessionInfo `json:"sessions"`
	Current  string             `json:"current,omitempty"`
	Total    int                `json:"total"`
	Limit    int                `json:"limit"`
	Offset   int                `json:"offset"`
}

AgentSessionsResponse represents the list of available sessions for an agent runtime.

type AuthHandler

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

AuthHandler handles authentication-related HTTP endpoints.

func NewAuthHandler

func NewAuthHandler(tm *security.TokenManager, registry *security.AuthRegistry, onOrphaned func([]string, string)) *AuthHandler

NewAuthHandler creates a new auth handler.

func (*AuthHandler) HandleExchange

func (h *AuthHandler) HandleExchange(w http.ResponseWriter, r *http.Request)

HandleExchange exchanges a pairing token for an access/refresh token pair. @Summary Exchange pairing token for access/refresh tokens @Description Exchanges a valid pairing token for an access token and refresh token pair @Tags auth @Accept json @Produce json @Param request body TokenExchangeRequest true "Pairing token to exchange" @Success 200 {object} TokenPairResponse @Failure 400 {object} ErrorResponse @Failure 401 {object} ErrorResponse @Router /api/auth/exchange [post]

func (*AuthHandler) HandlePairingApprove

func (h *AuthHandler) HandlePairingApprove(w http.ResponseWriter, r *http.Request)

HandlePairingApprove approves a pending pairing request.

func (*AuthHandler) HandlePairingPending

func (h *AuthHandler) HandlePairingPending(w http.ResponseWriter, r *http.Request)

HandlePairingPending lists pending pairing approval requests.

func (*AuthHandler) HandlePairingReject

func (h *AuthHandler) HandlePairingReject(w http.ResponseWriter, r *http.Request)

HandlePairingReject rejects a pending pairing request.

func (*AuthHandler) HandleRefresh

func (h *AuthHandler) HandleRefresh(w http.ResponseWriter, r *http.Request)

HandleRefresh refreshes an access token using a refresh token. @Summary Refresh access token @Description Uses a valid refresh token to obtain a new access/refresh token pair @Tags auth @Accept json @Produce json @Param request body TokenRefreshRequest true "Refresh token" @Success 200 {object} TokenPairResponse @Failure 400 {object} ErrorResponse @Failure 401 {object} ErrorResponse @Router /api/auth/refresh [post]

func (*AuthHandler) HandleRevoke

func (h *AuthHandler) HandleRevoke(w http.ResponseWriter, r *http.Request)

HandleRevoke revokes a refresh token and clears any workspace bindings for the device. @Summary Revoke refresh token @Description Revokes the refresh token for a device and releases any workspace bindings. @Tags auth @Accept json @Produce json @Param request body TokenRevokeRequest true "Refresh token" @Success 200 {object} map[string]interface{} @Failure 400 {object} ErrorResponse @Failure 401 {object} ErrorResponse @Router /api/auth/revoke [post]

func (*AuthHandler) SetPairingApproval

func (h *AuthHandler) SetPairingApproval(manager *security.PairingApprovalManager, trustedProxies []*net.IPNet)

SetPairingApproval enables manual approve/reject flow for pairing exchange.

type ClaudeHookPayload

type ClaudeHookPayload struct {
	// Common fields (all hook types)
	SessionID      string `json:"session_id,omitempty"`
	TranscriptPath string `json:"transcript_path,omitempty"`
	Cwd            string `json:"cwd,omitempty"`
	HookEventName  string `json:"hook_event_name,omitempty"` // PreToolUse, PostToolUse, Notification, SessionStart
	PermissionMode string `json:"permission_mode,omitempty"` // default, etc.

	// Tool use fields (PreToolUse/PostToolUse)
	ToolName   string      `json:"tool_name,omitempty"`
	ToolInput  interface{} `json:"tool_input,omitempty"`
	ToolResult interface{} `json:"tool_result,omitempty"`
	ToolUseID  string      `json:"tool_use_id,omitempty"`

	// Notification fields (permission_prompt)
	Message          string `json:"message,omitempty"`           // "Claude needs your permission to use Bash"
	NotificationType string `json:"notification_type,omitempty"` // "permission_prompt"

	// Raw payload for any fields we didn't explicitly map
	Raw map[string]interface{} `json:"-"`
}

ClaudeHookPayload represents the data sent by Claude hooks. Claude sends different structures for different hook types, so we capture both specific fields and the raw payload for flexibility.

type DebugHandler

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

DebugHandler provides debug and profiling endpoints.

func NewDebugHandler

func NewDebugHandler(pprofEnabled bool) *DebugHandler

NewDebugHandler creates a new debug handler.

func (*DebugHandler) Register

func (h *DebugHandler) Register(mux *http.ServeMux)

Register registers debug endpoints on the given ServeMux.

type DirectoryListingResponse

type DirectoryListingResponse struct {
	Path       string      `json:"path" example:"src/components"`
	Entries    []FileEntry `json:"entries"`
	TotalCount int         `json:"total_count" example:"10"`
}

DirectoryListingResponse represents the response for listing a directory.

type ErrorResponse

type ErrorResponse struct {
	Error string `json:"error" example:"Something went wrong"`
	Path  string `json:"path,omitempty" example:"src/main.ts"`
}

ErrorResponse represents an error response.

type FileContentResponse

type FileContentResponse struct {
	Path      string `json:"path" example:"src/main.ts"`
	Content   string `json:"content" example:"console.log('hello');"`
	Encoding  string `json:"encoding" example:"utf-8"`
	Truncated bool   `json:"truncated" example:"false"`
	Size      int    `json:"size" example:"25"`
}

FileContentResponse represents the file content response.

type FileEntry

type FileEntry struct {
	Name          string  `json:"name" example:"main.go"`
	Type          string  `json:"type" example:"file"` // "file" or "directory"
	Size          *int64  `json:"size,omitempty" example:"1024"`
	Modified      *string `json:"modified,omitempty" example:"2025-01-15T10:30:00Z"`
	ChildrenCount *int    `json:"children_count,omitempty" example:"5"`
}

FileEntry represents a file or directory entry.

type GitBranchInfo

type GitBranchInfo struct {
	Name      string `json:"name" example:"feature-branch"`
	IsCurrent bool   `json:"is_current" example:"false"`
	IsRemote  bool   `json:"is_remote" example:"false"`
	Upstream  string `json:"upstream,omitempty" example:"origin/feature-branch"`
	Ahead     int    `json:"ahead,omitempty" example:"2"`
	Behind    int    `json:"behind,omitempty" example:"1"`
}

GitBranchInfo represents information about a branch.

type GitBranchesResponse

type GitBranchesResponse struct {
	Current  string          `json:"current" example:"main"`
	Upstream string          `json:"upstream,omitempty" example:"origin/main"`
	Ahead    int             `json:"ahead" example:"0"`
	Behind   int             `json:"behind" example:"0"`
	Branches []GitBranchInfo `json:"branches"`
}

GitBranchesResponse represents the response for listing branches.

type GitCheckoutRequest

type GitCheckoutRequest struct {
	Branch string `json:"branch" example:"feature-branch" binding:"required"`
	Create bool   `json:"create,omitempty" example:"false"`
}

GitCheckoutRequest represents the request to checkout a branch.

type GitCheckoutResponse

type GitCheckoutResponse struct {
	Success bool   `json:"success" example:"true"`
	Branch  string `json:"branch,omitempty" example:"feature-branch"`
	Message string `json:"message,omitempty" example:"Switched to branch 'feature-branch'"`
	Error   string `json:"error,omitempty"`
}

GitCheckoutResponse represents the response after checkout.

type GitCommitRequest

type GitCommitRequest struct {
	Message string `json:"message" example:"feat: add new feature" binding:"required"`
	Push    bool   `json:"push,omitempty" example:"false"`
}

GitCommitRequest represents the request to commit changes.

type GitCommitResponse

type GitCommitResponse struct {
	Success        bool   `json:"success" example:"true"`
	SHA            string `json:"sha,omitempty" example:"abc123def"`
	Message        string `json:"message,omitempty" example:"feat: add new feature"`
	FilesCommitted int    `json:"files_committed,omitempty" example:"3"`
	Pushed         bool   `json:"pushed,omitempty" example:"false"`
	Error          string `json:"error,omitempty"`
}

GitCommitResponse represents the response after committing.

type GitDiffAllResponse

type GitDiffAllResponse struct {
	Diffs          []GitDiffItem `json:"diffs"`
	TruncatedPaths []string      `json:"truncated_paths,omitempty"`
}

GitDiffAllResponse represents the git diff response for all files.

type GitDiffItem

type GitDiffItem struct {
	Path      string `json:"path" example:"src/main.ts"`
	Diff      string `json:"diff" example:"@@ -1,3 +1,4 @@\n+new line"`
	Truncated bool   `json:"is_truncated,omitempty" example:"false"`
}

GitDiffItem represents a single file diff.

type GitDiffResponse

type GitDiffResponse struct {
	Path      string `json:"path" example:"src/main.ts"`
	Diff      string `json:"diff" example:"@@ -1,3 +1,4 @@\n+new line"`
	Truncated bool   `json:"is_truncated,omitempty" example:"false"`
}

GitDiffResponse represents the git diff response for a single file.

type GitDiscardRequest

type GitDiscardRequest struct {
	Paths []string `json:"paths" example:"[\"src/main.ts\"]"`
}

GitDiscardRequest represents the request to discard changes.

type GitDiscardResponse

type GitDiscardResponse struct {
	Success   bool     `json:"success" example:"true"`
	Discarded []string `json:"discarded" example:"[\"src/main.ts\"]"`
	Error     string   `json:"error,omitempty"`
}

GitDiscardResponse represents the response after discarding changes.

type GitEnhancedStatusResponse

type GitEnhancedStatusResponse struct {
	Branch     string         `json:"branch" example:"main"`
	Upstream   string         `json:"upstream,omitempty" example:"origin/main"`
	Ahead      int            `json:"ahead" example:"2"`
	Behind     int            `json:"behind" example:"0"`
	Staged     []GitFileEntry `json:"staged"`
	Unstaged   []GitFileEntry `json:"unstaged"`
	Untracked  []GitFileEntry `json:"untracked"`
	Conflicted []GitFileEntry `json:"conflicted"`
	RepoName   string         `json:"repo_name" example:"myproject"`
	RepoRoot   string         `json:"repo_root" example:"/Users/dev/myproject"`
}

GitEnhancedStatusResponse represents the enhanced git status response.

type GitFileEntry

type GitFileEntry struct {
	Path      string `json:"path" example:"src/main.ts"`
	Status    string `json:"status" example:"M"`
	Additions int    `json:"additions,omitempty" example:"10"`
	Deletions int    `json:"deletions,omitempty" example:"5"`
}

GitFileEntry represents a file entry with diff stats.

type GitFileStatus

type GitFileStatus struct {
	Path        string `json:"path" example:"src/main.ts"`
	Status      string `json:"status" example:"M "`
	IsStaged    bool   `json:"is_staged" example:"true"`
	IsUntracked bool   `json:"is_untracked" example:"false"`
}

GitFileStatus represents the status of a single file in git.

type GitPullResponse

type GitPullResponse struct {
	Success         bool     `json:"success" example:"true"`
	Message         string   `json:"message,omitempty" example:"Pulled 3 commits"`
	CommitsPulled   int      `json:"commits_pulled,omitempty" example:"3"`
	FilesChanged    int      `json:"files_changed,omitempty" example:"5"`
	ConflictedFiles []string `json:"conflicted_files,omitempty"`
	Error           string   `json:"error,omitempty"`
}

GitPullResponse represents the response after pulling.

type GitPushResponse

type GitPushResponse struct {
	Success       bool   `json:"success" example:"true"`
	Message       string `json:"message,omitempty" example:"Pushed 2 commits to origin/main"`
	CommitsPushed int    `json:"commits_pushed,omitempty" example:"2"`
	Error         string `json:"error,omitempty"`
}

GitPushResponse represents the response after pushing.

type GitStageRequest

type GitStageRequest struct {
	Paths []string `json:"paths" example:"[\"src/main.ts\", \"src/utils.ts\"]"`
}

GitStageRequest represents the request to stage files.

type GitStageResponse

type GitStageResponse struct {
	Success bool     `json:"success" example:"true"`
	Staged  []string `json:"staged" example:"[\"src/main.ts\"]"`
	Error   string   `json:"error,omitempty"`
}

GitStageResponse represents the response after staging files.

type GitStatusResponse

type GitStatusResponse struct {
	Files    []GitFileStatus `json:"files"`
	RepoRoot string          `json:"repo_root" example:"/Users/dev/myproject"`
	RepoName string          `json:"repo_name" example:"myproject"`
}

GitStatusResponse represents the git status response.

type GitUnstageRequest

type GitUnstageRequest struct {
	Paths []string `json:"paths" example:"[\"src/main.ts\"]"`
}

GitUnstageRequest represents the request to unstage files.

type GitUnstageResponse

type GitUnstageResponse struct {
	Success  bool     `json:"success" example:"true"`
	Unstaged []string `json:"unstaged" example:"[\"src/main.ts\"]"`
	Error    string   `json:"error,omitempty"`
}

GitUnstageResponse represents the response after unstaging files.

type HealthResponse

type HealthResponse struct {
	Status string `json:"status" example:"ok"`
	Time   string `json:"time" example:"2024-01-15T10:30:00Z"`
}

HealthResponse represents the health check response.

type HooksHandler

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

HooksHandler handles incoming Claude hook events.

func NewHooksHandler

func NewHooksHandler(h *hub.Hub) *HooksHandler

NewHooksHandler creates a new HooksHandler.

func (*HooksHandler) HandleHook

func (h *HooksHandler) HandleHook(w http.ResponseWriter, r *http.Request)

HandleHook handles POST /api/hooks/:hookType

@Summary		Receive Claude hook event
@Description	Receives events from Claude Code hooks (SessionStart, Notification, PreToolUse, PostToolUse)
@Tags			hooks
@Accept			json
@Produce		json
@Param			hookType	path		string				true	"Hook type (session, permission, tool-start, tool-end)"
@Param			body		body		ClaudeHookPayload	true	"Hook payload from Claude"
@Success		200			{object}	map[string]bool
@Router			/api/hooks/{hookType} [post]

func (*HooksHandler) SetPermissionManager

func (h *HooksHandler) SetPermissionManager(pm PermissionManager)

SetPermissionManager sets the permission manager for handling PreToolUse requests.

func (*HooksHandler) SetPermissionTimeout

func (h *HooksHandler) SetPermissionTimeout(timeout time.Duration)

SetPermissionTimeout sets the timeout for waiting for mobile responses.

func (*HooksHandler) SetWorkspaceResolver

func (h *HooksHandler) SetWorkspaceResolver(resolver WorkspaceResolver)

SetWorkspaceResolver sets the workspace resolver for resolving workspace IDs from paths.

type ImageHandler

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

ImageHandler handles image upload operations with multi-workspace support.

func NewImageHandler

func NewImageHandler(manager *imagestorage.Manager) *ImageHandler

NewImageHandler creates a new ImageHandler with multi-workspace support.

func (*ImageHandler) Close

func (h *ImageHandler) Close()

Close cleans up resources.

func (*ImageHandler) HandleClearImages

func (h *ImageHandler) HandleClearImages(w http.ResponseWriter, r *http.Request)

HandleClearImages handles DELETE /api/images/all - clear all images.

@Summary		Clear all images
@Description	Removes all stored images
@Tags			images
@Produce		json
@Success		200	{object}	map[string]interface{}
@Failure		503	{object}	ErrorResponse	"Image storage not available"
@Router			/api/images/all [delete]

func (*ImageHandler) HandleImageStats

func (h *ImageHandler) HandleImageStats(w http.ResponseWriter, r *http.Request)

HandleImageStats handles GET /api/images/stats

@Summary		Get image storage stats
@Description	Returns current storage statistics
@Tags			images
@Produce		json
@Success		200	{object}	ImageStatsResponse
@Failure		503	{object}	ErrorResponse	"Image storage not available"
@Router			/api/images/stats [get]

func (*ImageHandler) HandleImages

func (h *ImageHandler) HandleImages(w http.ResponseWriter, r *http.Request)

HandleImages handles POST /api/images (upload) and GET /api/images (list/get)

@Summary		List images
@Description	Returns list of all stored images or details of a specific image by ID
@Tags			images
@Produce		json
@Param			id			query		string	false	"Image ID to get specific image details"
@Success		200			{object}	ImageListResponse
@Failure		404			{object}	ErrorResponse		"Image not found"
@Failure		503			{object}	ErrorResponse		"Image storage not available"
@Router			/api/images [get]

func (*ImageHandler) ValidateImagePath

func (h *ImageHandler) ValidateImagePath(w http.ResponseWriter, r *http.Request)

ValidateImagePath handles GET /api/images/validate?path=...

@Summary		Validate image path
@Description	Validates that an image path is safe and accessible
@Tags			images
@Produce		json
@Param			path	query		string	true	"Image path to validate"
@Success		200		{object}	ImageValidateResponse
@Failure		400		{object}	ErrorResponse	"Invalid path"
@Router			/api/images/validate [get]

type ImageInfoResponse

type ImageInfoResponse struct {
	ID        string `json:"id" example:"abc123def456"`
	LocalPath string `json:"local_path" example:".cdev/images/img_abc123def456.jpg"`
	MimeType  string `json:"mime_type" example:"image/jpeg"`
	Size      int64  `json:"size" example:"102400"`
	CreatedAt int64  `json:"created_at" example:"1705317000"`
	ExpiresAt int64  `json:"expires_at" example:"1705320600"`
}

ImageInfoResponse represents information about a stored image.

type ImageListResponse

type ImageListResponse struct {
	Images         []ImageInfoResponse `json:"images"`
	Count          int                 `json:"count" example:"5"`
	TotalSizeBytes int64               `json:"total_size_bytes" example:"512000"`
	MaxImages      int                 `json:"max_images" example:"50"`
	MaxTotalSizeMB int                 `json:"max_total_size_mb" example:"100"`
}

ImageListResponse represents the list of stored images.

type ImageStatsResponse

type ImageStatsResponse struct {
	ImageCount      int    `json:"image_count" example:"5"`
	TotalSizeBytes  int64  `json:"total_size_bytes" example:"512000"`
	MaxImages       int    `json:"max_images" example:"50"`
	MaxTotalSizeMB  int    `json:"max_total_size_mb" example:"100"`
	MaxSingleSizeMB int    `json:"max_single_size_mb" example:"10"`
	CanAcceptUpload bool   `json:"can_accept_upload" example:"true"`
	Reason          string `json:"reason,omitempty" example:""`
}

ImageStatsResponse represents the storage statistics.

type ImageUploadResponse

type ImageUploadResponse struct {
	Success   bool   `json:"success" example:"true"`
	ID        string `json:"id" example:"abc123def456"`
	LocalPath string `json:"local_path" example:".cdev/images/img_abc123def456.jpg"`
	MimeType  string `json:"mime_type" example:"image/jpeg"`
	Size      int64  `json:"size" example:"102400"`
	ExpiresAt int64  `json:"expires_at" example:"1705320600"`
}

ImageUploadResponse represents the response after uploading an image.

type ImageValidateResponse

type ImageValidateResponse struct {
	Valid   bool   `json:"valid" example:"true"`
	Path    string `json:"path" example:".cdev/images/img_abc123.jpg"`
	Message string `json:"message,omitempty" example:"invalid path: path traversal not allowed"`
}

ImageValidateResponse represents the response for path validation.

type PairingCodeRequest

type PairingCodeRequest struct {
	Code string `json:"code"`
}

PairingCodeRequest is the request body for POST /api/pair/code.

type PairingCodeResponse

type PairingCodeResponse struct {
	PairingToken string `json:"pairing_token"`
	ExpiresAt    string `json:"expires_at"`
	ExpiresIn    int    `json:"expires_in"`
}

PairingCodeResponse is the response for POST /api/pair/code.

type PairingDecisionRequest

type PairingDecisionRequest struct {
	RequestID string `json:"request_id"`
}

PairingDecisionRequest is the request body for pairing approval decisions.

type PairingExchangePendingResponse

type PairingExchangePendingResponse struct {
	Status    string `json:"status"`
	RequestID string `json:"request_id"`
	ExpiresAt string `json:"expires_at"`
}

PairingExchangePendingResponse is returned when exchange requires approval.

type PairingHandler

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

PairingHandler handles pairing-related HTTP endpoints.

func NewPairingHandler

func NewPairingHandler(tokenManager *security.TokenManager, requireAuth bool, pairingInfoFn func() *pairing.PairingInfo, allowRequestExternal bool, requireSecureTransport bool, trustedProxies []string) *PairingHandler

NewPairingHandler creates a new pairing handler.

func (*PairingHandler) HandlePairCode

func (h *PairingHandler) HandlePairCode(w http.ResponseWriter, r *http.Request)

HandlePairCode handles POST /api/pair/code Exchanges a one-time pairing code for a pairing token.

@Summary		Exchange pairing code
@Description	Exchanges a short pairing code for a pairing token
@Tags			pairing
@Accept			json
@Produce		json
@Success		200	{object}	PairingCodeResponse
@Failure		400	{object}	ErrorResponse
@Failure		401	{object}	ErrorResponse
@Router			/api/pair/code [post]

func (*PairingHandler) HandlePairInfo

func (h *PairingHandler) HandlePairInfo(w http.ResponseWriter, r *http.Request)

HandlePairInfo handles GET /api/pair/info Returns connection info as JSON for the mobile app.

@Summary		Get pairing info
@Description	Returns connection info for mobile app pairing (WebSocket URL, HTTP URL, session ID, auth flag)
@Tags			pairing
@Produce		json
@Success		200	{object}	PairingInfoResponse
@Router			/api/pair/info [get]

func (*PairingHandler) HandlePairPage

func (h *PairingHandler) HandlePairPage(w http.ResponseWriter, r *http.Request)

HandlePairPage handles GET /pair Returns an HTML page with QR code for browser-based pairing.

@Summary		Pairing page
@Description	Returns an HTML page with QR code for browser-based mobile app pairing
@Tags			pairing
@Produce		html
@Success		200	{string}	string	"HTML page"
@Router			/pair [get]

func (*PairingHandler) HandlePairQR

func (h *PairingHandler) HandlePairQR(w http.ResponseWriter, r *http.Request)

HandlePairQR handles GET /api/pair/qr Returns a QR code image (PNG) containing the pairing info.

@Summary		Get pairing QR code
@Description	Returns a PNG QR code image containing connection info for mobile app
@Tags			pairing
@Produce		png
@Param			size	query		int	false	"QR code size in pixels (default 256, max 512)"
@Success		200		{file}		binary
@Failure		500		{object}	ErrorResponse	"Failed to generate QR code"
@Router			/api/pair/qr [get]

func (*PairingHandler) HandlePairRefresh

func (h *PairingHandler) HandlePairRefresh(w http.ResponseWriter, r *http.Request)

HandlePairRefresh handles POST /api/pair/refresh Generates a new pairing token (revokes old ones).

@Summary		Refresh pairing token
@Description	Generates a new pairing token and revokes all previous tokens
@Tags			pairing
@Produce		json
@Success		200	{object}	PairingRefreshResponse
@Failure		503	{object}	ErrorResponse	"Token manager not available"
@Router			/api/pair/refresh [post]

type PairingInfoResponse

type PairingInfoResponse struct {
	WebSocket      string `json:"ws"`
	HTTP           string `json:"http"`
	SessionID      string `json:"session"`
	RepoName       string `json:"repo"`
	AuthRequired   bool   `json:"auth_required"`
	Token          string `json:"token,omitempty"`
	TokenExpiresAt string `json:"token_expires_at,omitempty"`
}

PairingInfoResponse is the response for GET /api/pair/info.

type PairingRefreshResponse

type PairingRefreshResponse struct {
	Token     string `json:"token"`
	ExpiresAt string `json:"expires_at"`
	Message   string `json:"message"`
}

PairingRefreshResponse is the response for POST /api/pair/refresh.

type PermissionManager

type PermissionManager interface {
	CheckMemory(sessionID, toolName string, toolInput map[string]interface{}) *permission.StoredDecision
	StoreDecision(sessionID, workspaceID, pattern string, decision permission.Decision)
	AddPendingRequest(req *permission.Request)
	GetAndRemovePendingRequest(toolUseID string) *permission.Request
}

PermissionManager interface for checking/storing permission decisions. This allows the hooks handler to use the existing permission memory system.

type RepositoryFileInfo

type RepositoryFileInfo struct {
	Path        string  `json:"path" example:"internal/adapters/repository/indexer.go"`
	Name        string  `json:"name" example:"indexer.go"`
	Directory   string  `json:"directory" example:"internal/adapters/repository"`
	Extension   string  `json:"extension,omitempty" example:"go"`
	SizeBytes   int64   `json:"size_bytes" example:"12453"`
	ModifiedAt  string  `json:"modified_at" example:"2025-12-19T10:30:00Z"`
	IsBinary    bool    `json:"is_binary" example:"false"`
	IsSensitive bool    `json:"is_sensitive" example:"false"`
	GitTracked  bool    `json:"git_tracked" example:"true"`
	MatchScore  float64 `json:"match_score,omitempty" example:"0.95"`
}

RepositoryFileInfo represents a file in search results.

type RepositoryIndexStatusResponse

type RepositoryIndexStatusResponse struct {
	Status            string `json:"status" example:"ready"`
	TotalFiles        int    `json:"total_files" example:"1234"`
	IndexedFiles      int    `json:"indexed_files" example:"1234"`
	TotalSizeBytes    int64  `json:"total_size_bytes" example:"45829381"`
	LastFullScan      string `json:"last_full_scan" example:"2025-12-19T10:30:00Z"`
	LastUpdate        string `json:"last_update" example:"2025-12-19T11:45:23Z"`
	DatabaseSizeBytes int64  `json:"database_size_bytes" example:"2458234"`
	IsGitRepo         bool   `json:"is_git_repo" example:"true"`
}

RepositoryIndexStatusResponse is the API response type for index status.

type RepositorySearchRequest

type RepositorySearchRequest struct {
	Query           string   `json:"q" example:"main.go"`
	Mode            string   `json:"mode" example:"fuzzy" enums:"fuzzy,exact,prefix,extension"`
	Limit           int      `json:"limit" example:"50"`
	Offset          int      `json:"offset" example:"0"`
	Extensions      []string `json:"extensions,omitempty" example:"go,js,ts"`
	ExcludeBinaries bool     `json:"exclude_binaries" example:"true"`
	GitTrackedOnly  bool     `json:"git_tracked_only" example:"false"`
}

RepositorySearchRequest represents a search request.

type RepositorySearchResponse

type RepositorySearchResponse struct {
	Query     string               `json:"query" example:"indexer"`
	Mode      string               `json:"mode" example:"fuzzy"`
	Results   []RepositoryFileInfo `json:"results"`
	Total     int                  `json:"total" example:"5"`
	ElapsedMS int64                `json:"elapsed_ms" example:"23"`
}

RepositorySearchResponse represents a search response.

type RespondToClaudeRequest

type RespondToClaudeRequest struct {
	ToolUseID string `json:"tool_use_id" example:"toolu_abc123" binding:"required"`
	Response  string `json:"response" example:"Yes, proceed with the changes"`
	IsError   bool   `json:"is_error" example:"false"`
}

RespondToClaudeRequest represents the request to respond to Claude.

type RespondToClaudeResponse

type RespondToClaudeResponse struct {
	Status    string `json:"status" example:"sent"`
	ToolUseID string `json:"tool_use_id" example:"toolu_abc123"`
}

RespondToClaudeResponse represents the response after sending response to Claude.

type RunClaudeRequest

type RunClaudeRequest struct {
	Prompt    string      `json:"prompt" example:"Create a hello world function" binding:"required"`
	Mode      SessionMode `json:"mode,omitempty" example:"new" enums:"new,continue"`
	SessionID string      `json:"session_id,omitempty" example:"550e8400-e29b-41d4-a716-446655440000"`
}

RunClaudeRequest represents the request to start Claude.

type RunClaudeResponse

type RunClaudeResponse struct {
	Status    string `json:"status" example:"started"`
	Prompt    string `json:"prompt" example:"Create a hello world function"`
	PID       int    `json:"pid" example:"12345"`
	SessionID string `json:"session_id,omitempty" example:"550e8400-e29b-41d4-a716-446655440000"`
}

RunClaudeResponse represents the response after starting Claude.

type Server

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

Server is the HTTP API server.

func New

func New(host string, port int, statusFn func() map[string]interface{}, claudeManager *claude.Manager, gitTracker *git.Tracker, sessionCache *sessioncache.Cache, messageCache *sessioncache.MessageCache, eventHub ports.EventHub, maxFileSizeKB int, maxDiffSizeKB int, repoPath string) *Server

New creates a new HTTP server.

func (*Server) SetAuth

func (s *Server) SetAuth(tokenManager *security.TokenManager, requireAuth bool)

SetAuth configures HTTP authentication.

func (*Server) SetAuthAllowlist

func (s *Server) SetAuthAllowlist(allowlist []string)

SetAuthAllowlist overrides the default unauthenticated path allowlist.

func (*Server) SetAuthHandler

func (s *Server) SetAuthHandler(handler *AuthHandler)

SetAuthHandler sets up authentication endpoints for token exchange and refresh. Must be called before Start() to enable token refresh functionality.

func (*Server) SetCdevAccessToken

func (s *Server) SetCdevAccessToken(token string)

SetCdevAccessToken configures the optional token gate for protected cdev web routes. Protected routes currently include /pair, /api/pair/*, and /api/auth/pairing/*.

func (*Server) SetDebugHandler

func (s *Server) SetDebugHandler(handler *DebugHandler)

SetDebugHandler sets up debug and profiling endpoints. Must be called before Start() to enable debug functionality. Debug endpoints are automatically protected by localhost-only binding (default).

func (*Server) SetHooksHandler

func (s *Server) SetHooksHandler(handler *HooksHandler)

SetHooksHandler sets up Claude hooks endpoints for receiving events from external Claude sessions. This enables real-time event capture from Claude running in VS Code, Cursor, or terminal.

func (*Server) SetImageStorageManager

func (s *Server) SetImageStorageManager(manager *imagestorage.Manager)

SetImageStorageManager sets the image storage manager for multi-workspace support. The manager creates storage per-workspace on demand. Must be called before Start() to enable image upload functionality.

func (*Server) SetOriginChecker

func (s *Server) SetOriginChecker(checker *security.OriginChecker)

SetOriginChecker sets the origin checker for CORS validation.

func (*Server) SetPairAccessToken

func (s *Server) SetPairAccessToken(token string)

SetPairAccessToken configures the optional token gate for pairing routes. DEPRECATED: use SetCdevAccessToken. Kept for backward compatibility.

func (*Server) SetPairingHandler

func (s *Server) SetPairingHandler(handler *PairingHandler)

SetPairingHandler sets up pairing endpoints for mobile app connection. Must be called before Start() to enable pairing functionality.

func (*Server) SetRPCRegistry

func (s *Server) SetRPCRegistry(registry *handler.Registry)

SetRPCRegistry sets the RPC registry for dynamic OpenRPC generation.

func (*Server) SetRateLimitKeyExtractor

func (s *Server) SetRateLimitKeyExtractor(extractor middleware.KeyExtractor)

SetRateLimitKeyExtractor sets a custom key extractor for rate limiting.

func (*Server) SetRateLimiter

func (s *Server) SetRateLimiter(limiter *middleware.RateLimiter)

SetRateLimiter sets the rate limiter for request throttling.

func (*Server) SetRepositoryIndexer

func (s *Server) SetRepositoryIndexer(indexer *repository.SQLiteIndexer)

SetRepositoryIndexer sets the repository indexer for the server.

func (*Server) SetRequireSecureTransport

func (s *Server) SetRequireSecureTransport(require bool)

SetRequireSecureTransport requires HTTPS/WSS for non-localhost requests.

func (*Server) SetTLS

func (s *Server) SetTLS(certFile, keyFile string)

SetTLS configures TLS for HTTPS/WSS serving.

func (*Server) SetTrustedProxies

func (s *Server) SetTrustedProxies(trustedProxies []*net.IPNet)

SetTrustedProxies sets trusted proxy CIDRs for request-aware URL/Ratelimit logic.

func (*Server) SetWebSocketHandler

func (s *Server) SetWebSocketHandler(handler WebSocketHandler)

Start starts the HTTP server. SetWebSocketHandler sets the handler for WebSocket connections. Must be called before Start().

func (*Server) Start

func (s *Server) Start() error

func (*Server) Stop

func (s *Server) Stop(ctx context.Context) error

Stop gracefully stops the HTTP server.

type SessionInfo

type SessionInfo struct {
	SessionID    string `json:"session_id" example:"550e8400-e29b-41d4-a716-446655440000"`
	Summary      string `json:"summary" example:"Create a hello world function"`
	MessageCount int    `json:"message_count" example:"5"`
	LastUpdated  string `json:"last_updated" example:"2024-01-15T10:30:00Z"`
}

SessionInfo represents information about a Claude session.

type SessionMessage

type SessionMessage struct {
	Type      string `json:"type" example:"user"`
	Role      string `json:"role" example:"user"`
	Content   string `json:"content" example:"Create a hello world function"`
	Timestamp string `json:"timestamp" example:"2024-01-15T10:30:00Z"`
}

SessionMessage represents a single message in a session.

type SessionMessagesResponse

type SessionMessagesResponse struct {
	SessionID string           `json:"session_id" example:"550e8400-e29b-41d4-a716-446655440000"`
	Messages  []SessionMessage `json:"messages"`
	Count     int              `json:"count" example:"10"`
}

SessionMessagesResponse represents the messages in a session.

type SessionMode

type SessionMode string

SessionMode defines how to handle conversation sessions.

const (
	// SessionModeNew starts a new conversation (default).
	SessionModeNew SessionMode = "new"
	// SessionModeContinue continues a conversation by session ID.
	// Requires session_id parameter.
	SessionModeContinue SessionMode = "continue"
)

type SessionsResponse

type SessionsResponse struct {
	Sessions []SessionInfo `json:"sessions"`
	Current  string        `json:"current,omitempty" example:"550e8400-e29b-41d4-a716-446655440000"`
}

SessionsResponse represents the list of available sessions.

type StatusResponse

type StatusResponse struct {
	SessionID        string `json:"session_id" example:"550e8400-e29b-41d4-a716-446655440000"`       // Claude session ID (for continue) - empty if no active session
	AgentSessionID   string `json:"agent_session_id" example:"01ce425c-5b91-4f8a-b8dd-5d14644c3494"` // Agent instance ID (generated on startup)
	Version          string `json:"version" example:"1.0.0"`
	RepoPath         string `json:"repo_path" example:"/Users/dev/myproject"`
	RepoName         string `json:"repo_name" example:"myproject"`
	UptimeSeconds    int64  `json:"uptime_seconds" example:"3600"`
	ClaudeState      string `json:"claude_state" example:"idle"`
	ConnectedClients int    `json:"connected_clients" example:"1"`
	WatcherEnabled   bool   `json:"watcher_enabled" example:"true"`
	GitEnabled       bool   `json:"git_enabled" example:"true"`
	IsGitRepo        bool   `json:"is_git_repo" example:"true"`
}

StatusResponse represents the agent status response.

type StopClaudeResponse

type StopClaudeResponse struct {
	Status string `json:"status" example:"stopped"`
}

StopClaudeResponse represents the response after stopping Claude.

type TokenExchangeRequest

type TokenExchangeRequest struct {
	PairingToken string `json:"pairing_token"`
}

TokenExchangeRequest is the request body for token exchange.

type TokenPairResponse

type TokenPairResponse struct {
	AccessToken        string `json:"access_token"`
	AccessTokenExpiry  string `json:"access_token_expires_at"`
	RefreshToken       string `json:"refresh_token"`
	RefreshTokenExpiry string `json:"refresh_token_expires_at"`
	TokenType          string `json:"token_type"`
	ExpiresIn          int    `json:"expires_in"` // seconds until access token expires
}

TokenPairResponse is the response containing access and refresh tokens.

type TokenRefreshRequest

type TokenRefreshRequest struct {
	RefreshToken string `json:"refresh_token"`
}

TokenRefreshRequest is the request body for token refresh.

type TokenRevokeRequest

type TokenRevokeRequest struct {
	RefreshToken string `json:"refresh_token"`
}

TokenRevokeRequest is the request body for token revocation.

type WebSocketHandler

type WebSocketHandler func(http.ResponseWriter, *http.Request)

WebSocketHandler is a function that handles WebSocket connections.

type WorkspaceResolver

type WorkspaceResolver interface {
	ResolveWorkspaceID(path string) (string, error)
}

WorkspaceResolver resolves workspace ID from a filesystem path.

Directories

Path Synopsis
Package middleware provides HTTP middleware components for the cdev server.
Package middleware provides HTTP middleware components for the cdev server.

Jump to

Keyboard shortcuts

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