Documentation
¶
Overview ¶
Package mcpsrv exposes the library over the Model Context Protocol. M2.
A translation layer, not a home for logic: each tool definition validates its arguments, calls one function in internal/library, and marshals the result. It must never import internal/store.
M2 is cheap because M1 already did the work, and it is the part no existing citation-map tool has — an assistant that can answer "what connects these two papers in my library" against a graph the user owns.
Index ¶
Constants ¶
This section is empty.
Variables ¶
This section is empty.
Functions ¶
Types ¶
type Candidate ¶
type Candidate struct {
Work
TitleMatch bool `json:"title_match,omitempty" jsonschema:"the title matches the one given, allowing for case, punctuation and a typo"`
}
Candidate is one work a title could mean.
type DuplicateGroup ¶
DuplicateGroup is fetched works that share a title.
type NoTextPaper ¶ added in v0.3.0
type NoTextPaper struct {
Paper Work `json:"paper"`
Status string `json:"status" jsonschema:"no-text (a scan), gibberish, unreadable or timed-out"`
Reason string `json:"reason,omitempty"`
}
NoTextPaper is a paper whose PDF gave no searchable text.
type Page ¶
type Page struct {
Total int `json:"total" jsonschema:"how many there are in the library"`
Fetched int `json:"fetched" jsonschema:"how many of them have been fetched; the rest are stubs"`
Omitted int `json:"omitted" jsonschema:"how many were left out of works; raise limit to see more"`
Works []Work `json:"works"`
}
Page is a capped list: the works returned, and how many were left out. An assistant handed five thousand works spends its context on them and loses the thread, so no tool returns an unbounded list (§6, rule 1).
type Passage ¶ added in v0.3.0
type Passage struct {
Paper Work `json:"paper"`
Page int `json:"page" jsonschema:"the page of the PDF it is on, from 1"`
Text string `json:"text" jsonschema:"the matching stretch of the passage; matched words are between [[ and ]]"`
InRefs bool `json:"in_reference_list,omitempty" jsonschema:"the passage is from the paper's reference list"`
PDFPath string `json:"pdf_path" jsonschema:"the PDF on the user's disk"`
}
Passage is one passage that matched.
type Sentence ¶ added in v0.3.0
type Sentence struct {
Cited Work `json:"cited"`
Page int `json:"page"`
Sentence string `json:"sentence"`
Section string `json:"section,omitempty"`
}
Sentence is a place the paper cites one of its references.
type Step ¶
type Step struct {
Work
Next string `json:"next,omitempty" jsonschema:"cites: this paper cites the next one; cited_by: the next one cites this paper"`
}
Step is one paper on a chain, and how it relates to the next.
type Work ¶
type Work struct {
FilID string `json:"fil_id" jsonschema:"the library's own ID for this paper, which never changes; pass it to any other tool"`
ID string `json:"id,omitempty" jsonschema:"OpenAlex ID; also accepted by any other tool"`
OAStatus string `json:"oa_status" jsonschema:"diamond, gold, green, hybrid or bronze are free to read; closed is not; unknown until fetched"`
// Stub marks a work known only by its ID: something in the library cites
// it, but its metadata has not been fetched. It must never be presented as
// if the library knew what it is (§6, rule 3).
Stub bool `` /* 133-byte string literal not displayed */
Title string `json:"title,omitempty"`
// Authors is the byline, so that an answer can credit a paper from the
// library rather than from the model's memory. Capped like every list.
Authors []string `json:"authors,omitempty" jsonschema:"the first authors, in byline order; absent when not recorded"`
MoreAuthors int `json:"more_authors,omitempty" jsonschema:"how many further authors the byline has (et al.)"`
Year int `json:"year,omitempty"`
Type string `json:"type,omitempty"`
Venue string `json:"venue,omitempty"`
DOI string `json:"doi,omitempty"`
OAURL string `json:"oa_url,omitempty" jsonschema:"a free-to-read copy, when OpenAlex knows one"`
CitedByCount int `` /* 133-byte string literal not displayed */
Seed bool `json:"seed,omitempty" jsonschema:"the user added this paper themselves"`
Unresolved bool `json:"unresolved,omitempty" jsonschema:"OpenAlex has no record of this ID; it will never be fetched"`
}
Work is a paper as an assistant sees it. Two things are never omitted, whatever else is missing (ARCHITECTURE.md §6): an ID, so that every answer can be followed up with another call, and the open-access status, so that an assistant does not claim it can read a paper it cannot. The fil ID is always there (D17); the OpenAlex ID is there for every work OpenAlex knows.