fix(frontmatter): consolidate 3 independent fence-parsers into one (#139)
Co-authored-by: Mathias <mthbqv@gmail.com>
This commit was merged in pull request #139.
This commit is contained in:
@@ -66,7 +66,7 @@ func Fix(doc []byte) ([]byte, bool, error) {
|
||||
return doc, false, fmt.Errorf("frontmatter: quoting did not repair the block: %w", err)
|
||||
}
|
||||
|
||||
_, rest, _ := split(doc)
|
||||
_, rest, _ := Split(doc)
|
||||
out := []byte(fence + "\n")
|
||||
out = append(out, fixed...)
|
||||
out = append(out, []byte(fence)...)
|
||||
@@ -122,14 +122,25 @@ func needsQuoting(value string) bool {
|
||||
|
||||
// block returns the raw YAML between the opening and closing fences.
|
||||
func block(doc []byte) ([]byte, bool) {
|
||||
b, _, ok := split(doc)
|
||||
b, _, ok := Split(doc)
|
||||
return b, ok
|
||||
}
|
||||
|
||||
// split returns the frontmatter block and everything from the closing fence
|
||||
// onward (the closing fence itself excluded, its trailing newline included).
|
||||
func split(doc []byte) (block, rest []byte, ok bool) {
|
||||
s := string(doc)
|
||||
// Split returns doc's frontmatter block and everything from the closing
|
||||
// fence onward (the closing fence itself excluded, its trailing newline
|
||||
// included), or ok=false if doc has no properly-fenced frontmatter.
|
||||
//
|
||||
// The canonical fence detector for this codebase (hyperguild#138): three
|
||||
// independent reimplementations of this same logic each grew their own gap
|
||||
// through separate bug-fixing before being consolidated here —
|
||||
// internal/mcp's needed a CRLF/BOM guard added after both silently defeated
|
||||
// its own HasPrefix check, and internal/api's closing-fence match had no
|
||||
// trailing-newline requirement, so a document ending in "\n---extra" with no
|
||||
// real newline after the fence was treated as validly closed. Both classes
|
||||
// are closed here, once, for every caller.
|
||||
func Split(doc []byte) (block, rest []byte, ok bool) {
|
||||
s := strings.TrimPrefix(string(doc), "\xef\xbb\xbf")
|
||||
s = strings.ReplaceAll(s, "\r\n", "\n")
|
||||
if !strings.HasPrefix(s, fence+"\n") {
|
||||
return nil, nil, false
|
||||
}
|
||||
@@ -139,5 +150,18 @@ func split(doc []byte) (block, rest []byte, ok bool) {
|
||||
if idx < 0 {
|
||||
return nil, nil, false
|
||||
}
|
||||
return []byte(body[:idx+1]), []byte(body[idx+1+len(fence):]), true
|
||||
// What follows the closing fence must be either a newline (a real body
|
||||
// follows) or nothing at all (the fence is the literal end of the
|
||||
// document — no body, not a bypass attempt). Anything else, e.g.
|
||||
// "\n---extra", is not a valid close: an earlier version of this check
|
||||
// accepted it, which is exactly the looser match hyperguild#138 closes.
|
||||
after := idx + 1 + len(fence)
|
||||
switch {
|
||||
case after == len(body):
|
||||
return []byte(body[:idx+1]), nil, true
|
||||
case body[after] == '\n':
|
||||
return []byte(body[:idx+1]), []byte(body[after:]), true
|
||||
default:
|
||||
return nil, nil, false
|
||||
}
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user