workspace

package
v0.1.0 Latest Latest
Warning

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

Go to latest
Published: Apr 10, 2026 License: MIT Imports: 19 Imported by: 0

Documentation

Overview

Package workspace provides workspace/project management.

Package workspace provides workspace discovery functionality.

Package workspace provides workspace/project management.

Package workspace provides workspace/project management.

Package workspace provides workspace and project management for bc.

A workspace represents a project directory containing bc configuration and agent state in .bc/settings.json.

Basic Usage

Find the current workspace:

ws, err := workspace.Find(".")
if err != nil {
    log.Fatal("not in a bc workspace")
}
fmt.Println("Workspace:", ws.Name())

Initialize a new workspace:

ws, err := workspace.Init("/path/to/project")
if err != nil {
    log.Fatal(err)
}

Load an existing workspace:

ws, err := workspace.Load("/path/to/project")
if err != nil {
    log.Fatal(err)
}

Index

Constants

View Source
const ConfigVersion = 2

ConfigVersion is the current config schema version.

View Source
const DefaultBaseRole = `` /* 2540-byte string literal not displayed */

DefaultBaseRole is the foundational role all other roles inherit from. It provides the bc MCP server so every agent can communicate with the workspace.

View Source
const DefaultRootRole = `` /* 619-byte string literal not displayed */

DefaultRootRole returns the default content for root.md.

View Source
const NameMaxLength = 30

User name limits.

Variables

View Source
var (
	ErrInvalidVersion          = errors.New("version must be 2")
	ErrMissingDefaultProvider  = errors.New("providers.default is required")
	ErrDefaultProviderNotFound = errors.New("providers.default references undefined provider")
	ErrInvalidTheme            = errors.New("ui.theme must be one of: dark, light, matrix, synthwave, high-contrast")
	ErrInvalidThemeMode        = errors.New("ui.mode must be one of: auto, dark, light")
	ErrNameTooLong             = errors.New("user.name is too long")
)

Validation errors.

View Source
var DefaultRoles = map[string]string{
	"feature-dev": `---
name: feature-dev
description: Feature developer — implements tasks in isolated worktrees
parent_roles:
  - base
mcp_servers:
  - github
secrets:
  - GITHUB_PERSONAL_ACCESS_TOKEN
prompt_start: |
  Check #engineering channel for any new assignments or updates.
---

# Feature Developer

You implement features, fix bugs, and write tests in an isolated git worktree.

## Workflow
1. Read the assigned issue, create a feature branch (feat/<issue>-<slug>)
2. Implement with tests, run make check
3. Open a PR and post to #merge when ready for review
`,
	"go-reviewer": `---
name: go-reviewer
description: Go code quality reviewer
parent_roles:
  - feature-dev
---

# Go Reviewer

Review Go pull requests for correctness, security, and test coverage.
Use the github MCP to fetch PR diffs and leave inline review comments.
Block merges on security issues or broken tests; suggest rather than block on style.
`,
	"web-reviewer": `---
name: web-reviewer
description: Web/TypeScript UI reviewer
parent_roles:
  - feature-dev
---

# Web Reviewer

Review React/TypeScript pull requests for correctness and component patterns.
Use the github MCP to fetch PR diffs and leave inline review comments.
Hooks cannot be tested without a DOM in Ink — test exported helpers instead.
`,
	"designer": `---
name: designer
description: Design system and Web UI specialist
parent_roles:
  - feature-dev
---

# Designer

Maintain the design token system, build React/Ink TUI components, and implement
CSS/Tailwind changes for the web dashboard. Accessibility is non-negotiable.
`,
	"product-manager": `---
name: product-manager
description: Product coordination and epic management
parent_roles:
  - base
mcp_servers:
  - github
secrets:
  - GITHUB_PERSONAL_ACCESS_TOKEN
---

# Product Manager

Break down goals into epics and issues, assign work to agents, and review
completed work against acceptance criteria. Use GitHub issues for all tracking.
`,
	"docs": `---
name: docs
description: Documentation writer
parent_roles:
  - feature-dev
---

# Documentation Writer

Write and maintain README, CONTRIBUTING, API docs, and CLAUDE.md.
Update docs in the same PR as the feature. Use concrete examples.
`,
}

