Help us shape the future of Go! Take the 2026 Go Developer Survey

index

package
v0.8.0 Latest Latest
Warning

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

Go to latest
Published: Oct 18, 2026 License: Apache-2.0 Imports: 30 Imported by: 0

Documentation

Overview

Package index orchestrates a full indexing pass: walk the workspace, parse supported files, resolve call references into edges, mine git history, and write everything into the store atomically.

Index

Constants

View Source
const (
	SourceFixes   = "fixes"
	SourceReviews = "reviews"
)

Source names. BeforePersist and RefreshEvent use them.

Variables

This section is empty.

Functions

func CheckExclude added in v0.8.0

func CheckExclude(pattern string) error

CheckExclude reports why the reader rejects one exclude pattern, or nil for a valid pattern. The settings editor validates each draft item with it, so the form shows the reader's own message.

func RefreshFixes added in v0.5.0

func RefreshFixes(root, dbPath string, logf func(string, ...any)) (int, error)

RefreshFixes mines and persists only fix commits reachable from the repository's current HEAD. It performs no network access, which makes it the deterministic lesson-source mode for a pinned historical checkout.

func RefreshReviews

func RefreshReviews(root, dbPath string, logf func(string, ...any)) (res reviews.Result, fixCount int, err error)

RefreshReviews mines the lesson sources for the repo at root: PR review comments (network, via gh) and fix commits (local git) — each degrading independently, so a repo without GitHub still gains fix findings and an offline run still keeps its stored reviews. It is deliberately separate from Run: lesson sources change on the review/push cadence, not on every local edit. fixCount reports the fix findings stored this pass.

func ResolveRoot

func ResolveRoot(root string) (string, error)

ResolveRoot widens to the git toplevel when inside a repository. It is history.ResolveRoot. The name stays here, because Run applies this rule, and the CLI and the LSP server call it by this name.

func WorkspaceState

func WorkspaceState(root string) string

WorkspaceState fingerprints the workspace content the index depends on: HEAD, the status listing, the CONTENT of tracked changes (`git diff HEAD` — an already-dirty file edited again keeps its status line but not its patch), and a size+mtime proxy for untracked files (their status line never changes either). Two equal fingerprints mean the index is current. "" when git is unavailable — there is no cheap fingerprint without it.

Types

type Config

type Config struct {
	Index struct {
		// Generated indexes files carrying a "Code generated … DO NOT
		// EDIT." header. Default false: such files (protoc, stringer,
		// mockgen output) are boilerplate that inflates the graph and
		// pollutes most-called, and are not meant to be hand-navigated.
		Generated bool `yaml:"generated"`
		// Exclude is a list of gitignore-ish globs skipped on top of
		// .gitignore and the built-in skip dirs. Forms: a bare glob
		// (`*.pb.go`, `*_test.go`) matches any basename; a `**/`-prefixed
		// glob matches the basename in any directory; a trailing-slash
		// entry (`internal/gen/`) matches a directory prefix.
		Exclude []string `yaml:"exclude"`
	} `yaml:"index"`

	Reviews struct {
		// WindowDays bounds how old a mined review comment may be:
		// absent means the 730-day default, 0 means unlimited. The
		// newest 200 comments always survive the window, so a slow
		// repository keeps a working corpus with no tuning.
		WindowDays *int `yaml:"window_days"`
	} `yaml:"reviews"`
}

Config tunes what the indexer walks (`.seamark/config.yaml`). An absent file yields the defaults: generated files are skipped, nothing else is excluded. Kept separate from the gate/lessons overlays — this is about which files enter the graph at all.

func LoadConfig

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

LoadConfig reads <root>/.seamark/config.yaml. A missing file is not an error (defaults apply); a malformed one is, so a typo'd exclude is not silently ignored.

func ParseConfig added in v0.8.0

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

ParseConfig decodes the index and reviews sections from the bytes of config.yaml and checks every exclude pattern. LoadConfig calls it, so both entry points report the same error text. The settings editor calls it to validate planned bytes before a write. Empty input yields the defaults, the same as an absent file.

func (*Config) ReviewWindowDays added in v0.2.0

func (c *Config) ReviewWindowDays() int

ReviewWindowDays maps the config field onto reviews.Options semantics: 0 = default, negative = unlimited.

type Options

