mirror of
https://github.com/router-for-me/CLIProxyAPI.git
synced 2026-09-03 06:35:00 +08:00
Add a no-copy GJSON parse helper
gjson.ParseBytes copies the entire document before returning a result, which is prohibitive for multi-megabyte requests. ParseGJSONBytesNoCopy mirrors the existing GetGJSONBytesNoCopy contract: the returned result references the caller's bytes, so callers must neither retain it nor mutate the buffer while it is in use.
This commit is contained in:
@@ -14,3 +14,14 @@ func GetGJSONBytesNoCopy(data []byte, path string) gjson.Result {
|
||||
}
|
||||
return gjson.Get(unsafe.String(unsafe.SliceData(data), len(data)), path)
|
||||
}
|
||||
|
||||
// ParseGJSONBytesNoCopy parses data into a GJSON result that references data
|
||||
// directly. gjson.ParseBytes copies the whole document, which is prohibitive
|
||||
// for multi-megabyte payloads. Callers must not retain the result or mutate
|
||||
// data while using it.
|
||||
func ParseGJSONBytesNoCopy(data []byte) gjson.Result {
|
||||
if len(data) == 0 {
|
||||
return gjson.Result{}
|
||||
}
|
||||
return gjson.Parse(unsafe.String(unsafe.SliceData(data), len(data)))
|
||||
}
|
||||
|
||||
@@ -1,6 +1,9 @@
|
||||
package util
|
||||
|
||||
import "testing"
|
||||
import (
|
||||
"testing"
|
||||
"unsafe"
|
||||
)
|
||||
|
||||
func TestGetGJSONBytesNoCopy(t *testing.T) {
|
||||
input := []byte(`{"request":{"contents":[{"role":"user"}]}}`)
|
||||
@@ -15,3 +18,28 @@ func TestGetGJSONBytesNoCopyEmptyInput(t *testing.T) {
|
||||
t.Fatalf("empty input result = %s, want missing", result.Raw)
|
||||
}
|
||||
}
|
||||
|
||||
func TestParseGJSONBytesNoCopy(t *testing.T) {
|
||||
input := []byte(`{"request":{"contents":[{"role":"user"}]}}`)
|
||||
root := ParseGJSONBytesNoCopy(input)
|
||||
if !root.IsObject() || root.Get("request.contents.0.role").String() != "user" {
|
||||
t.Fatalf("parsed root = %s, want user content array", root.Raw)
|
||||
}
|
||||
}
|
||||
|
||||
func TestParseGJSONBytesNoCopyReferencesInput(t *testing.T) {
|
||||
input := []byte(`{"contents":[{"role":"user"}]}`)
|
||||
root := ParseGJSONBytesNoCopy(input)
|
||||
if len(root.Raw) != len(input) {
|
||||
t.Fatalf("raw length = %d, want %d", len(root.Raw), len(input))
|
||||
}
|
||||
if unsafe.StringData(root.Raw) != unsafe.SliceData(input) {
|
||||
t.Fatal("parsed result copied the input instead of referencing it")
|
||||
}
|
||||
}
|
||||
|
||||
func TestParseGJSONBytesNoCopyEmptyInput(t *testing.T) {
|
||||
if result := ParseGJSONBytesNoCopy(nil); result.Exists() {
|
||||
t.Fatalf("empty input result = %s, want missing", result.Raw)
|
||||
}
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user