DefaultRoles contains the built-in role definitions for the bc agent team. These are written to .bc/roles/ if the files don't already exist.

View Source
var ErrNotV1Workspace = errors.New("not a v1 workspace (no .bc/config.json found)")

ErrNotV1Workspace is returned when migration is attempted on a non-v1 workspace.

View Source
var ValidModes = []string{"auto", "dark", "light"}

Valid theme modes.

View Source
var ValidThemes = []string{"dark", "light", "matrix", "synthwave", "high-contrast"}

Valid theme names.

Functions

func BCHome

func BCHome() (string, error)

BCHome returns the global bc home directory (~/.bc). Respects BC_HOME env var override.

func ConfigPath

func ConfigPath(rootDir string) string

ConfigPath returns the standard config file path for a workspace root. Checks global state dir first, falls back to legacy .bc/.

func CountLegacyAgentFiles

func CountLegacyAgentFiles(stateDir string) int

CountLegacyAgentFiles counts legacy per-agent JSON files in the agents directory. Exported so callers (e.g. the migrate command) can show a file count preview.

func DiscoverAndRegister

func DiscoverAndRegister(opts DiscoverOptions) (int, error)

DiscoverAndRegister discovers workspaces and adds new ones to the registry. Returns the number of newly registered workspaces.

func EnsureBCHome

func EnsureBCHome() error

EnsureBCHome creates the global ~/.bc directory structure if it doesn't exist.

func FormatRoleFile

func FormatRoleFile(role *Role) (string, error)

FormatRoleFile formats a role as a markdown file with YAML frontmatter.

func GlobalDir

func GlobalDir() string

GlobalDir returns the path to ~/.bc/.

func GlobalStateDir

func GlobalStateDir(rootDir string) (string, error)

GlobalStateDir returns the state directory for a workspace. Path: ~/.bc/workspaces/<workspace-id>/ The workspace ID is the first 6 hex chars of SHA256(absRootDir). Respects BC_STATE_DIR env var override.

func IsWorkspace

func IsWorkspace(dir string) bool

IsWorkspace checks if a directory is a workspace. Checks legacy .bc/ directory and global state dir (~/.bc/workspaces/<id>/).

func MigrateToGlobalState

func MigrateToGlobalState(rootDir string) (string, error)

MigrateToGlobalState moves workspace state from <project>/.bc/ to ~/.bc/workspaces/<id>/. Leaves a .bc-migrated marker in the old location. Returns the new state directory path.

func NeedsMigration

func NeedsMigration(rootDir string) bool

NeedsMigration returns true if the workspace has legacy .bc/ state that hasn't been migrated to ~/.bc/workspaces/<id>/ yet.

func NormalizeNickname

func NormalizeNickname(nickname string) (string, error)

NormalizeNickname ensures a nickname has the @ prefix and is valid.

func NormalizeRoleName

func NormalizeRoleName(name string) string

NormalizeRoleName canonicalises a role name by replacing underscores with hyphens and lower-casing, preventing duplicates like "product_manager" vs "product-manager".

func RegistryPath

func RegistryPath() string

RegistryPath returns the path to ~/.bc/workspaces.json.

func UserRCConfigPath

func UserRCConfigPath() string

UserRCConfigPath returns the path to the user's .bcrc file. Default: ~/.bcrc

func UserRCExists

func UserRCExists() bool

UserRCExists returns true if ~/.bcrc exists.

func V1ConfigPath

func V1ConfigPath(rootDir string) string

V1ConfigPath returns the path to the v1 config.json.

func ValidateNickname

func ValidateNickname(nickname string) error

ValidateNickname validates a nickname and returns an error if invalid.

Types

type AliasConflictError

type AliasConflictError struct {
	Alias        string
	ExistingPath string
}

AliasConflictError indicates the alias is already in use.

func (*AliasConflictError) Error

func (e *AliasConflictError) Error() string

type Config

type Config struct {
	User      UserConfig      `json:"user"`
	Providers ProvidersConfig `json:"providers"`
	Gateways  GatewaysConfig  `json:"gateways"`
	Runtime   RuntimeConfig   `json:"runtime"`
	Storage   StorageConfig   `json:"storage"`
	Server    ServerConfig    `json:"server"`
	Cron      CronConfig      `json:"cron"`
	Logs      LogsConfig      `json:"logs"`
	UI        UIConfig        `json:"ui"`
	Version   int             `json:"version"`
}

