Documentation
¶
Overview ¶
Package dot provides a modern, type-safe symlink manager for dotfiles.
dot is a modern dotfile manager written in Go 1.26, following strict constitutional principles: test-driven development, atomic operations, functional programming, and comprehensive error handling.
Architecture ¶
The library exposes a Client facade over per-verb services. Domain types are re-exported from internal/domain through pkg/dot so callers depend only on the public package:
- Client interface and Config in pkg/dot (stable public API)
- Per-verb services in pkg/dot (ManageService, UnmanageService, StatusService, DoctorService, AdoptService, ManifestService, BootstrapService, CloneService)
- Internal implementation in internal/{pipeline,executor,planner,scanner,manifest}
- Domain types aliased into pkg/dot from internal/domain
Type aliases in pkg/dot keep the public surface stable while internal packages evolve, and prevent an import cycle between pkg/dot and internal.
Basic Usage ¶
Create a client and manage packages:
import (
"context"
"log"
"github.com/yaklabco/dot/internal/adapters"
"github.com/yaklabco/dot/pkg/dot"
)
cfg := dot.Config{
PackageDir: "/home/user/dotfiles",
TargetDir: "/home/user",
FS: adapters.NewOSFilesystem(),
Logger: adapters.NewNoopLogger(),
}
client, err := dot.NewClient(cfg)
if err != nil {
log.Fatal(err)
}
ctx := context.Background()
if err := client.Manage(ctx, "vim", "zsh", "git"); err != nil {
log.Fatal(err)
}
Dry Run Mode ¶
Preview operations without applying changes:
cfg.DryRun = true
client, _ := dot.NewClient(cfg)
// Shows what would be done without executing
if err := client.Manage(ctx, "vim"); err != nil {
log.Fatal(err)
}
Planning Operations ¶
Get execution plan without applying:
plan, err := client.PlanManage(ctx, "vim")
if err != nil {
log.Fatal(err)
}
fmt.Printf("Would execute %d operations\n", len(plan.Operations))
for _, op := range plan.Operations {
fmt.Printf(" %s\n", op.Kind())
}
Query Operations ¶
Check installation status:
status, err := client.Status(ctx, "vim")
if err != nil {
log.Fatal(err)
}
for _, pkg := range status.Packages {
fmt.Printf("%s: %d links\n", pkg.Name, pkg.LinkCount)
}
List all installed packages:
packages, err := client.List(ctx)
if err != nil {
log.Fatal(err)
}
for _, pkg := range packages {
fmt.Printf("%s (installed %s)\n", pkg.Name, pkg.InstalledAt)
}
Configuration ¶
The Config struct controls all dot behavior:
- PackageDir: Source directory containing packages (required, absolute path)
- TargetDir: Destination directory for symlinks (required, absolute path)
- FS: Filesystem implementation (required)
- Logger: Logger implementation (required)
- Tracer: Distributed tracing (optional, defaults to noop)
- Metrics: Metrics collection (optional, defaults to noop)
- LinkMode: Relative or absolute symlinks (default: relative)
- Folding: Enable directory folding (default: true)
- DryRun: Preview mode (default: false)
- Verbosity: Logging level (default: 0)
- BackupDir: Location for backup files (default: <TargetDir>/.dot-backup)
- Concurrency: Parallel operation limit (default: NumCPU)
- Backup: Back up conflicting files before replacing (default: false)
- Overwrite: Delete conflicting files before linking; takes precedence over Backup
- ManifestDir: Manifest location (default: TargetDir)
- Translate: Enable dot- prefix translation (*bool, default: true)
- PackageNameMapping: Map package name to target subdirectory (default: true)
- IgnorePatterns / UseDefaultIgnorePatterns / PerPackageIgnore: Ignore configuration
- MaxFileSize: Maximum file size to include, 0 for no limit
- InteractiveLargeFiles, Stdin, Stdout: Interactive prompt configuration
Validate() requires only PackageDir, TargetDir, FS, and Logger; all other fields have usable zero values or defaults.
Configuration must be validated before use:
cfg := dot.Config{
PackageDir: "/home/user/dotfiles",
TargetDir: "/home/user",
FS: adapters.NewOSFilesystem(),
Logger: adapters.NewNoopLogger(),
}
if err := cfg.Validate(); err != nil {
log.Fatal(err)
}
Observability ¶
The library provides first-class observability through injected ports:
- Structured logging via Logger interface (slog compatible)
- Distributed tracing via Tracer interface (OpenTelemetry compatible)
- Metrics collection via Metrics interface (Prometheus compatible)
Example with full observability:
cfg := dot.Config{
PackageDir: "/home/user/dotfiles",
TargetDir: "/home/user",
FS: adapters.NewOSFilesystem(),
Logger: adapters.NewSlogLogger(slog.Default()),
Tracer: otelTracer, // Your OpenTelemetry tracer
Metrics: promMetrics, // Your Prometheus metrics
}
Testing ¶
The library is designed for testability:
- All operations accept context.Context for cancellation
- Filesystem abstraction enables testing without disk I/O
- Pure functional core enables property-based testing
- Interface-based Client enables mocking
Example test using in-memory filesystem:
func TestMyTool(t *testing.T) {
fs := adapters.NewMemFS()
cfg := dot.Config{
PackageDir: "/test/packages",
TargetDir: "/test/target",
FS: fs,
Logger: adapters.NewNoopLogger(),
}
client, _ := dot.NewClient(cfg)
err := client.Manage(ctx, "vim")
require.NoError(t, err)
}
Error Handling ¶
All operations return explicit errors. Common error types:
- ErrInvalidPath: Path validation failed
- ErrPackageNotFound: Package doesn't exist in PackageDir
- ErrConflict: Conflict detected during operation
- ErrCyclicDependency: Circular dependency in operations
- ErrMultiple: Multiple errors occurred
Error types implement error with descriptive messages. CLI-facing formatting and remediation suggestions are produced by internal/cli/errors, not by the error types themselves.
Safety Guarantees ¶
The library provides strong safety guarantees:
- Type safety: Phantom types prevent path mixing at compile time
- Transaction safety: Two-phase commit with rollback of executed operations on failure
- Conflict detection: All conflicts reported before modification
- Rollback accounting: Operations that cannot be reverted are reported in ErrExecutionFailed.RollbackFailed rather than silently dropped
- Thread safety: All Client operations safe for concurrent use
Implementation Status ¶
All core operations are fully implemented:
- Client interface with registration pattern
- Manage/PlanManage operations with dependency resolution
- Unmanage operations with restore, purge, and cleanup options
- Adopt operations with file and directory support
- Status/List query operations
Future enhancements:
- Streaming API for large operations
- ConfigBuilder for fluent configuration
- Performance optimizations for large package sets
For architecture details, see docs/developer/architecture.md. For the CLI layering contract, see docs/developer/cli-architecture.md.
Index ¶
- Constants
- func GetConfigPath(appName string) string
- func IsManifestNotFoundError(err error) bool
- func UntranslateDotfile(name string) string
- func UpgradeConfig(configPath string, force bool) (string, error)
- func UserFacingError(err error) string
- type AdoptService
- type Attribute
- type BootstrapResult
- type BootstrapService
- type Client
- func (c *Client) Adopt(ctx context.Context, files []string, pkg string) error
- func (c *Client) Clone(ctx context.Context, repoURL string, opts CloneOptions) error
- func (c *Client) Config() Config
- func (c *Client) Doctor(ctx context.Context) (DiagnosticReport, error)
- func (c *Client) DoctorIgnoreLink(ctx context.Context, linkPath, reason string) error
- func (c *Client) DoctorIgnorePattern(ctx context.Context, pattern string) error
- func (c *Client) DoctorListIgnored(ctx context.Context) (map[string]IgnoredLink, []string, error)
- func (c *Client) DoctorUnignoreLink(ctx context.Context, linkPath string) error
- func (c *Client) DoctorUnignorePattern(ctx context.Context, pattern string) error
- func (c *Client) DoctorWithMode(ctx context.Context, mode DiagnosticMode, scanCfg ScanConfig) (DiagnosticReport, error)
- func (c *Client) DoctorWithScan(ctx context.Context, scanCfg ScanConfig) (DiagnosticReport, error)
- func (c *Client) GenerateBootstrap(ctx context.Context, opts GenerateBootstrapOptions) (BootstrapResult, error)
- func (c *Client) List(ctx context.Context) ([]PackageInfo, error)
- func (c *Client) Manage(ctx context.Context, packages ...string) error
- func (c *Client) PlanAdopt(ctx context.Context, files []string, pkg string) (Plan, error)
- func (c *Client) PlanManage(ctx context.Context, packages ...string) (Plan, error)
- func (c *Client) PlanRemanage(ctx context.Context, packages ...string) (Plan, error)
- func (c *Client) PlanUnmanage(ctx context.Context, packages ...string) (Plan, error)
- func (c *Client) Remanage(ctx context.Context, packages ...string) error
- func (c *Client) RepositoryInfo(ctx context.Context) (RepositoryInfo, bool, error)
- func (c *Client) Status(ctx context.Context, packages ...string) (Status, error)
- func (c *Client) Triage(ctx context.Context, scanCfg ScanConfig, opts TriageOptions) (TriageResult, error)
- func (c *Client) Unmanage(ctx context.Context, packages ...string) error
- func (c *Client) UnmanageAll(ctx context.Context, opts UnmanageOptions) (int, error)
- func (c *Client) UnmanageWithOptions(ctx context.Context, opts UnmanageOptions, packages ...string) error
- func (c *Client) WriteBootstrap(ctx context.Context, data []byte, outputPath string) error
- type CloneOptions
- type CloneService
- type Config
- type ConfigBuilder
- func (b *ConfigBuilder) Build() Config
- func (b *ConfigBuilder) BuildRaw() Config
- func (b *ConfigBuilder) IsBackupSet() bool
- func (b *ConfigBuilder) IsDryRunSet() bool
- func (b *ConfigBuilder) IsFoldingSet() bool
- func (b *ConfigBuilder) IsInteractiveLargeFilesSet() bool
- func (b *ConfigBuilder) IsOverwriteSet() bool
- func (b *ConfigBuilder) IsPackageNameMappingSet() bool
- func (b *ConfigBuilder) IsPerPackageIgnoreSet() bool
- func (b *ConfigBuilder) IsUseDefaultIgnorePatternsSet() bool
- func (b *ConfigBuilder) WithBackup(v bool) *ConfigBuilder
- func (b *ConfigBuilder) WithBackupDir(dir string) *ConfigBuilder
- func (b *ConfigBuilder) WithConcurrency(n int) *ConfigBuilder
- func (b *ConfigBuilder) WithDryRun(v bool) *ConfigBuilder
- func (b *ConfigBuilder) WithFS(fs FS) *ConfigBuilder
- func (b *ConfigBuilder) WithFolding(v bool) *ConfigBuilder
- func (b *ConfigBuilder) WithIgnorePatterns(patterns []string) *ConfigBuilder
- func (b *ConfigBuilder) WithInteractiveLargeFiles(v bool) *ConfigBuilder
- func (b *ConfigBuilder) WithLinkMode(mode LinkMode) *ConfigBuilder
- func (b *ConfigBuilder) WithLogger(logger Logger) *ConfigBuilder
- func (b *ConfigBuilder) WithManifestDir(dir string) *ConfigBuilder
- func (b *ConfigBuilder) WithMaxFileSize(size int64) *ConfigBuilder
- func (b *ConfigBuilder) WithMetrics(metrics Metrics) *ConfigBuilder
- func (b *ConfigBuilder) WithOverwrite(v bool) *ConfigBuilder
- func (b *ConfigBuilder) WithPackageDir(dir string) *ConfigBuilder
- func (b *ConfigBuilder) WithPackageNameMapping(v bool) *ConfigBuilder
- func (b *ConfigBuilder) WithPerPackageIgnore(v bool) *ConfigBuilder
- func (b *ConfigBuilder) WithStdin(r io.Reader) *ConfigBuilder
- func (b *ConfigBuilder) WithStdout(w io.Writer) *ConfigBuilder
- func (b *ConfigBuilder) WithTargetDir(dir string) *ConfigBuilder
- func (b *ConfigBuilder) WithTracer(tracer Tracer) *ConfigBuilder
- func (b *ConfigBuilder) WithUseDefaultIgnorePatterns(v bool) *ConfigBuilder
- func (b *ConfigBuilder) WithVerbosity(v int) *ConfigBuilder
- type ConfigLoader
- type ConfigWriter
- type ConflictInfo
- type Counter
- type DiagnosticMode
- type DiagnosticReport
- type DiagnosticStats
- type DirCopy
- type DirCreate
- type DirDelete
- type DirEntry
- type DirRemoveAll
- type DoctorService
- func (s *DoctorService) Doctor(ctx context.Context) (DiagnosticReport, error)
- func (s *DoctorService) DoctorWithMode(ctx context.Context, mode DiagnosticMode, scanCfg ScanConfig) (DiagnosticReport, error)
- func (s *DoctorService) DoctorWithScan(ctx context.Context, scanCfg ScanConfig) (DiagnosticReport, error)
- func (s *DoctorService) Fix(ctx context.Context, scanCfg ScanConfig, opts FixOptions) (FixResult, error)
- func (s *DoctorService) IgnoreLink(ctx context.Context, linkPath, reason string) error
- func (s *DoctorService) IgnorePattern(ctx context.Context, pattern string) error
- func (s *DoctorService) ListIgnored(ctx context.Context) (map[string]manifest.IgnoredLink, []string, error)
- func (s *DoctorService) PreFlightCheck(ctx context.Context, packages []string) (DiagnosticReport, error)
- func (s *DoctorService) Triage(ctx context.Context, scanCfg ScanConfig, opts TriageOptions) (TriageResult, error)
- func (s *DoctorService) UnignoreLink(ctx context.Context, linkPath string) error
- func (s *DoctorService) UnignorePattern(ctx context.Context, pattern string) error
- type ErrAuthFailed
- type ErrBootstrapExists
- type ErrBootstrapNotFound
- type ErrCheckpointNotFound
- type ErrCloneFailed
- type ErrConflict
- type ErrCyclicDependency
- type ErrDuplicateTarget
- type ErrEmptyPlan
- type ErrExecutionFailed
- type ErrFilesystemOperation
- type ErrInvalidBootstrap
- type ErrInvalidPath
- type ErrMultiple
- type ErrNoChanges
- type ErrNotImplemented
- type ErrPackageDirNotEmpty
- type ErrPackageNotFound
- type ErrParentNotFound
- type ErrPermissionDenied
- type ErrProfileNotFound
- type ErrSourceNotFound
- type ErrTargetKindConflict
- type ExecutionResult
- type ExtendedConfig
- type FS
- type FSReader
- type FSWriter
- type FileBackup
- type FileDelete
- type FileInfo
- type FileMove
- type FilePath
- type FixOptions
- type FixResult
- type Gauge
- type GenerateBootstrapOptions
- type GitHubRelease
- type HealthChecker
- type HealthStatus
- type Histogram
- type IgnoredLink
- type Issue
- type IssueSeverity
- type IssueType
- type LinkCreate
- type LinkDelete
- type LinkHealthResult
- type LinkMode
- type Logger
- type ManageService
- func (s *ManageService) Manage(ctx context.Context, packages ...string) error
- func (s *ManageService) PlanManage(ctx context.Context, packages ...string) (Plan, error)
- func (s *ManageService) PlanRemanage(ctx context.Context, packages ...string) (Plan, error)
- func (s *ManageService) Remanage(ctx context.Context, packages ...string) error
- type ManifestService
- func (s *ManifestService) Load(ctx context.Context, targetPath TargetPath) domain.Result[manifest.Manifest]
- func (s *ManifestService) RemovePackage(ctx context.Context, targetPath TargetPath, pkg string) error
- func (s *ManifestService) RemovePackages(ctx context.Context, targetPath TargetPath, pkgs []string) error
- func (s *ManifestService) Save(ctx context.Context, targetPath TargetPath, m manifest.Manifest) error
- func (s *ManifestService) Update(ctx context.Context, targetPath TargetPath, packageDir string, ...) error
- func (s *ManifestService) UpdateWithSource(ctx context.Context, targetPath TargetPath, packageDir string, ...) error
- type Metrics
- type Node
- type NodeType
- type Operation
- type OperationID
- type OperationKind
- type OrphanGroup
- type Package
- type PackageInfo
- type PackageManager
- type PackagePath
- type Plan
- type PlanMetadata
- type RepositoryInfo
- type Result
- func Collect[T any](results []Result[T]) Result[[]T]
- func Err[T any](err error) Result[T]
- func FlatMap[T, U any](r Result[T], fn func(T) Result[U]) Result[U]
- func Map[T, U any](r Result[T], fn func(T) U) Result[U]
- func NewFilePath(s string) Result[FilePath]
- func NewPackagePath(s string) Result[PackagePath]
- func NewTargetPath(s string) Result[TargetPath]
- func Ok[T any](value T) Result[T]
- type ScanConfig
- type ScanMode
- type SecretDetection
- type SensitivePattern
- type Span
- type SpanOption
- type StartupChecker
- type Status
- type StatusService
- type TargetPath
- type Tracer
- type TriageOptions
- type TriageResult
- type UnmanageOptions
- type UnmanageService
- func (s *UnmanageService) PlanUnmanage(ctx context.Context, packages ...string) (Plan, error)
- func (s *UnmanageService) Unmanage(ctx context.Context, packages ...string) error
- func (s *UnmanageService) UnmanageAll(ctx context.Context, opts UnmanageOptions) (int, error)
- func (s *UnmanageService) UnmanageWithOptions(ctx context.Context, opts UnmanageOptions, packages ...string) error
- type UpdateCheckResult
- type VersionChecker
- type WarningInfo
- type WriteOptions
Constants ¶
const ( NodeFile = domain.NodeFile NodeDir = domain.NodeDir NodeSymlink = domain.NodeSymlink )
NodeType constants
const ( OpKindLinkCreate = domain.OpKindLinkCreate OpKindLinkDelete = domain.OpKindLinkDelete OpKindDirCreate = domain.OpKindDirCreate OpKindDirDelete = domain.OpKindDirDelete OpKindDirRemoveAll = domain.OpKindDirRemoveAll OpKindFileMove = domain.OpKindFileMove OpKindFileBackup = domain.OpKindFileBackup OpKindFileDelete = domain.OpKindFileDelete OpKindDirCopy = domain.OpKindDirCopy )
Operation kind constants
Variables ¶
This section is empty.
Functions ¶
func GetConfigPath ¶ added in v0.6.3
GetConfigPath returns XDG-compliant configuration directory path.
func IsManifestNotFoundError ¶
IsManifestNotFoundError checks if an error indicates a missing manifest.
func UntranslateDotfile ¶ added in v0.6.3
UntranslateDotfile converts a dotfile name to its untranslated package form. Example: ".ssh" -> "dot-ssh"
func UpgradeConfig ¶ added in v0.6.3
UpgradeConfig upgrades the configuration file to the latest format.
func UserFacingError ¶
UserFacingError converts an error into a user-friendly message.
Types ¶
type AdoptService ¶
type AdoptService struct {
// contains filtered or unexported fields
}
AdoptService handles file adoption operations.
func (*AdoptService) Adopt ¶
Adopt moves existing files from target into package then creates symlinks.
func (*AdoptService) GetManagedPaths ¶
func (s *AdoptService) GetManagedPaths(ctx context.Context) (map[string]struct{}, error)
GetManagedPaths returns a map of all paths currently managed by dot. The map keys are absolute paths that are already symlinked. This is useful for filtering out already-managed files during discovery.
type BootstrapResult ¶
type BootstrapResult struct {
// Config is the generated bootstrap configuration
Config bootstrap.Config
// YAML is the marshaled configuration
YAML []byte
// PackageCount is the number of packages included
PackageCount int
// InstalledCount is the number of packages currently installed
InstalledCount int
}
BootstrapResult contains the generated bootstrap configuration.
type BootstrapService ¶
type BootstrapService struct {
// contains filtered or unexported fields
}
BootstrapService handles bootstrap configuration generation.
func (*BootstrapService) GenerateBootstrap ¶
func (s *BootstrapService) GenerateBootstrap(ctx context.Context, opts GenerateBootstrapOptions) (BootstrapResult, error)
GenerateBootstrap creates a bootstrap configuration from the current installation.
The method:
- Scans package directory for available packages
- Reads manifest to identify installed packages
- Generates bootstrap configuration with appropriate defaults
- Marshals configuration to YAML
Returns an error if:
- Package directory cannot be scanned
- No packages are found
- Configuration generation fails
- YAML marshaling fails
func (*BootstrapService) WriteBootstrap ¶
func (s *BootstrapService) WriteBootstrap(ctx context.Context, data []byte, outputPath string) error
WriteBootstrap writes the bootstrap configuration to a file.
Returns an error if:
- File already exists (unless Force option was set during generation)
- File cannot be written
type Client ¶
type Client struct {
// contains filtered or unexported fields
}
Client provides the high-level API for dot operations.
Client acts as a facade that delegates operations to specialized services. This design provides clean separation of concerns while maintaining a simple public API.
All operations are safe for concurrent use from multiple goroutines.
func NewClient ¶
NewClient creates a new Client with the given configuration.
Returns an error if:
- Configuration is invalid (see Config.Validate)
- Required dependencies are missing (FS, Logger)
The returned Client is safe for concurrent use from multiple goroutines.
func (*Client) Clone ¶
Clone clones a dotfiles repository and installs packages.
Workflow:
- Validates package directory is empty (unless Force=true)
- Clones repository to package directory
- Loads optional bootstrap configuration
- Selects packages (via profile, interactive, or all)
- Filters packages by current platform
- Installs selected packages
- Updates manifest with repository tracking
Returns an error if:
- Package directory is not empty (and Force=false)
- Authentication fails
- Clone operation fails
- Bootstrap config is invalid
- Package installation fails
func (*Client) Doctor ¶
func (c *Client) Doctor(ctx context.Context) (DiagnosticReport, error)
Doctor performs health checks with default scan configuration.
func (*Client) DoctorIgnoreLink ¶ added in v0.6.6
DoctorIgnoreLink adds a target-relative symlink path to the doctor ignore list.
func (*Client) DoctorIgnorePattern ¶ added in v0.6.6
DoctorIgnorePattern adds a glob pattern to the doctor ignore list.
func (*Client) DoctorListIgnored ¶ added in v0.6.6
DoctorListIgnored returns the doctor ignore list: ignored links keyed by target-relative path, and ignored glob patterns.
func (*Client) DoctorUnignoreLink ¶ added in v0.6.6
DoctorUnignoreLink removes a symlink path from the doctor ignore list.
func (*Client) DoctorUnignorePattern ¶ added in v0.6.6
DoctorUnignorePattern removes a glob pattern from the doctor ignore list.
func (*Client) DoctorWithMode ¶
func (c *Client) DoctorWithMode(ctx context.Context, mode DiagnosticMode, scanCfg ScanConfig) (DiagnosticReport, error)
DoctorWithMode performs health checks with explicit mode and scan configuration.
func (*Client) DoctorWithScan ¶
func (c *Client) DoctorWithScan(ctx context.Context, scanCfg ScanConfig) (DiagnosticReport, error)
DoctorWithScan performs health checks with explicit scan configuration.
func (*Client) GenerateBootstrap ¶
func (c *Client) GenerateBootstrap(ctx context.Context, opts GenerateBootstrapOptions) (BootstrapResult, error)
GenerateBootstrap creates a bootstrap configuration from current installation.
Workflow:
- Discovers packages in package directory
- Reads manifest to identify installed packages (optional)
- Generates bootstrap configuration with defaults
- Marshals configuration to YAML
Returns bootstrap result containing configuration and YAML, or an error if:
- No packages found
- Configuration generation fails
- YAML marshaling fails
func (*Client) List ¶
func (c *Client) List(ctx context.Context) ([]PackageInfo, error)
List returns all installed packages from the manifest.
func (*Client) PlanManage ¶
PlanManage computes the execution plan for managing packages without applying changes.
func (*Client) PlanRemanage ¶
PlanRemanage computes incremental execution plan using hash-based change detection.
func (*Client) PlanUnmanage ¶
PlanUnmanage computes the execution plan for unmanaging packages.
func (*Client) Remanage ¶
Remanage reinstalls packages using incremental hash-based change detection.
func (*Client) RepositoryInfo ¶ added in v0.7.0
RepositoryInfo returns the repository information recorded in the manifest, covering the clone URL, branch, commit and selected profile.
The boolean result reports whether any repository information is recorded: installations that were never cloned, and manifests written before the field existed, report false. Reading the manifest uses the same store as every other command, so the configured manifest directory is honoured.
func (*Client) Triage ¶
func (c *Client) Triage(ctx context.Context, scanCfg ScanConfig, opts TriageOptions) (TriageResult, error)
Triage performs interactive triage of orphaned symlinks.
func (*Client) Unmanage ¶
Unmanage removes the specified packages by deleting symlinks. Adopted packages are automatically restored unless disabled.
func (*Client) UnmanageAll ¶
UnmanageAll removes all installed packages with specified options. Returns the count of packages unmanaged.
func (*Client) UnmanageWithOptions ¶
func (c *Client) UnmanageWithOptions(ctx context.Context, opts UnmanageOptions, packages ...string) error
UnmanageWithOptions removes packages with specified options.
type CloneOptions ¶
type CloneOptions struct {
// Profile specifies which bootstrap profile to use.
// If empty, uses default profile or interactive selection.
Profile string
// Interactive forces interactive package selection.
// If false, uses profile or installs all packages.
Interactive bool
// Force allows cloning into non-empty packageDir.
Force bool
// Branch specifies which branch to clone.
// If empty, clones default branch.
Branch string
}
CloneOptions configures repository cloning behavior.
type CloneService ¶
type CloneService struct {
// contains filtered or unexported fields
}
CloneService handles repository cloning and package installation.
func (*CloneService) Clone ¶
func (s *CloneService) Clone(ctx context.Context, repoURL string, opts CloneOptions) error
Clone clones a repository and installs packages.
Workflow:
- Validate packageDir is empty (unless Force=true)
- Resolve authentication from environment
- Clone repository to packageDir
- Load bootstrap config if present, resolving the host profile from its machines section when no profile was requested
- Select packages (profile, interactive, or all)
- Filter packages by current platform
- Install selected packages via ManageService
- Update manifest with repository information
type Config ¶
type Config struct {
// PackageDir is the source directory containing packages.
// Must be an absolute path.
PackageDir string
// TargetDir is the destination directory for symlinks.
// Must be an absolute path.
TargetDir string
// LinkMode specifies whether to create relative or absolute symlinks.
LinkMode LinkMode
// Folding enables directory-level linking when all contents
// belong to a single package.
Folding bool
// DryRun enables preview mode without applying changes.
DryRun bool
// Verbosity controls logging detail (0=quiet, 1=info, 2=debug, 3=trace).
Verbosity int
// BackupDir specifies where to store backup files.
// If empty, backups go to <TargetDir>/.dot-backup/
BackupDir string
// Backup enables automatic backup of conflicting files.
// When true, conflicting files are backed up before being replaced.
Backup bool
// Overwrite enables automatic overwriting of conflicting files.
// When true, conflicting files are deleted before creating symlinks.
// Takes precedence over Backup if both are true.
Overwrite bool
// ManifestDir specifies where to store the manifest file.
// If empty, manifest is stored in TargetDir for backward compatibility.
ManifestDir string
// Concurrency limits parallel operation execution.
// If zero, defaults to runtime.NumCPU().
Concurrency int
// Translate enables dot- prefix to . translation in file names.
// When enabled, "dot-vimrc" becomes ".vimrc" in the target.
// Default: true. Use boolPtr(false) to disable.
Translate *bool
// PackageNameMapping enables package name to target directory mapping.
// When enabled, package "dot-gnupg" targets ~/.gnupg/ instead of ~/.
// Default: true (project is pre-1.0, breaking change acceptable)
PackageNameMapping bool
// IgnorePatterns contains additional ignore patterns beyond defaults.
// Supports glob patterns and negation with ! prefix.
IgnorePatterns []string
// UseDefaultIgnorePatterns controls whether default patterns are applied.
// Default: true (.git, .DS_Store, etc.)
UseDefaultIgnorePatterns bool
// PerPackageIgnore enables reading .dotignore files from packages.
// Default: true
PerPackageIgnore bool
// MaxFileSize is the maximum file size to include in bytes (0 = no limit).
MaxFileSize int64
// InteractiveLargeFiles enables prompting for large files in TTY mode.
// Default: true
InteractiveLargeFiles bool
// Stdin is the input reader for interactive prompts.
// Defaults to os.Stdin if nil.
Stdin io.Reader
// Stdout is the output writer for interactive prompts.
// Defaults to os.Stdout if nil.
Stdout io.Writer
// Infrastructure dependencies (required)
FS FS
Logger Logger
Tracer Tracer
Metrics Metrics
}
Config holds configuration for the dot Client.
func (Config) WithDefaults ¶
WithDefaults returns a copy of the config with defaults applied.
type ConfigBuilder ¶ added in v0.6.4
type ConfigBuilder struct {
// contains filtered or unexported fields
}
ConfigBuilder provides a fluent interface for constructing Config objects. It tracks which optional boolean fields have been explicitly set, allowing distinction between unset (use default) and explicitly set to false.
func NewConfigBuilder ¶ added in v0.6.4
func NewConfigBuilder() *ConfigBuilder
NewConfigBuilder creates a new ConfigBuilder with zero values. Use the With* methods to set fields, then call Build() to get the Config.
func (*ConfigBuilder) Build ¶ added in v0.6.4
func (b *ConfigBuilder) Build() Config
Build returns the constructed Config. This applies defaults for optional bool fields that were not explicitly set.
func (*ConfigBuilder) BuildRaw ¶ added in v0.6.4
func (b *ConfigBuilder) BuildRaw() Config
BuildRaw returns the constructed Config without applying defaults. Use this when you need to inspect exactly what was set.
func (*ConfigBuilder) IsBackupSet ¶ added in v0.6.4
func (b *ConfigBuilder) IsBackupSet() bool
IsBackupSet returns whether Backup was explicitly set.
func (*ConfigBuilder) IsDryRunSet ¶ added in v0.6.4
func (b *ConfigBuilder) IsDryRunSet() bool
IsDryRunSet returns whether DryRun was explicitly set.
func (*ConfigBuilder) IsFoldingSet ¶ added in v0.6.4
func (b *ConfigBuilder) IsFoldingSet() bool
IsFoldingSet returns whether Folding was explicitly set.
func (*ConfigBuilder) IsInteractiveLargeFilesSet ¶ added in v0.6.4
func (b *ConfigBuilder) IsInteractiveLargeFilesSet() bool
IsInteractiveLargeFilesSet returns whether InteractiveLargeFiles was explicitly set.
func (*ConfigBuilder) IsOverwriteSet ¶ added in v0.6.4
func (b *ConfigBuilder) IsOverwriteSet() bool
IsOverwriteSet returns whether Overwrite was explicitly set.
func (*ConfigBuilder) IsPackageNameMappingSet ¶ added in v0.6.4
func (b *ConfigBuilder) IsPackageNameMappingSet() bool
IsPackageNameMappingSet returns whether PackageNameMapping was explicitly set.
func (*ConfigBuilder) IsPerPackageIgnoreSet ¶ added in v0.6.4
func (b *ConfigBuilder) IsPerPackageIgnoreSet() bool
IsPerPackageIgnoreSet returns whether PerPackageIgnore was explicitly set.
func (*ConfigBuilder) IsUseDefaultIgnorePatternsSet ¶ added in v0.6.4
func (b *ConfigBuilder) IsUseDefaultIgnorePatternsSet() bool
IsUseDefaultIgnorePatternsSet returns whether UseDefaultIgnorePatterns was explicitly set.
func (*ConfigBuilder) WithBackup ¶ added in v0.6.4
func (b *ConfigBuilder) WithBackup(v bool) *ConfigBuilder
WithBackup sets whether backup is enabled.
func (*ConfigBuilder) WithBackupDir ¶ added in v0.6.4
func (b *ConfigBuilder) WithBackupDir(dir string) *ConfigBuilder
WithBackupDir sets the backup directory.
func (*ConfigBuilder) WithConcurrency ¶ added in v0.6.4
func (b *ConfigBuilder) WithConcurrency(n int) *ConfigBuilder
WithConcurrency sets the concurrency limit.
func (*ConfigBuilder) WithDryRun ¶ added in v0.6.4
func (b *ConfigBuilder) WithDryRun(v bool) *ConfigBuilder
WithDryRun sets whether dry run mode is enabled.
func (*ConfigBuilder) WithFS ¶ added in v0.6.4
func (b *ConfigBuilder) WithFS(fs FS) *ConfigBuilder
WithFS sets the filesystem implementation.
func (*ConfigBuilder) WithFolding ¶ added in v0.6.4
func (b *ConfigBuilder) WithFolding(v bool) *ConfigBuilder
WithFolding sets whether directory folding is enabled.
func (*ConfigBuilder) WithIgnorePatterns ¶ added in v0.6.4
func (b *ConfigBuilder) WithIgnorePatterns(patterns []string) *ConfigBuilder
WithIgnorePatterns sets additional ignore patterns.
func (*ConfigBuilder) WithInteractiveLargeFiles ¶ added in v0.6.4
func (b *ConfigBuilder) WithInteractiveLargeFiles(v bool) *ConfigBuilder
WithInteractiveLargeFiles sets whether to prompt for large files. Default is true when not explicitly set.
func (*ConfigBuilder) WithLinkMode ¶ added in v0.6.4
func (b *ConfigBuilder) WithLinkMode(mode LinkMode) *ConfigBuilder
WithLinkMode sets the symlink creation mode.
func (*ConfigBuilder) WithLogger ¶ added in v0.6.4
func (b *ConfigBuilder) WithLogger(logger Logger) *ConfigBuilder
WithLogger sets the logger implementation.
func (*ConfigBuilder) WithManifestDir ¶ added in v0.6.4
func (b *ConfigBuilder) WithManifestDir(dir string) *ConfigBuilder
WithManifestDir sets the manifest directory.
func (*ConfigBuilder) WithMaxFileSize ¶ added in v0.6.4
func (b *ConfigBuilder) WithMaxFileSize(size int64) *ConfigBuilder
WithMaxFileSize sets the maximum file size.
func (*ConfigBuilder) WithMetrics ¶ added in v0.6.4
func (b *ConfigBuilder) WithMetrics(metrics Metrics) *ConfigBuilder
WithMetrics sets the metrics implementation.
func (*ConfigBuilder) WithOverwrite ¶ added in v0.6.4
func (b *ConfigBuilder) WithOverwrite(v bool) *ConfigBuilder
WithOverwrite sets whether overwrite is enabled.
func (*ConfigBuilder) WithPackageDir ¶ added in v0.6.4
func (b *ConfigBuilder) WithPackageDir(dir string) *ConfigBuilder
WithPackageDir sets the package directory.
func (*ConfigBuilder) WithPackageNameMapping ¶ added in v0.6.4
func (b *ConfigBuilder) WithPackageNameMapping(v bool) *ConfigBuilder
WithPackageNameMapping sets whether package name mapping is enabled. Default is true when not explicitly set.
func (*ConfigBuilder) WithPerPackageIgnore ¶ added in v0.6.4
func (b *ConfigBuilder) WithPerPackageIgnore(v bool) *ConfigBuilder
WithPerPackageIgnore sets whether per-package .dotignore files are read. Default is true when not explicitly set.
func (*ConfigBuilder) WithStdin ¶ added in v0.6.4
func (b *ConfigBuilder) WithStdin(r io.Reader) *ConfigBuilder
WithStdin sets the input reader.
func (*ConfigBuilder) WithStdout ¶ added in v0.6.4
func (b *ConfigBuilder) WithStdout(w io.Writer) *ConfigBuilder
WithStdout sets the output writer.
func (*ConfigBuilder) WithTargetDir ¶ added in v0.6.4
func (b *ConfigBuilder) WithTargetDir(dir string) *ConfigBuilder
WithTargetDir sets the target directory.
func (*ConfigBuilder) WithTracer ¶ added in v0.6.4
func (b *ConfigBuilder) WithTracer(tracer Tracer) *ConfigBuilder
WithTracer sets the tracer implementation.
func (*ConfigBuilder) WithUseDefaultIgnorePatterns ¶ added in v0.6.4
func (b *ConfigBuilder) WithUseDefaultIgnorePatterns(v bool) *ConfigBuilder
WithUseDefaultIgnorePatterns sets whether default ignore patterns are used. Default is true when not explicitly set.
func (*ConfigBuilder) WithVerbosity ¶ added in v0.6.4
func (b *ConfigBuilder) WithVerbosity(v int) *ConfigBuilder
WithVerbosity sets the verbosity level.
type ConfigLoader ¶ added in v0.6.3
type ConfigLoader struct {
// contains filtered or unexported fields
}
ConfigLoader handles configuration loading with precedence.
func NewConfigLoader ¶ added in v0.6.3
func NewConfigLoader(appName, configPath string) *ConfigLoader
NewConfigLoader creates a new configuration loader.
func (*ConfigLoader) LoadWithEnv ¶ added in v0.6.3
func (l *ConfigLoader) LoadWithEnv() (*ExtendedConfig, error)
LoadWithEnv loads configuration with environment variable overrides.
type ConfigWriter ¶ added in v0.6.3
type ConfigWriter struct {
// contains filtered or unexported fields
}
ConfigWriter wraps the internal config writer.
func NewConfigWriter ¶ added in v0.6.3
func NewConfigWriter(path string) *ConfigWriter
NewConfigWriter creates a new config writer for the given path.
func (*ConfigWriter) Update ¶ added in v0.6.3
func (w *ConfigWriter) Update(key, value string) error
Update updates a configuration value by key.
func (*ConfigWriter) WriteDefault ¶ added in v0.6.3
func (w *ConfigWriter) WriteDefault(opts config.WriteOptions) error
WriteDefault writes default configuration with options.
type ConflictInfo ¶
type ConflictInfo = domain.ConflictInfo
ConflictInfo represents conflict information in plan metadata.
type DiagnosticMode ¶
type DiagnosticMode string
DiagnosticMode defines the depth of diagnostic checks to perform.
const ( // DiagnosticFast performs only essential checks (managed packages, manifest integrity). DiagnosticFast DiagnosticMode = "fast" // DiagnosticDeep performs comprehensive checks including orphan detection. DiagnosticDeep DiagnosticMode = "deep" )
type DiagnosticReport ¶
type DiagnosticReport struct {
OverallHealth HealthStatus `json:"overall_health" yaml:"overall_health"`
Issues []Issue `json:"issues" yaml:"issues"`
Statistics DiagnosticStats `json:"statistics" yaml:"statistics"`
}
DiagnosticReport contains health check results.
type DiagnosticStats ¶
type DiagnosticStats struct {
TotalLinks int `json:"total_links" yaml:"total_links"`
BrokenLinks int `json:"broken_links" yaml:"broken_links"`
OrphanedLinks int `json:"orphaned_links" yaml:"orphaned_links"`
ManagedLinks int `json:"managed_links" yaml:"managed_links"`
}
DiagnosticStats contains summary statistics.
type DirCopy ¶
DirCopy recursively copies a directory.
func NewDirCopy ¶
func NewDirCopy(id OperationID, source, dest FilePath) DirCopy
NewDirCopy creates a new DirCopy operation.
type DirCreate ¶
DirCreate creates a directory.
func NewDirCreate ¶
func NewDirCreate(id OperationID, path FilePath) DirCreate
NewDirCreate creates a new DirCreate operation.
type DirDelete ¶
DirDelete removes a directory.
func NewDirDelete ¶
func NewDirDelete(id OperationID, path FilePath) DirDelete
NewDirDelete creates a new DirDelete operation.
func NewDirDeleteWithMode ¶ added in v0.6.6
func NewDirDeleteWithMode(id OperationID, path FilePath, mode os.FileMode) DirDelete
NewDirDeleteWithMode creates a DirDelete operation that records the directory permissions observed at plan time so rollback can restore them.
type DirRemoveAll ¶
type DirRemoveAll = domain.DirRemoveAll
DirRemoveAll recursively removes a directory and all its contents.
func NewDirRemoveAll ¶
func NewDirRemoveAll(id OperationID, path FilePath) DirRemoveAll
NewDirRemoveAll creates a new DirRemoveAll operation.
type DoctorService ¶
type DoctorService struct {
// contains filtered or unexported fields
}
DoctorService handles health check and diagnostic operations.
func (*DoctorService) Doctor ¶
func (s *DoctorService) Doctor(ctx context.Context) (DiagnosticReport, error)
Doctor performs health checks with default scan configuration.
func (*DoctorService) DoctorWithMode ¶
func (s *DoctorService) DoctorWithMode(ctx context.Context, mode DiagnosticMode, scanCfg ScanConfig) (DiagnosticReport, error)
DoctorWithMode performs health checks with explicit mode and configuration.
func (*DoctorService) DoctorWithScan ¶
func (s *DoctorService) DoctorWithScan(ctx context.Context, scanCfg ScanConfig) (DiagnosticReport, error)
DoctorWithScan performs health checks with explicit scan configuration.
func (*DoctorService) Fix ¶
func (s *DoctorService) Fix(ctx context.Context, scanCfg ScanConfig, opts FixOptions) (FixResult, error)
Fix repairs broken symlinks found during doctor scan.
func (*DoctorService) IgnoreLink ¶
func (s *DoctorService) IgnoreLink(ctx context.Context, linkPath, reason string) error
IgnoreLink adds a symlink to the ignore list.
func (*DoctorService) IgnorePattern ¶
func (s *DoctorService) IgnorePattern(ctx context.Context, pattern string) error
IgnorePattern adds a glob pattern to ignore list.
func (*DoctorService) ListIgnored ¶
func (s *DoctorService) ListIgnored(ctx context.Context) (map[string]manifest.IgnoredLink, []string, error)
ListIgnored returns all ignored links and patterns.
func (*DoctorService) PreFlightCheck ¶
func (s *DoctorService) PreFlightCheck(ctx context.Context, packages []string) (DiagnosticReport, error)
PreFlightCheck performs quick checks before an operation.
func (*DoctorService) Triage ¶
func (s *DoctorService) Triage(ctx context.Context, scanCfg ScanConfig, opts TriageOptions) (TriageResult, error)
Triage performs interactive triage of orphaned symlinks.
func (*DoctorService) UnignoreLink ¶
func (s *DoctorService) UnignoreLink(ctx context.Context, linkPath string) error
UnignoreLink removes a symlink from ignore list.
func (*DoctorService) UnignorePattern ¶ added in v0.6.6
func (s *DoctorService) UnignorePattern(ctx context.Context, pattern string) error
UnignorePattern removes a glob pattern from the ignore list.
type ErrAuthFailed ¶
type ErrAuthFailed struct {
Cause error
}
ErrAuthFailed indicates authentication failure during git clone.
func (ErrAuthFailed) Error ¶
func (e ErrAuthFailed) Error() string
func (ErrAuthFailed) Is ¶ added in v0.6.4
func (e ErrAuthFailed) Is(target error) bool
Is implements errors.Is for ErrAuthFailed.
func (ErrAuthFailed) Unwrap ¶
func (e ErrAuthFailed) Unwrap() error
type ErrBootstrapExists ¶
type ErrBootstrapExists struct {
Path string
}
ErrBootstrapExists indicates the bootstrap file already exists.
func (ErrBootstrapExists) Error ¶
func (e ErrBootstrapExists) Error() string
func (ErrBootstrapExists) Is ¶ added in v0.6.4
func (e ErrBootstrapExists) Is(target error) bool
Is implements errors.Is for ErrBootstrapExists.
type ErrBootstrapNotFound ¶
type ErrBootstrapNotFound struct {
Path string
}
ErrBootstrapNotFound indicates the bootstrap configuration file was not found.
func (ErrBootstrapNotFound) Error ¶
func (e ErrBootstrapNotFound) Error() string
func (ErrBootstrapNotFound) Is ¶ added in v0.6.4
func (e ErrBootstrapNotFound) Is(target error) bool
Is implements errors.Is for ErrBootstrapNotFound.
type ErrCheckpointNotFound ¶
type ErrCheckpointNotFound = domain.ErrCheckpointNotFound
ErrCheckpointNotFound represents a missing checkpoint error.
type ErrCloneFailed ¶
ErrCloneFailed indicates repository cloning failed.
func (ErrCloneFailed) Error ¶
func (e ErrCloneFailed) Error() string
func (ErrCloneFailed) Is ¶ added in v0.6.4
func (e ErrCloneFailed) Is(target error) bool
Is implements errors.Is for ErrCloneFailed.
func (ErrCloneFailed) Unwrap ¶
func (e ErrCloneFailed) Unwrap() error
type ErrConflict ¶
type ErrConflict = domain.ErrConflict
ErrConflict represents a conflict during installation.
type ErrCyclicDependency ¶
type ErrCyclicDependency = domain.ErrCyclicDependency
ErrCyclicDependency represents a dependency cycle error.
type ErrDuplicateTarget ¶ added in v0.7.0
type ErrDuplicateTarget = domain.ErrDuplicateTarget
ErrDuplicateTarget represents two packages claiming the same target path.
type ErrEmptyPlan ¶
type ErrEmptyPlan = domain.ErrEmptyPlan
ErrEmptyPlan represents an empty plan error.
type ErrExecutionFailed ¶
type ErrExecutionFailed = domain.ErrExecutionFailed
ErrExecutionFailed represents an execution failure error.
type ErrFilesystemOperation ¶
type ErrFilesystemOperation = domain.ErrFilesystemOperation
ErrFilesystemOperation represents a filesystem operation error.
type ErrInvalidBootstrap ¶
ErrInvalidBootstrap indicates the bootstrap configuration is invalid.
func (ErrInvalidBootstrap) Error ¶
func (e ErrInvalidBootstrap) Error() string
func (ErrInvalidBootstrap) Is ¶ added in v0.6.4
func (e ErrInvalidBootstrap) Is(target error) bool
Is implements errors.Is for ErrInvalidBootstrap.
func (ErrInvalidBootstrap) Unwrap ¶
func (e ErrInvalidBootstrap) Unwrap() error
type ErrInvalidPath ¶
type ErrInvalidPath = domain.ErrInvalidPath
ErrInvalidPath represents a path validation error.
type ErrMultiple ¶
type ErrMultiple = domain.ErrMultiple
ErrMultiple represents multiple aggregated errors.
type ErrNoChanges ¶ added in v0.6.4
type ErrNoChanges struct {
Packages []string
}
ErrNoChanges indicates that an operation found no changes to apply.
func (ErrNoChanges) Error ¶ added in v0.6.4
func (e ErrNoChanges) Error() string
func (ErrNoChanges) Is ¶ added in v0.6.4
func (e ErrNoChanges) Is(target error) bool
Is implements errors.Is for ErrNoChanges.
type ErrNotImplemented ¶
type ErrNotImplemented = domain.ErrNotImplemented
ErrNotImplemented represents a not implemented error.
type ErrPackageDirNotEmpty ¶
ErrPackageDirNotEmpty indicates the package directory is not empty.
func (ErrPackageDirNotEmpty) Error ¶
func (e ErrPackageDirNotEmpty) Error() string
func (ErrPackageDirNotEmpty) Is ¶ added in v0.6.4
func (e ErrPackageDirNotEmpty) Is(target error) bool
Is implements errors.Is for ErrPackageDirNotEmpty.
func (ErrPackageDirNotEmpty) Unwrap ¶
func (e ErrPackageDirNotEmpty) Unwrap() error
type ErrPackageNotFound ¶
type ErrPackageNotFound = domain.ErrPackageNotFound
ErrPackageNotFound represents a missing package error.
type ErrParentNotFound ¶
type ErrParentNotFound = domain.ErrParentNotFound
ErrParentNotFound represents a missing parent directory error.
type ErrPermissionDenied ¶
type ErrPermissionDenied = domain.ErrPermissionDenied
ErrPermissionDenied represents a permission denied error.
type ErrProfileNotFound ¶
type ErrProfileNotFound struct {
Profile string
}
ErrProfileNotFound indicates the requested profile does not exist.
func (ErrProfileNotFound) Error ¶
func (e ErrProfileNotFound) Error() string
func (ErrProfileNotFound) Is ¶ added in v0.6.4
func (e ErrProfileNotFound) Is(target error) bool
Is implements errors.Is for ErrProfileNotFound.
type ErrSourceNotFound ¶
type ErrSourceNotFound = domain.ErrSourceNotFound
ErrSourceNotFound represents a missing source file error.
type ErrTargetKindConflict ¶ added in v0.7.0
type ErrTargetKindConflict = domain.ErrTargetKindConflict
ErrTargetKindConflict represents one package wanting a target path to be a link while another needs it to be a directory.
type ExecutionResult ¶
type ExecutionResult = domain.ExecutionResult
ExecutionResult contains the outcome of plan execution.
type ExtendedConfig ¶ added in v0.6.3
type ExtendedConfig = config.ExtendedConfig
ExtendedConfig contains all application configuration. It is an alias to the internal ExtendedConfig to provide a stable API.
func DefaultExtendedConfig ¶ added in v0.6.3
func DefaultExtendedConfig() *ExtendedConfig
DefaultExtendedConfig returns extended configuration with sensible defaults.
func LoadExtendedFromFile ¶ added in v0.6.3
func LoadExtendedFromFile(path string) (*ExtendedConfig, error)
LoadExtendedFromFile loads extended configuration from specified file.
type FS ¶
FS combines all filesystem operations (read and write).
func NewOSFilesystem ¶ added in v0.6.3
func NewOSFilesystem() FS
NewOSFilesystem returns a filesystem implementation that uses the OS filesystem.
type FileBackup ¶
type FileBackup = domain.FileBackup
FileBackup backs up a file before modification.
func NewFileBackup ¶
func NewFileBackup(id OperationID, source, backup FilePath) FileBackup
NewFileBackup creates a new FileBackup operation.
type FileDelete ¶
type FileDelete = domain.FileDelete
FileDelete deletes a file.
func NewFileDelete ¶
func NewFileDelete(id OperationID, path FilePath) FileDelete
NewFileDelete creates a new FileDelete operation.
func NewFileDeleteWithBackup ¶ added in v0.6.6
func NewFileDeleteWithBackup(id OperationID, path, backup FilePath) FileDelete
NewFileDeleteWithBackup creates a FileDelete operation that records the path of a backup copy so rollback can restore the deleted file.
type FileMove ¶
FileMove moves a file from one location to another.
func NewFileMove ¶
func NewFileMove(id OperationID, source TargetPath, dest FilePath) FileMove
NewFileMove creates a new FileMove operation.
type FilePath ¶
FilePath is a path to a file or directory within a package. Includes methods: String(), Join(), Parent(), Equals()
func MustParsePath ¶
MustParsePath creates a FilePath from a string, panicking on error. This function is intended for use in tests only where paths are known to be valid. Production code should use NewFilePath which returns a Result for proper error handling.
type FixOptions ¶
type FixOptions struct {
DryRun bool
AutoConfirm bool // --yes flag
Interactive bool // Prompt user for decisions
}
FixOptions configures fix behavior.
type GenerateBootstrapOptions ¶
type GenerateBootstrapOptions struct {
// FromManifest only includes packages from manifest
FromManifest bool
// ConflictPolicy sets default conflict resolution policy
ConflictPolicy string
// IncludeComments adds helpful comments to output
IncludeComments bool
// Force allows overwriting existing bootstrap files
Force bool
}
GenerateBootstrapOptions configures bootstrap generation.
type GitHubRelease ¶ added in v0.6.3
type GitHubRelease = updater.GitHubRelease
GitHubRelease represents a GitHub release.
type HealthChecker ¶
type HealthChecker struct {
// contains filtered or unexported fields
}
HealthChecker provides unified health checking logic for symlinks.
func (*HealthChecker) CheckLink ¶
func (h *HealthChecker) CheckLink(ctx context.Context, pkgName, linkPath, packageDir string) LinkHealthResult
CheckLink validates a single symlink and returns detailed health information. This is the single source of truth for link health checking.
func (*HealthChecker) CheckPackage ¶
func (h *HealthChecker) CheckPackage(ctx context.Context, pkgName string, links []string, packageDir string) (bool, string)
CheckPackage validates all symlinks for a package and returns aggregated health status. Returns healthy status and issue type if problems are found.
type HealthStatus ¶
type HealthStatus int
HealthStatus represents the overall health of the installation.
const ( // HealthOK indicates no issues found. HealthOK HealthStatus = iota // HealthWarnings indicates non-critical issues found. HealthWarnings // HealthErrors indicates critical issues found. HealthErrors )
func (HealthStatus) MarshalJSON ¶
func (h HealthStatus) MarshalJSON() ([]byte, error)
MarshalJSON marshals HealthStatus as a string.
func (HealthStatus) MarshalYAML ¶
func (h HealthStatus) MarshalYAML() (interface{}, error)
MarshalYAML marshals HealthStatus as a string.
func (HealthStatus) String ¶
func (h HealthStatus) String() string
String returns the string representation of health status.
type IgnoredLink ¶ added in v0.6.6
type IgnoredLink = manifest.IgnoredLink
IgnoredLink describes a symlink the user acknowledged and wants doctor to ignore.
type Issue ¶
type Issue struct {
Severity IssueSeverity `json:"severity" yaml:"severity"`
Type IssueType `json:"type" yaml:"type"`
Path string `json:"path,omitempty" yaml:"path,omitempty"`
Message string `json:"message" yaml:"message"`
Suggestion string `json:"suggestion,omitempty" yaml:"suggestion,omitempty"`
}
Issue represents a single diagnostic issue.
type IssueSeverity ¶
type IssueSeverity int
IssueSeverity indicates the severity of an issue.
const ( // SeverityInfo represents informational messages. SeverityInfo IssueSeverity = iota // SeverityWarning represents non-critical issues. SeverityWarning // SeverityError represents critical issues requiring attention. SeverityError )
func (IssueSeverity) MarshalJSON ¶
func (s IssueSeverity) MarshalJSON() ([]byte, error)
MarshalJSON marshals IssueSeverity as a string.
func (IssueSeverity) MarshalYAML ¶
func (s IssueSeverity) MarshalYAML() (interface{}, error)
MarshalYAML marshals IssueSeverity as a string.
func (IssueSeverity) String ¶
func (s IssueSeverity) String() string
String returns the string representation of severity.
type IssueType ¶
type IssueType int
IssueType categorizes the type of issue.
const ( // IssueBrokenLink indicates a symlink pointing to a non-existent target. IssueBrokenLink IssueType = iota // IssueOrphanedLink indicates a symlink not managed by any package. IssueOrphanedLink // IssueWrongTarget indicates a symlink pointing to an unexpected target. IssueWrongTarget // IssuePermission indicates insufficient permissions for an operation. IssuePermission // IssueCircular indicates a circular symlink reference. IssueCircular // IssueManifestInconsistency indicates mismatch between manifest and filesystem. IssueManifestInconsistency )
func (IssueType) MarshalJSON ¶
MarshalJSON marshals IssueType as a string.
func (IssueType) MarshalYAML ¶
MarshalYAML marshals IssueType as a string.
type LinkCreate ¶
type LinkCreate = domain.LinkCreate
LinkCreate creates a symbolic link.
func NewLinkCreate ¶
func NewLinkCreate(id OperationID, source FilePath, target TargetPath) LinkCreate
NewLinkCreate creates a new LinkCreate operation.
type LinkDelete ¶
type LinkDelete = domain.LinkDelete
LinkDelete removes a symbolic link.
func NewLinkDelete ¶
func NewLinkDelete(id OperationID, target TargetPath) LinkDelete
NewLinkDelete creates a new LinkDelete operation.
func NewLinkDeleteWithDestination ¶ added in v0.6.6
func NewLinkDeleteWithDestination(id OperationID, target TargetPath, destination string) LinkDelete
NewLinkDeleteWithDestination creates a LinkDelete operation that records the symlink destination observed at plan time.
type LinkHealthResult ¶
type LinkHealthResult struct {
IsHealthy bool
IssueType IssueType
Severity IssueSeverity
Message string
Suggestion string
}
LinkHealthResult contains detailed health information for a single link.
type Logger ¶
Logger provides structured logging.
func NewJSONLogger ¶ added in v0.6.3
NewJSONLogger returns a configured JSON logger.
func NewNoopLogger ¶ added in v0.6.3
func NewNoopLogger() Logger
NewNoopLogger returns a logger that discards all output.
func NewSlogLogger ¶ added in v0.6.3
NewSlogLogger returns a logger backed by slog.
type ManageService ¶
type ManageService struct {
// contains filtered or unexported fields
}
ManageService handles package installation (manage and remanage operations).
func (*ManageService) Manage ¶
func (s *ManageService) Manage(ctx context.Context, packages ...string) error
Manage installs the specified packages by creating symlinks.
func (*ManageService) PlanManage ¶
PlanManage computes the execution plan for managing packages without applying changes.
func (*ManageService) PlanRemanage ¶
PlanRemanage computes incremental execution plan using hash-based change detection.
type ManifestService ¶
type ManifestService struct {
// contains filtered or unexported fields
}
ManifestService manages manifest operations.
func (*ManifestService) Load ¶
func (s *ManifestService) Load(ctx context.Context, targetPath TargetPath) domain.Result[manifest.Manifest]
Load loads the manifest from the target directory.
func (*ManifestService) RemovePackage ¶
func (s *ManifestService) RemovePackage(ctx context.Context, targetPath TargetPath, pkg string) error
RemovePackage removes a package from the manifest.
func (*ManifestService) RemovePackages ¶ added in v0.6.5
func (s *ManifestService) RemovePackages(ctx context.Context, targetPath TargetPath, pkgs []string) error
RemovePackages removes multiple packages from the manifest in a single load-save cycle.
func (*ManifestService) Save ¶
func (s *ManifestService) Save(ctx context.Context, targetPath TargetPath, m manifest.Manifest) error
Save saves the manifest to the target directory.
func (*ManifestService) Update ¶
func (s *ManifestService) Update(ctx context.Context, targetPath TargetPath, packageDir string, packages []string, plan Plan) error
Update updates the manifest with package information from a plan.
func (*ManifestService) UpdateWithSource ¶
func (s *ManifestService) UpdateWithSource(ctx context.Context, targetPath TargetPath, packageDir string, packages []string, plan Plan, source manifest.PackageSource) error
UpdateWithSource updates the manifest with package information and source type.
type Metrics ¶
Metrics provides metrics collection.
func NewNoopMetrics ¶
func NewNoopMetrics() Metrics
NewNoopMetrics returns a metrics collector that does nothing.
type OperationID ¶
type OperationID = domain.OperationID
OperationID uniquely identifies an operation.
type OperationKind ¶
type OperationKind = domain.OperationKind
OperationKind identifies the type of operation.
type OrphanGroup ¶
type OrphanGroup struct {
Category *doctor.PatternCategory
Links []Issue
Confidence string
Pattern string // Suggested ignore pattern
IsUncategorized bool
}
OrphanGroup groups orphaned symlinks by category.
type PackageInfo ¶
type PackageInfo struct {
Name string `json:"name" yaml:"name"`
Source string `json:"source" yaml:"source"`
InstalledAt time.Time `json:"installed_at" yaml:"installed_at"`
LinkCount int `json:"link_count" yaml:"link_count"`
Links []string `json:"links" yaml:"links"`
TargetDir string `json:"target_dir,omitempty" yaml:"target_dir,omitempty"`
PackageDir string `json:"package_dir,omitempty" yaml:"package_dir,omitempty"`
IsHealthy bool `json:"is_healthy" yaml:"is_healthy"`
IssueType string `json:"issue_type,omitempty" yaml:"issue_type,omitempty"`
}
PackageInfo contains metadata about an installed package.
type PackageManager ¶ added in v0.6.3
type PackageManager = updater.PackageManager
PackageManager represents a package manager for upgrades.
func ResolvePackageManager ¶ added in v0.6.3
func ResolvePackageManager(configured string) (PackageManager, error)
ResolvePackageManager resolves the package manager based on configuration.
type PackagePath ¶
type PackagePath = domain.PackagePath
PackagePath is a path to a package directory. Includes methods: String(), Join(), Parent(), Equals()
type PlanMetadata ¶
type PlanMetadata = domain.PlanMetadata
PlanMetadata contains statistics and diagnostic information about a plan.
type RepositoryInfo ¶ added in v0.7.0
type RepositoryInfo = manifest.RepositoryInfo
RepositoryInfo is the repository provenance recorded at clone time.
type Result ¶
Result represents a value or an error, implementing a Result monad for error handling. This provides a functional approach to error handling with composition support.
This is a re-export of domain.Result. See internal/domain for implementation.
func Collect ¶
Collect aggregates a slice of Results into a Result containing a slice. Returns Err if any Result is Err, otherwise returns Ok with all values.
func FlatMap ¶
FlatMap applies a function that returns a Result to the contained value if Ok. This is the monadic bind operation, enabling composition of Result-returning functions.
func Map ¶
Map applies a function to the contained value if Ok, otherwise propagates the error. This is the functorial map operation.
func NewFilePath ¶
NewFilePath creates a new file path with validation.
func NewPackagePath ¶
func NewPackagePath(s string) Result[PackagePath]
NewPackagePath creates a new package path with validation.
func NewTargetPath ¶
func NewTargetPath(s string) Result[TargetPath]
NewTargetPath creates a new target path with validation.
type ScanConfig ¶
type ScanConfig struct {
// Mode determines the scanning strategy.
Mode ScanMode
// MaxDepth limits directory recursion depth.
// Values <= 0 are normalized to 3 (scoped) or 10 (deep) by constructor helpers.
// Default: 3 (scoped), 10 (deep)
MaxDepth int
// ScopeToDirs limits scanning to specific directories.
// Empty means auto-detect from manifest (for ScanScoped) or target dir (for ScanDeep).
ScopeToDirs []string
// SkipPatterns are directory names/patterns to skip during scanning.
// Default constructors include common large directories unlikely to contain dotfile symlinks.
SkipPatterns []string
// MaxWorkers limits parallel directory scanning goroutines.
// Values <= 0 default to runtime.NumCPU().
// Set to 1 to disable parallel scanning.
// Default: 0 (use NumCPU)
MaxWorkers int
// MaxIssues limits the number of issues to collect before stopping scan.
// Values <= 0 mean unlimited (scan everything).
// Useful for fast health checks without full enumeration.
// Default: 0 (unlimited)
MaxIssues int
}
ScanConfig controls orphaned link detection behavior.
func DeepScanConfig ¶
func DeepScanConfig(maxDepth int) ScanConfig
DeepScanConfig returns a scan configuration for deep scanning.
func DefaultScanConfig ¶
func DefaultScanConfig() ScanConfig
DefaultScanConfig returns the default scan configuration (scoped). Scoped scanning checks directories containing managed links for orphaned symlinks.
func ScopedScanConfig ¶
func ScopedScanConfig() ScanConfig
ScopedScanConfig returns a scan configuration for scoped scanning.
type ScanMode ¶
type ScanMode int
ScanMode controls orphaned link detection behavior.
const ( // ScanOff disables orphaned link detection (fastest, use --scan-mode=off to enable). ScanOff ScanMode = iota // ScanScoped only scans directories containing managed links (default, recommended). ScanScoped // ScanDeep performs full recursive scan with depth limits (slowest, thorough). ScanDeep )
type SecretDetection ¶ added in v0.6.3
type SecretDetection = doctor.SecretDetection
SecretDetection represents a detected potential secret.
func DetectSecrets ¶ added in v0.6.3
func DetectSecrets(files []string, patterns []SensitivePattern) []SecretDetection
DetectSecrets scans files for potential secrets using the provided patterns.
type SensitivePattern ¶ added in v0.6.3
type SensitivePattern = doctor.SensitivePattern
SensitivePattern represents a pattern for detecting sensitive information.
func DefaultSensitivePatterns ¶ added in v0.6.3
func DefaultSensitivePatterns() []SensitivePattern
DefaultSensitivePatterns returns the default patterns for secret detection.
type StartupChecker ¶ added in v0.6.3
type StartupChecker struct {
// contains filtered or unexported fields
}
StartupChecker checks for updates at startup. It wraps the internal StartupChecker.
func NewStartupChecker ¶ added in v0.6.3
func NewStartupChecker(currentVersion string, cfg *ExtendedConfig, configDir string, output io.Writer) *StartupChecker
NewStartupChecker creates a new startup update checker.
func (*StartupChecker) Check ¶ added in v0.6.3
func (c *StartupChecker) Check() (*UpdateCheckResult, error)
Check performs the update check.
func (*StartupChecker) ShowNotification ¶ added in v0.6.3
func (c *StartupChecker) ShowNotification(result *UpdateCheckResult)
ShowNotification displays an update notification if available.
type Status ¶
type Status struct {
Packages []PackageInfo `json:"packages" yaml:"packages"`
NotFound []string `json:"not_found,omitempty" yaml:"not_found,omitempty"`
}
Status represents the installation state of packages.
type StatusService ¶
type StatusService struct {
// contains filtered or unexported fields
}
StatusService handles status and listing operations.
func (*StatusService) List ¶
func (s *StatusService) List(ctx context.Context) ([]PackageInfo, error)
List returns all installed packages from the manifest.
type TargetPath ¶
type TargetPath = domain.TargetPath
TargetPath is a path to a target directory. Includes methods: String(), Join(), Parent(), Equals()
func MustParseTargetPath ¶
func MustParseTargetPath(s string) TargetPath
MustParseTargetPath creates a TargetPath from a string, panicking on error. This function is intended for use in tests only where paths are known to be valid. Production code should use NewTargetPath which returns a Result for proper error handling.
Panic is appropriate here because: - Function is only used in test code with hardcoded, known-valid paths - Panicking on test setup errors fails fast and clearly indicates test bugs - Test failures from panic are easier to debug than silent errors
type TriageOptions ¶
type TriageOptions struct {
AutoIgnoreHighConfidence bool // Automatically ignore high confidence categories
DryRun bool // Show what would change without modifying
AutoConfirm bool // Skip confirmation prompts (--yes flag)
}
TriageOptions configures triage behavior.
type TriageResult ¶
type TriageResult struct {
Ignored []string // Links ignored
Patterns []string // Patterns added
Adopted map[string]string // Link -> package name
Skipped []string // Links skipped
Errors map[string]error // Link -> error
}
TriageResult contains the results of a triage operation.
type UnmanageOptions ¶
type UnmanageOptions struct {
// Purge deletes the package directory instead of restoring files
Purge bool
// Restore moves adopted files back to target directory (default for adopted packages)
Restore bool
// Cleanup removes orphaned manifest entries (packages with no links or missing directories)
Cleanup bool
}
UnmanageOptions configures unmanage behavior.
func DefaultUnmanageOptions ¶
func DefaultUnmanageOptions() UnmanageOptions
DefaultUnmanageOptions returns default unmanage options.
type UnmanageService ¶
type UnmanageService struct {
// contains filtered or unexported fields
}
UnmanageService handles package removal (unmanage operations).
func (*UnmanageService) PlanUnmanage ¶
PlanUnmanage computes the execution plan for unmanaging packages.
func (*UnmanageService) Unmanage ¶
func (s *UnmanageService) Unmanage(ctx context.Context, packages ...string) error
Unmanage removes the specified packages by deleting symlinks. Uses default options (restore adopted packages, don't purge).
func (*UnmanageService) UnmanageAll ¶
func (s *UnmanageService) UnmanageAll(ctx context.Context, opts UnmanageOptions) (int, error)
UnmanageAll removes all installed packages with specified options. Returns the count of packages unmanaged.
func (*UnmanageService) UnmanageWithOptions ¶
func (s *UnmanageService) UnmanageWithOptions(ctx context.Context, opts UnmanageOptions, packages ...string) error
UnmanageWithOptions removes packages with specified options.
type UpdateCheckResult ¶ added in v0.6.3
type UpdateCheckResult = updater.CheckResult
UpdateCheckResult contains the result of an update check.
type VersionChecker ¶ added in v0.6.3
type VersionChecker struct {
// contains filtered or unexported fields
}
VersionChecker checks for new versions on GitHub.
func NewVersionChecker ¶ added in v0.6.3
func NewVersionChecker(repository string) *VersionChecker
NewVersionChecker creates a new version checker.
func (*VersionChecker) CheckForUpdate ¶ added in v0.6.3
func (v *VersionChecker) CheckForUpdate(currentVersion string, includePrerelease bool) (*GitHubRelease, bool, error)
CheckForUpdate checks if a new version is available.
type WarningInfo ¶
type WarningInfo = domain.WarningInfo
WarningInfo represents warning information in plan metadata.
type WriteOptions ¶ added in v0.6.3
type WriteOptions = config.WriteOptions
WriteOptions contains options for writing configuration.
Source Files
¶
- adapters.go
- adopt_service.go
- bootstrap_service.go
- cli_support.go
- client.go
- clone_service.go
- config.go
- configuration.go
- conflict.go
- diagnostics.go
- doc.go
- doctor_fix.go
- doctor_ignore.go
- doctor_service.go
- doctor_triage.go
- domain.go
- errors.go
- execution.go
- github.go
- health_checker.go
- manage_service.go
- manifest_service.go
- operation.go
- path.go
- ports.go
- result.go
- scanner.go
- secrets.go
- status.go
- status_service.go
- unmanage_service.go
- updater.go
- version.go