refactor(packages): extract hashline-core package
Move the hash-anchored edit core (hash computation, validation, edit operations, text normalization, chunk formatter, diff utilities, and a runtime-aware xxHash32 binding) into a new @oh-my-opencode/hashline-core workspace package. The src/tools/hashline-edit/ surface becomes a set of thin re-export shims, so existing import paths in the plugin keep working while the pure logic lives behind a stable package boundary that has no opencode runtime dependencies. Tests: bun test packages/hashline-core src/tools/hashline-edit
This commit is contained in:
@@ -1,56 +1 @@
|
||||
import { parseLineRef } from "./validation"
|
||||
import type { HashlineEdit } from "./types"
|
||||
|
||||
export function getEditLineNumber(edit: HashlineEdit): number {
|
||||
switch (edit.op) {
|
||||
case "replace":
|
||||
return parseLineRef(edit.end ?? edit.pos).line
|
||||
case "append":
|
||||
return edit.pos ? parseLineRef(edit.pos).line : Number.NEGATIVE_INFINITY
|
||||
case "prepend":
|
||||
return edit.pos ? parseLineRef(edit.pos).line : Number.NEGATIVE_INFINITY
|
||||
default:
|
||||
return Number.POSITIVE_INFINITY
|
||||
}
|
||||
}
|
||||
|
||||
export function collectLineRefs(edits: HashlineEdit[]): string[] {
|
||||
return edits.flatMap((edit) => {
|
||||
switch (edit.op) {
|
||||
case "replace":
|
||||
return edit.end ? [edit.pos, edit.end] : [edit.pos]
|
||||
case "append":
|
||||
case "prepend":
|
||||
return edit.pos ? [edit.pos] : []
|
||||
default:
|
||||
return []
|
||||
}
|
||||
})
|
||||
}
|
||||
|
||||
export function detectOverlappingRanges(edits: HashlineEdit[]): string | null {
|
||||
const ranges: { start: number; end: number; idx: number }[] = []
|
||||
for (let i = 0; i < edits.length; i++) {
|
||||
const edit = edits[i]
|
||||
if (edit.op !== "replace" || !edit.end) continue
|
||||
const start = parseLineRef(edit.pos).line
|
||||
const end = parseLineRef(edit.end).line
|
||||
ranges.push({ start, end, idx: i })
|
||||
}
|
||||
if (ranges.length < 2) return null
|
||||
|
||||
ranges.sort((a, b) => a.start - b.start || a.end - b.end)
|
||||
for (let i = 1; i < ranges.length; i++) {
|
||||
const prev = ranges[i - 1]
|
||||
const curr = ranges[i]
|
||||
if (curr.start <= prev.end) {
|
||||
return (
|
||||
`Overlapping range edits detected: ` +
|
||||
`edit ${prev.idx + 1} (lines ${prev.start}-${prev.end}) overlaps with ` +
|
||||
`edit ${curr.idx + 1} (lines ${curr.start}-${curr.end}). ` +
|
||||
`Use pos-only replace for single-line edits.`
|
||||
)
|
||||
}
|
||||
}
|
||||
return null
|
||||
}
|
||||
export { getEditLineNumber, collectLineRefs, detectOverlappingRanges } from "@oh-my-opencode/hashline-core"
|
||||
|
||||
Reference in New Issue
Block a user