Config represents the JSON-based workspace configuration for bc.

func DefaultConfig

func DefaultConfig() Config

DefaultConfig returns sensible defaults for a new workspace.

func LoadConfig

func LoadConfig(path string) (*Config, error)

LoadConfig reads and parses a JSON config file.

func ParseConfig

func ParseConfig(data []byte) (*Config, error)

ParseConfig parses JSON data into a Config.

func (*Config) FillDefaults

func (c *Config) FillDefaults()

FillDefaults fills zero-valued fields with defaults. Called after ParseConfig to handle configs from older versions.

func (*Config) GetDefaultProvider

func (c *Config) GetDefaultProvider() string

GetDefaultProvider returns the default AI provider name.

func (*Config) GetPreferredTool

func (c *Config) GetPreferredTool(rc *UserRCConfig) string

GetPreferredTool returns the first available preferred tool from .bcrc.

func (*Config) GetProvider

func (c *Config) GetProvider(name string) *ProviderConfig

GetProvider returns an AI provider's configuration by name.

func (*Config) HasProviderDefined

func (c *Config) HasProviderDefined(name string) bool

HasProviderDefined checks if an AI provider is configured.

func (*Config) ListProviders

func (c *Config) ListProviders() []string

ListProviders returns the names of all configured AI providers.

func (*Config) MergeWithUserRC

func (c *Config) MergeWithUserRC(rc *UserRCConfig)

MergeWithUserRC merges user-level defaults from .bcrc into a workspace config.

func (*Config) Save

func (c *Config) Save(path string) error

Save writes the config to a JSON file atomically (temp+rename).

func (*Config) Validate

func (c *Config) Validate() error

Validate checks the config for required fields and consistency.

type CronConfig

type CronConfig struct {
	PollIntervalSeconds int `json:"poll_interval_seconds"`
	JobTimeoutSeconds   int `json:"job_timeout_seconds"`
}

CronConfig configures the cron/job scheduler.

type DiscordGatewayConfig

type DiscordGatewayConfig struct {
	BotToken string `json:"bot_token"`
	Enabled  bool   `json:"enabled"`
}

DiscordGatewayConfig configures the Discord gateway adapter.

type DiscoverOptions

type DiscoverOptions struct {
	// ScanPaths additional paths to scan for workspaces
	ScanPaths []string
	// MaxDepth maximum directory depth to scan (default 3)
	MaxDepth int
	// IncludeCached includes workspaces from the global registry (~/.bc/workspaces.json)
	IncludeCached bool
	// ScanHome scans ~/Projects and ~/Developer directories
	ScanHome bool
}

DiscoverOptions configures workspace discovery.

func DefaultDiscoverOptions

func DefaultDiscoverOptions() DiscoverOptions

DefaultDiscoverOptions returns sensible defaults for discovery.

type DiscoveredWorkspace

type DiscoveredWorkspace struct {
	Path      string // Absolute path to workspace root
	Name      string // Workspace name (from config or directory name)
	IsV2      bool   // True if v2 (TOML) workspace
	FromCache bool   // True if found in registry (not disk scan)
}

DiscoveredWorkspace represents a workspace found during discovery.

func Discover

func Discover(opts DiscoverOptions) ([]DiscoveredWorkspace, error)

Discover finds all bc workspaces on the machine. It checks the global registry and optionally scans common directories.

type DockerRuntimeConfig

type DockerRuntimeConfig struct {
	ExtraMounts      []string `json:"extra_mounts"`
	Image            string   `json:"image"`
	Network          string   `json:"network"`
	DockerSocketPath string   `json:"docker_socket_path"`
	MemoryMB         int64    `json:"memory_mb"`
	CPUs             float64  `json:"cpus"`
}

DockerRuntimeConfig configures Docker container settings for agents.

type GatewaysConfig

type GatewaysConfig struct {
	Telegram *TelegramGatewayConfig `json:"telegram,omitempty"`
	Discord  *DiscordGatewayConfig  `json:"discord,omitempty"`
	Slack    *SlackGatewayConfig    `json:"slack,omitempty"`
}

