Documentation
¶
Overview ¶
Package ingest turns documents on disk into indexed chunks: it walks folders, extracts text with provenance (page numbers, headings), and splits it for the index.
Index ¶
Constants ¶
const ( PhaseExtracting = "extracting" PhaseEmbedding = "embedding" )
Progress phases, in the order a pass runs them.
const ConfigName = ".haypile.yml"
ConfigName is the per-folder configuration file, created by `hay init` and editable by hand. The daemon watches it: saving a change reconciles the index — newly excluded files drop out, newly included ones come in.
Variables ¶
This section is empty.
Functions ¶
func SetOCR ¶ added in v0.2.0
SetOCR installs the transcriber used for pages with no extractable text (scanned PDFs). A nil fn — or never calling this — means such pages index empty, exactly as before.
Types ¶
type Chunk ¶
type Chunk struct {
Seq int
Page int // 1-based page number; 0 when the format has no pages
Text string
}
Chunk is one indexable piece of a document.
func SplitSections ¶
SplitSections chunks extracted sections for indexing. Structure decides the boundaries: chunks never cross a section (page, heading scope), and within a section paragraphs pack together up to the budget. Consecutive chunks overlap so a fact straddling a boundary is findable in both.
type Config ¶
type Config struct {
// Tag applies to searches scoped with --tag. A tag passed explicitly
// to `hay add` wins over this.
Tag string `yaml:"tag,omitempty"`
// Exclude lists doublestar patterns (gitignore-flavored globs) matched
// against paths relative to the folder: "drafts/**", "*.bak",
// "**/archive/**".
Exclude []string `yaml:"exclude,omitempty"`
}
Config is a source folder's indexing configuration.
func LoadConfig ¶
LoadConfig reads root's .haypile.yml. A missing file is a valid empty config; a malformed one is an error — silently indexing everything against the user's written intent would be worse than failing.
type Progress ¶ added in v0.3.0
type Progress struct {
Phase string `json:"phase"`
Path string `json:"path,omitempty"` // file just finished (extracting)
FilesDone int `json:"files_done"`
FilesTotal int `json:"files_total"`
BytesDone int64 `json:"bytes_done"`
BytesTotal int64 `json:"bytes_total"`
ChunksDone int `json:"chunks_done"`
ChunksTotal int `json:"chunks_total"`
}
Progress is a snapshot of one indexing pass. Extraction is measured in files and bytes because that is what the walk knows up front; embedding is measured in chunks because extraction only just created them. Totals are fixed for the life of a phase, so done/total is an honest fraction.
type Section ¶
type Section struct {
Text string
Page int // 1-based page number; 0 when the format has no pages
// ScanSkipped marks a page that looked scanned (an image, no text)
// with no vision model around to transcribe it; ScanFailed marks one
// where a model existed but errored or read nothing. Both index
// empty and both are counted into Stats, because the two situations
// need different advice and silence would be mistaken for a broken
// index.
ScanSkipped bool
ScanFailed bool
}
Section is a contiguous run of extracted text with its provenance. The chunker never merges across section boundaries — a section is the unit a citation points at (a PDF page, a markdown heading's scope).
type Stats ¶
type Stats struct {
Indexed int // files (re)indexed this pass
Skipped int // files already indexed and unchanged
Failed int // files whose extraction failed (indexing continues)
Chunks int // chunks written this pass
Embedded int // vectors computed this pass (cache hits excluded)
// ScanSkipped counts pages that looked scanned (an image, no text)
// but had no vision model to transcribe them; ScanFailed counts
// pages where the model errored or read nothing. Both index empty.
// Surfaced by the CLI and web UI so the silence is never mistaken
// for a broken index.
ScanSkipped int
ScanFailed int
}
Stats reports what one IndexFolder pass did.
func IndexFolder ¶
func IndexFolder(st *index.Store, folder, tag string, emb embed.Embedder, progress func(Progress)) (Stats, error)
IndexFolder walks folder, indexes every supported file into st, and prunes records for files that vanished from disk. Unchanged files (same content hash) are skipped. If emb is non-nil, chunks are embedded for semantic search, cheapest first: the content-addressed cache is consulted before the model runs. progress, if non-nil, receives a snapshot after every file and every embedding batch.