type Options struct {
	// Root is the workspace directory. When inside a git repository it is
	// widened to the repository toplevel so paths are repo-relative.
	Root string
	// DBPath overrides the index location (default: <root>/.seamark/index.db).
	DBPath string
	// History tunes the git mining pass.
	History history.Options
	// Force rebuilds even when the workspace fingerprint says the index
	// is already current.
	Force bool
	// Logf receives progress and warnings; nil discards them.
	Logf func(format string, args ...any)
	// Progress receives phase events for interactive surfaces: a phase
	// name with units done/total (0 total = indeterminate, reported
	// again as 1/1 when the phase ends). Nil discards — piped and agent
	// surfaces stay on Logf's plain lines.
	Progress func(phase string, done, total int)
}

Options configures one indexing run.

type RefreshEvent added in v0.8.0

type RefreshEvent struct {
	Phase  RefreshPhase
	Source string
	// Repository is the "owner/name" slug for the review phases.
	Repository string
	// Bytes is the fetched byte count for PhaseFetchBytes.
	Bytes int
	// Comments and Kept carry the counts for PhaseFetched.
	Comments int
	Kept     int
	// State is the source state for PhaseSourceDone.
	State SourceState
}

RefreshEvent is one typed progress event of an evidence refresh.

type RefreshPhase added in v0.8.0

type RefreshPhase int

RefreshPhase names one step of an evidence refresh for typed progress.

const (
	// PhaseMineFixes means the local fix mine starts. It has no progress
	// count and cannot stop part way.
	PhaseMineFixes RefreshPhase = iota + 1
	// PhaseFetchReviews means the GitHub fetch starts.
	PhaseFetchReviews
	// PhaseFetchBytes reports the fetched bytes so far. No total exists.
	PhaseFetchBytes
	// PhaseFetched reports the parsed and kept comment counts.
	PhaseFetched
	// PhaseCluster means the fetched comments are clustered.
	PhaseCluster
	// PhasePersist means a source write starts.
	PhasePersist
	// PhaseSourceDone reports the final state of one source.
	PhaseSourceDone
)

type RefreshRequest added in v0.8.0

type RefreshRequest struct {
	// Root is the workspace directory; it widens to the git top level.
	Root string
	// DBPath overrides the index location (default: <root>/.seamark/index.db).
	DBPath string
	// Mode selects the sources.
	Mode SourceMode
	// WindowDays is the review window for reviews.Options. The caller
	// resolves it, because the CLI falls back to the default on a bad
	// config file and the console blocks instead.
	WindowDays int
	// Fetch is the review fetcher; nil means gh.
	Fetch reviews.FetchFunc
	// Logf receives the CLI progress lines; nil discards them.
	Logf func(format string, args ...any)
	// Progress receives typed events; nil discards them.
	Progress func(RefreshEvent)
	// BeforePersist runs before each source opens the store, with the
	// source name. The console re-probes the database there. It runs
	// before the open and not only before the write, because store.Open
	// creates a missing database and migrates an older one. The fix
	// source runs it for an unmined result too, because its store also
	// opens then. An error aborts the source before the open: the source
	// reads stopped for a context error and failed otherwise, and the
	// refresh returns the error.
	BeforePersist func(source string) error
}

RefreshRequest configures one evidence refresh.

type RefreshResult added in v0.8.0

type RefreshResult struct {
	Fixes   SourceOutcome
	Reviews SourceOutcome
	// Review is the raw review mining result. The CLI prints from it.
	Review reviews.Result
	// FixCount is the fix finding count that the CLI prints.
	FixCount int
}

RefreshResult reports one evidence refresh.

func RefreshSources added in v0.8.0

func RefreshSources(ctx context.Context, req RefreshRequest) (RefreshResult, error)

RefreshSources mines and persists the lesson sources that req.Mode selects. The order is fixed: mine the fixes, run BeforePersist, open the store, store the fixes, close the store, fetch the reviews with ctx, run BeforePersist, reopen the store, and replace the review corpus. The fix phase runs to its end even after a stop, because the fix mine cannot stop part way; the refresh then stops before any GitHub work. No store handle stays open across the fetch. The error is non-nil only where RefreshFixes and RefreshReviews have always returned one, plus a BeforePersist error.

type SourceCause added in v0.8.0

type SourceCause int

SourceCause is the typed cause of a source state. The console picks its guidance from it, for example a gh login for CauseAuth. Reason is display text and not a contract, so callers never parse it.