GatewaysConfig configures external messaging platform integrations.

type LogsConfig

type LogsConfig struct {
	Path     string `json:"path"`
	MaxBytes int64  `json:"max_bytes"`
}

LogsConfig configures persistent session log streaming.

type MigrateResult

type MigrateResult struct {
	BackupPath     string // Path to backup of old .bc directory
	AgentFiles     int    // Number of agent state files migrated
	ConfigMigrated bool   // Whether config.json → settings.json migration ran
	ChannelJSON    bool   // Whether channels.json was migrated to SQLite
}

MigrateResult summarizes what the migration changed.

func MigrateV1ToV2

func MigrateV1ToV2(rootDir string) (*MigrateResult, error)

MigrateV1ToV2 migrates a v1 workspace to v2 format.

Steps performed:

  1. Read .bc/config.json
  2. Write .bc/config.json.bak (backup)
  3. Convert and write .bc/settings.json (v2 format)

Agent JSON→SQLite and channel JSON→SQLite migrations happen automatically the next time those stores are opened (existing auto-migration in pkg/agent and pkg/channel).

Returns ErrNotV1Workspace if .bc/config.json does not exist.

type ProviderConfig

type ProviderConfig struct {
	Command string `json:"command"`
}

ProviderConfig defines an AI provider's configuration.

type ProvidersConfig

type ProvidersConfig struct {
	Default   string                    `json:"default"`
	Providers map[string]ProviderConfig `json:"providers,omitempty"`
}

ProvidersConfig configures AI agent providers.

type Registry

type Registry struct {
	Active     string          `json:"active,omitempty"` // Path or alias of active workspace
	Workspaces []RegistryEntry `json:"workspaces"`
	// contains filtered or unexported fields
}

Registry manages the global list of workspaces at ~/.bc/workspaces.json. Issue #1218: Multi-workspace orchestration support.

func LoadRegistry

func LoadRegistry() (*Registry, error)

LoadRegistry loads the global workspace registry. Returns an empty registry if the file doesn't exist.

func (*Registry) Find

func (r *Registry) Find(path string) *RegistryEntry

Find returns the entry for a given path, or nil if not found.

func (*Registry) FindByAlias

func (r *Registry) FindByAlias(alias string) *RegistryEntry

FindByAlias returns the entry for a given alias, or nil if not found. Issue #1218: Multi-workspace orchestration.

func (*Registry) FindByNameOrAlias

func (r *Registry) FindByNameOrAlias(identifier string) *RegistryEntry

FindByNameOrAlias returns the entry matching name, alias, or path. Tries alias first, then name, then path.

func (*Registry) GetActive

func (r *Registry) GetActive() *RegistryEntry

GetActive returns the active workspace entry, or nil if none set.

func (*Registry) List

func (r *Registry) List() []RegistryEntry

List returns all registered workspaces.

func (*Registry) Prune

func (r *Registry) Prune() int

Prune removes entries where the workspace no longer exists on disk. Checks for .bc/ dir in project root OR state dir in ~/.bc/workspaces/<id>/.

func (*Registry) Register

func (r *Registry) Register(path, name string)

Register adds or updates a workspace in the registry.

func (*Registry) RegisterWithAlias

func (r *Registry) RegisterWithAlias(path, name, alias string) error

RegisterWithAlias adds or updates a workspace with an optional alias. Issue #1218: Multi-workspace orchestration.

func (*Registry) Save

func (r *Registry) Save() error

Save persists the registry to disk.

func (*Registry) SetActive

func (r *Registry) SetActive(identifier string) error

SetActive sets the active workspace by path, alias, or name.

func (*Registry) SetAlias

func (r *Registry) SetAlias(path, alias string) error

SetAlias sets or clears the alias for a workspace.

func (*Registry) Touch

func (r *Registry) Touch(path string)

Touch updates the last-accessed time for a workspace.

func (*Registry) Unregister

func (r *Registry) Unregister(path string)

Unregister removes a workspace from the registry.

type RegistryEntry

type RegistryEntry struct {
	CreatedAt    time.Time `json:"created_at"`
	LastAccessed time.Time `json:"last_accessed"`
	Path         string    `json:"path"`
	Name         string    `json:"name"`
	Alias        string    `json:"alias,omitempty"` // Short alias for quick access (#1218)
}

RegistryEntry represents a registered workspace.

type ResolvedRole

type ResolvedRole struct {
	Settings     map[string]any    // Merged settings (child overrides parent)
	Rules        map[string]string // Merged rule files (child overrides parent)
	Agents       map[string]string // Merged agent templates
	Skills       map[string]string // Merged skill files
	Commands     map[string]string // Merged command files
	PromptStart  string            // Lifecycle: sent on agent start/restart
	Name         string            // Role name
	PromptStop   string            // Lifecycle: sent on agent stop
	PromptDelete string            // Lifecycle: sent on agent delete
	PromptCreate string            // Lifecycle: sent on agent create
	Prompt       string            // Merged prompt body (child + parent)
	Review       string            // REVIEW.md content
	Plugins      []string          // Unioned plugins from all ancestors
	Secrets      []string          // Unioned secret names from all ancestors
	MCPServers   []string          // Unioned MCP servers from all ancestors
	CLITools     []string          // Unioned CLI tools from all ancestors
	Description  string            // Human-readable role description
}

ResolvedRole contains the fully resolved role after BFS inheritance merge.

type Role

type Role struct {
	FilePath string       // Path to the role file
	Prompt   string       // Markdown body after frontmatter
	Metadata RoleMetadata // Parsed YAML frontmatter
}

Role represents a parsed role file with metadata and prompt content.

func ParseRoleFile

func ParseRoleFile(data []byte) (*Role, error)

ParseRoleFile parses a role file with YAML frontmatter and markdown body. The frontmatter is delimited by --- on its own lines.

func (*Role) Description

func (r *Role) Description() string

Description returns a brief description for the role. Uses Metadata.Description if set, otherwise extracts from the first heading in Prompt.

type RoleManager

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

RoleManager handles role operations for a workspace. All role data is stored in SQL (SQLite or Postgres) via the RoleStore. The rolesDir field is retained only for migration from legacy file-based storage.

func NewRoleManager

func NewRoleManager(stateDir string) *RoleManager

NewRoleManager creates a new role manager for the given workspace state directory. It opens a SQLite-backed RoleStore at stateDir/bc.db automatically and performs a best-effort migration of any .md files in the roles directory. If the store cannot be opened, operations that require the store will return errors.

func NewRoleManagerWithStore

func NewRoleManagerWithStore(stateDir string, store *RoleStore) *RoleManager

NewRoleManagerWithStore creates a role manager backed by a SQLite store. The filesystem rolesDir is still used for migration and backward compatibility.

func (*RoleManager) AddMCPServer

func (rm *RoleManager) AddMCPServer(roleName, server string) error

AddMCPServer adds an MCP server association to a role if not already present.

func (*RoleManager) DeleteRole

func (rm *RoleManager) DeleteRole(name string) error

DeleteRole removes a role by name from the SQL store.

func (*RoleManager) EnsureDefaultRoles

func (rm *RoleManager) EnsureDefaultRoles() ([]string, error)

EnsureDefaultRoles writes built-in default roles to the store if they don't already exist. Returns the names of any roles that were created.

func (*RoleManager) EnsureDefaultRoot

func (rm *RoleManager) EnsureDefaultRoot() (bool, error)

EnsureDefaultRoot ensures the base and root roles exist in the store. Returns true if the root role was created, false if it already existed.

func (*RoleManager) EnsureRolesDir

func (rm *RoleManager) EnsureRolesDir() error

EnsureRolesDir creates the roles directory if it doesn't exist.

func (*RoleManager) GetMCPServers

func (rm *RoleManager) GetMCPServers(roleName string) ([]string, error)

GetMCPServers returns the MCP server associations for a role.

func (*RoleManager) GetRole

func (rm *RoleManager) GetRole(name string) (*Role, bool)

GetRole returns a cached role by name.

func (*RoleManager) HasRole

func (rm *RoleManager) HasRole(name string) bool

HasRole checks if a role exists (cached or in store).

func (*RoleManager) LoadAllRoles

func (rm *RoleManager) LoadAllRoles() (map[string]*Role, error)

LoadAllRoles loads all roles from the SQL store.

func (*RoleManager) LoadRole

func (rm *RoleManager) LoadRole(name string) (*Role, error)