const (
	// CauseNone means that no cause applies: the source refreshed, stored
	// an empty result, or did not start.
	CauseNone SourceCause = iota
	// CauseNoHistory means that the fix mine found no git repository, no
	// commit, or no git.
	CauseNoHistory
	// CauseMineFailed means that the local fix mine returned an error.
	CauseMineFailed
	// CauseNoRepository means that origin names no GitHub repository.
	CauseNoRepository
	// CauseGHMissing means that the gh executable is not on PATH.
	CauseGHMissing
	// CauseAuth means that gh reported an authentication problem: no
	// login, a bad or expired token, or a token without the needed access.
	CauseAuth
	// CauseRateLimited means that a GitHub rate limit refused the fetch.
	// A later refresh can succeed without a new login.
	CauseRateLimited
	// CauseFetchFailed means any other fetch error, for example a network
	// error, a server error, or an unknown repository.
	CauseFetchFailed
	// CauseUnreadable means that the fetched reply is not the API JSON.
	CauseUnreadable
	// CauseStopped means that a stop request ended the source.
	CauseStopped
	// CauseStore means that the index database did not open or did not
	// accept the write.
	CauseStore
	// CauseRefused means that the caller's check refused the work, for
	// example because the workspace changed after the preview.
	CauseRefused
)

func (SourceCause) String added in v0.8.0

func (c SourceCause) String() string

String returns a stable lower-case name for the cause.

type SourceMode added in v0.8.0

type SourceMode int

SourceMode selects the lesson sources that one evidence refresh mines. The two values are exactly the two CLI modes, so the console offers no source combination that the CLI lacks.

const (
	// SourcesLocal mines only local fix commits (`index --fixes-only`).
	SourcesLocal SourceMode = iota
	// SourcesReviewsAndLocal mines local fix commits first and GitHub
	// review comments second (`index --reviews`).
	SourcesReviewsAndLocal
)

func (SourceMode) String added in v0.8.0

func (m SourceMode) String() string

String returns a stable lower-case name for the mode.

type SourceOutcome added in v0.8.0

type SourceOutcome struct {
	State SourceState
	// Cause is the typed cause of a state other than refreshed and
	// successful-empty; CauseNone otherwise.
	Cause SourceCause
	// Stored counts the findings that this refresh stored for the source.
	Stored int
	// Lessons counts the stored review lessons; it is 0 for fixes.
	Lessons int
	// MinedAt is the mine stamp that this refresh wrote, in Unix
	// seconds; 0 when it wrote none.
	MinedAt int64
	// Reason explains a state other than refreshed in one safe line:
	// control characters are removed and secrets are redacted.
	Reason string
	// Err is the cause, or nil. It is for errors.Is, not for display.
	Err error
}

SourceOutcome reports what one refresh did to one source.

type SourceState added in v0.8.0

type SourceState string

SourceState is the typed outcome of one source in one refresh.

const (
	// SourceRefreshed means the source replaced its stored corpus with a
	// non-empty result and stamped the mine time.
	SourceRefreshed SourceState = "refreshed"
	// SourceEmpty means an authoritative empty result replaced the
	// stored corpus and stamped the mine time.
	SourceEmpty SourceState = "successful-empty"
	// SourceUnavailable means the source could not run, for example no
	// git history, no GitHub origin, or no gh. The stored corpus stays.
	SourceUnavailable SourceState = "unavailable"
	// SourceFailed means a fetch, parse, or write error. The stored
	// corpus stays.
	SourceFailed SourceState = "failed"
	// SourceStopped means a stop request ended the source before its
	// write. The stored corpus stays.
	SourceStopped SourceState = "stopped"
	// SourceNotAttempted means the refresh did not start the source.
	SourceNotAttempted SourceState = "not-attempted"
)

type Summary

type Summary struct {
	Root   string
	DBPath string
	// Skipped is true when the workspace fingerprint matched the index
	// and nothing was rebuilt.
	Skipped bool
	// FilesSeen counts the listed files that exist in the working tree.
	// A deleted path and a path outside a sparse checkout are not in it,
	// because no file exists to see.
	FilesSeen   int
	FilesParsed int // files a language extractor handled
	// FilesReparsed counts files actually run through tree-sitter this
	// pass; the rest were served from the parse cache. Equals FilesParsed
	// on a --force or first index.
	FilesReparsed int
	// FilesSkipped counts supported files dropped by config — generated
	// (default) or an exclude glob.
	FilesSkipped int
	// FilesDeleted counts the tracked paths that git status shows as
	// deleted and not staged, also a file that a directory replaces.
	// They are not parse errors, because no bytes exist to parse. A path
	// outside a sparse checkout is not deleted, as in git status. Outside
	// git it is always 0.
	FilesDeleted int
	ParseErrors  int
	HistoryMined bool
	// HistorySkipNote says why the history layer is absent when
	// HistoryMined is false: "not a git repository" and "mining failed"
	// are different situations and must not be conflated in output.
	HistorySkipNote string
	Stats           store.Stats
	Duration        time.Duration
}

Summary reports what a run produced.

func Run

func Run(opts Options) (*Summary, error)

Run executes a full indexing pass.

Jump to

Keyboard shortcuts

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