LoadRole loads and parses a single role from the SQL store.

func (*RoleManager) RemoveMCPServer

func (rm *RoleManager) RemoveMCPServer(roleName, server string) error

RemoveMCPServer removes an MCP server association from a role.

func (*RoleManager) ResolveRole

func (rm *RoleManager) ResolveRole(name string) (*ResolvedRole, error)

ResolveRole loads a role directly from the store. No inheritance — each role is self-contained with all its own MCP servers, secrets, plugins, etc.

func (*RoleManager) RolesDir

func (rm *RoleManager) RolesDir() string

RolesDir returns the roles directory path.

func (*RoleManager) SetMCPServers

func (rm *RoleManager) SetMCPServers(roleName string, servers []string) error

SetMCPServers replaces the MCP server list for a role.

func (*RoleManager) Store

func (rm *RoleManager) Store() *RoleStore

Store returns the underlying RoleStore, or nil if filesystem-only.

func (*RoleManager) WriteRole

func (rm *RoleManager) WriteRole(role *Role) error

WriteRole writes a role to the SQL store.

type RoleMetadata

type RoleMetadata struct {
	Settings     map[string]any    `yaml:"settings,omitempty"`      // Claude settings overrides (e.g., model, permissions)
	Rules        map[string]string `yaml:"rules,omitempty"`         // Rule files written to .claude/rules/*.md
	Agents       map[string]string `yaml:"agents,omitempty"`        // Agent templates written to .claude/agents/*.md
	Skills       map[string]string `yaml:"skills,omitempty"`        // Skill files written to .claude/skills/*.md
	Commands     map[string]string `yaml:"commands,omitempty"`      // Command files written to .claude/commands/*.md
	PromptStop   string            `yaml:"prompt_stop,omitempty"`   // Sent when agent is stopped
	PromptCreate string            `yaml:"prompt_create,omitempty"` // Sent when agent is created
	PromptStart  string            `yaml:"prompt_start,omitempty"`  // Sent when agent is started/restarted
	Name         string            `yaml:"name"`                    // Role name (e.g., "engineer", "manager")
	PromptDelete string            `yaml:"prompt_delete,omitempty"` // Sent when agent is deleted
	Description  string            `yaml:"description,omitempty"`   // Human-readable role description
	Review       string            `yaml:"review,omitempty"`        // REVIEW.md content for the role
	Plugins      []string          `yaml:"plugins,omitempty"`       // Claude Code plugins to install on agent start
	Secrets      []string          `yaml:"secrets,omitempty"`       // Secret names needed by MCP env vars
	MCPServers   []string          `yaml:"mcp_servers,omitempty"`   // MCP servers available to this role
	ParentRoles  []string          `yaml:"parent_roles,omitempty"`  // Roles to inherit from (capabilities, prompts)
	CLITools     []string          `yaml:"cli_tools,omitempty"`     // CLI tools expected in agent PATH (e.g., gh, aws, wrangler)
}

RoleMetadata contains the parsed frontmatter from a role file.

type RoleStore

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

RoleStore provides SQL-backed persistence for roles. It supports both SQLite and Postgres via the driver field.

func NewRoleStore

func NewRoleStore(dbPath string) (*RoleStore, error)

NewRoleStore opens (or creates) a SQLite database at dbPath and ensures the roles table exists. The caller must call Close when done.

func NewRoleStoreFromDB

func NewRoleStoreFromDB(sqlDB *sql.DB, driver string) (*RoleStore, error)

NewRoleStoreFromDB creates a RoleStore from an existing *sql.DB connection. The caller retains ownership of the connection — Close on this store is a no-op.

func (*RoleStore) Close

func (s *RoleStore) Close() error

Close closes the database if this store owns the connection.

func (*RoleStore) Delete

func (s *RoleStore) Delete(name string) error

Delete removes a single role by name.

func (*RoleStore) Has

func (s *RoleStore) Has(name string) bool

Has checks if a role exists in the database.

func (*RoleStore) InitSchema

func (s *RoleStore) InitSchema() error

InitSchema creates the roles table if it does not exist. Uses driver-appropriate column types.

func (*RoleStore) Load

func (s *RoleStore) Load(name string) (*Role, error)

Load reads a single role by name. Returns an error if not found.

func (*RoleStore) LoadAll

func (s *RoleStore) LoadAll() (map[string]*Role, error)

LoadAll reads every role into a map keyed by name.

func (*RoleStore) MigrateDefaults

func (s *RoleStore) MigrateDefaults() error

MigrateDefaults inserts the built-in default roles (base, root, and DefaultRoles map) into the database if they don't already exist.

func (*RoleStore) MigrateFromFiles

func (s *RoleStore) MigrateFromFiles(rolesDir string) (int, error)

MigrateFromFiles scans a roles directory for .md files and inserts them into the database. Existing roles in the DB are not overwritten. The source files are NOT deleted (kept as backup).

func (*RoleStore) Save

func (s *RoleStore) Save(role *Role) error

Save persists a single role (upsert).

type RuntimeConfig

type RuntimeConfig struct {
	K8s     json.RawMessage     `json:"k8s,omitempty"` // future
	Default string              `json:"default"`       // "tmux" or "docker"
	Docker  DockerRuntimeConfig `json:"docker"`
	Tmux    TmuxRuntimeConfig   `json:"tmux"`
}

RuntimeConfig configures the agent session backend.

type SQLiteStorageConfig

type SQLiteStorageConfig struct {
	Path string `json:"path"`
}

SQLiteStorageConfig configures SQLite storage.

type ServerConfig

type ServerConfig struct {
	Host       string `json:"host"`
	CORSOrigin string `json:"cors_origin"`
	Port       int    `json:"port"`
}

ServerConfig configures the bcd HTTP server.

func (ServerConfig) Addr

func (s ServerConfig) Addr() string

Addr returns the host:port string for the server.

type SlackGatewayConfig

type SlackGatewayConfig struct {
	BotToken string `json:"bot_token"`
	AppToken string `json:"app_token"`
	Mode     string `json:"mode"`
	Enabled  bool   `json:"enabled"`
}

SlackGatewayConfig configures the Slack gateway adapter.

type StorageConfig

type StorageConfig struct {
	Default   string                 `json:"default"` // "sqlite" or "timescale"
	SQLite    SQLiteStorageConfig    `json:"sqlite"`
	Timescale TimescaleStorageConfig `json:"timescale"`
}

StorageConfig configures persistent storage.

type TelegramGatewayConfig

type TelegramGatewayConfig struct {
	BotToken string `json:"bot_token"`
	Mode     string `json:"mode"`
	Enabled  bool   `json:"enabled"`
}

TelegramGatewayConfig configures the Telegram gateway adapter.

type TimescaleStorageConfig

type TimescaleStorageConfig struct {
	Host     string `json:"host"`
	User     string `json:"user"`
	Password string `json:"password"`
	Database string `json:"database"`
	Port     int    `json:"port"`
}

TimescaleStorageConfig configures TimescaleDB (Postgres) storage.

type TmuxRuntimeConfig

type TmuxRuntimeConfig struct {
	SessionPrefix string `json:"session_prefix"`
	DefaultShell  string `json:"default_shell"`
	HistoryLimit  int    `json:"history_limit"`
}

TmuxRuntimeConfig configures tmux session settings.

type UIConfig

type UIConfig struct {
	Theme       string `json:"theme"`
	Mode        string `json:"mode"`
	DefaultView string `json:"default_view"`
}

UIConfig configures UI appearance.

type UserConfig

type UserConfig struct {
	Name string `json:"name"`
}

UserConfig holds user identity settings.

type UserRCConfig

type UserRCConfig struct {
	User     UserRCUserConfig     `json:"user"`
	Defaults UserRCDefaultsConfig `json:"defaults"`
	Tools    UserRCToolsConfig    `json:"tools"`
}

UserRCConfig represents user-level defaults stored in ~/.bcrc. These values are merged with workspace config when loading.

func DefaultUserRCConfig

func DefaultUserRCConfig() UserRCConfig

DefaultUserRCConfig returns sensible defaults for a new .bcrc file.

func LoadUserRCConfig

func LoadUserRCConfig() (*UserRCConfig, error)

LoadUserRCConfig loads the user's .bcrc file.

func ParseUserRCConfig

func ParseUserRCConfig(data []byte) (*UserRCConfig, error)

ParseUserRCConfig parses JSON data into a UserRCConfig.

func (*UserRCConfig) Save

func (c *UserRCConfig) Save() error

Save writes the user config to the .bcrc file.

type UserRCDefaultsConfig

type UserRCDefaultsConfig struct {
	DefaultRole   string `json:"default_role,omitempty"`
	AutoStartRoot bool   `json:"auto_start_root,omitempty"`
}

UserRCDefaultsConfig holds default behavior settings.

type UserRCToolsConfig

type UserRCToolsConfig struct {
	Preferred []string `json:"preferred,omitempty"`
}

UserRCToolsConfig holds tool preferences.

type UserRCUserConfig

type UserRCUserConfig struct {
	Nickname string `json:"nickname,omitempty"`
}

UserRCUserConfig holds user identity settings.

type V1Config

type V1Config struct {
	Name        string            `json:"name"`
	Description string            `json:"description"`
	Provider    string            `json:"provider"`  // default provider name
	Command     string            `json:"command"`   // default provider command
	Providers   map[string]string `json:"providers"` // name → command
	Nickname    string            `json:"nickname"`  // user nickname
	Runtime     string            `json:"runtime"`   // "tmux" or "docker"
}

V1Config represents the legacy JSON config format used in bc v1. Fields are mapped from the original config.json schema.

func LoadV1Config

func LoadV1Config(rootDir string) (*V1Config, error)

LoadV1Config reads and parses the v1 config.json from rootDir. Returns ErrNotV1Workspace if the file does not exist.

type Workspace

type Workspace struct {
	Config      *Config      // JSON config
	RoleManager *RoleManager // Role file manager
	RootDir     string       // Project root directory
	// contains filtered or unexported fields
}

Workspace represents an active workspace.

func Find

func Find(dir string) (*Workspace, error)

Find searches for a workspace starting from dir and going up. It checks the registry first (for .bc/-free workspaces), then falls back to the legacy .bc/ directory walk.

func Init

func Init(rootDir string) (*Workspace, error)

Init initializes a new workspace. State is stored under ~/.bc/workspaces/<id>/.

func Load

func Load(rootDir string) (*Workspace, error)

Load loads a workspace from a directory. If only a v1 config.json exists (no settings.json), Load returns an error wrapping ErrNotV1Workspace so callers can suggest migration.

func (*Workspace) AgentsDir

func (w *Workspace) AgentsDir() string

AgentsDir returns the agents state directory.

func (*Workspace) ChannelsDir

func (w *Workspace) ChannelsDir() string

ChannelsDir returns the channels directory path.

func (*Workspace) DefaultProvider

func (w *Workspace) DefaultProvider() string

DefaultProvider returns the default provider name for this workspace.

func (*Workspace) DefaultProviderCommand

func (w *Workspace) DefaultProviderCommand() string

DefaultProviderCommand returns the command for the default provider.

func (*Workspace) EnsureDirs

func (w *Workspace) EnsureDirs() error

EnsureDirs creates all required directories.

func (*Workspace) GetRole

func (w *Workspace) GetRole(name string) (*Role, error)

GetRole returns a role by name, loading it if necessary.

func (*Workspace) GetRolePrompt

func (w *Workspace) GetRolePrompt(name string) string

GetRolePrompt returns the prompt content for a role.

func (*Workspace) LogsDir

func (w *Workspace) LogsDir() string

LogsDir returns the logs directory.

func (*Workspace) Name

func (w *Workspace) Name() string

Name returns the workspace name (derived from directory).

func (*Workspace) RolesDir

func (w *Workspace) RolesDir() string

RolesDir returns the roles directory path.

func (*Workspace) Save

func (w *Workspace) Save() error

Save saves the workspace configuration.

func (*Workspace) StateDir

func (w *Workspace) StateDir() string

StateDir returns the state directory path. Uses the resolved state dir (global ~/.bc/workspaces/<id>/ or legacy .bc/).

type WorkspaceNotFoundError

type WorkspaceNotFoundError struct {
	Identifier string
}

WorkspaceNotFoundError indicates the workspace was not found.

func (*WorkspaceNotFoundError) Error

func (e *WorkspaceNotFoundError) Error() string

Jump to

Keyboard shortcuts

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