Documentation
¶
Index ¶
- Variables
- func Marshal(v any, opts ...any) (string, error)
- func ReadArray(s *Scanner) ([]any, error)
- func ReadArrayCallback(s *Scanner, callback func(any) error) error
- func ReadObject(s *Scanner) (map[string]any, error)
- func ReadObjectCallback(s *Scanner, callback func(k string, v any) error) error
- func ReadValue(s *Scanner) (any, error)
- type ArrMarshaler
- type ArrayWriter
- type FloatPrecision
- type ObjMarshaler
- type ObjectWriter
- type Scanner
- type ScannerFlag
- type StrMarshaler
- type UnsupportedTypeError
Examples ¶
Constants ¶
This section is empty.
Variables ¶
var ( ErrUnexpectedToken = errors.New("unexpected token") ErrUnexpectedEOF = errors.New("unexpected EOF") ErrInvalidNumber = errors.New("invalid number") ErrInvalidString = errors.New("invalid string") ErrInvalidUnicodeEscape = errors.New("invalid unicode escape") ErrNumericValueOutOfRange = errors.New("numeric value out of range") )
Functions ¶
func Marshal ¶
Marshal marshals any supported value into a JSON string.
Example (Array) ¶
// Marshal arrays and slices
numbers := []int{1, 2, 3}
result, _ := Marshal(numbers)
fmt.Println(result)
Output: [1,2,3]
Example (CustomObject) ¶
// Marshal custom object
person := Person{name: "John", age: 30}
result, _ := Marshal(person)
fmt.Println(result)
Output: {"name":"John","age":30}
Example (FloatPrecision) ¶
// Control float precision
pi := 3.14159265359
result, _ := Marshal(pi, FloatPrecision{Precision: 3})
fmt.Println(result)
Output: 3.14
Example (FunctionalArray) ¶
result, _ := Marshal(func(w ArrayWriter) error {
w.Element(1)
w.Element(2)
w.Element(3)
return nil
})
fmt.Println(result)
Output: [1,2,3]
Example (FunctionalNested) ¶
result, _ := Marshal(func(w ObjectWriter) error {
w.Member("name", "John")
w.Member("address", func(w ObjectWriter) error {
w.Member("street", "123 Main St")
w.Member("city", "Springfield")
return nil
})
w.Member("hobbies", func(w ArrayWriter) error {
w.Element("reading")
w.Element("coding")
return nil
})
w.Member("scores", map[string]int{
"math": 95,
"english": 87,
})
return nil
})
fmt.Println(result)
Output: {"name":"John","address":{"street":"123 Main St","city":"Springfield"},"hobbies":["reading","coding"],"scores":{"english":87,"math":95}}
Example (FunctionalObject) ¶
result, _ := Marshal(func(w ObjectWriter) error {
w.Member("name", "John")
w.Member("age", 30)
w.Member("hobbies", []string{"reading", "coding"})
return nil
})
fmt.Println(result)
Output: {"name":"John","age":30,"hobbies":["reading","coding"]}
Example (Nested) ¶
container := ArrayContainer{data: []int{1, 2}}
nested := []any{container, "str", 42}
result, _ := Marshal(nested)
fmt.Println(result)
Output: [[1,2],"str",42]
Example (Primitives) ¶
// Marshal primitive types
fmt.Println(Marshal("hello")) // string
fmt.Println(Marshal(42)) // int
fmt.Println(Marshal(3.14)) // float
fmt.Println(Marshal(true)) // bool
fmt.Println(Marshal(nil)) // null
Output: "hello" <nil> 42 <nil> 3.14 <nil> true <nil> null <nil>
func ReadArray ¶
ReadArray reads a JSON array and returns it as []any
Example (Direct) ¶
input := `[
42,
"hello",
true,
{"key": "value"},
[1, 2, 3]
]`
scanner := NewScanner([]byte(input))
arr, err := ReadArray(scanner)
if err != nil {
fmt.Printf("error: %v\n", err)
return
}
fmt.Printf("%#v\n", arr)
Output: []interface {}{42, "hello", true, map[string]interface {}{"key":"value"}, []interface {}{1, 2, 3}}
func ReadArrayCallback ¶
ReadArrayCallback reads a JSON array and invokes the callback function for each element. This allows for memory-efficient processing of arrays without storing the entire structure.
Example:
err := ReadArrayCallback(scanner, func(value any) error {
fmt.Printf("value: %v\n", value)
return nil
})
Example ¶
input := `[
{"type": "user", "name": "John"},
{"type": "order", "id": "A123"},
{"type": "user", "name": "Jane"},
{"type": "order", "id": "B456"}
]`
scanner := NewScanner([]byte(input))
err := ReadArrayCallback(scanner, func(value any) error {
// Type-check and process each array element
if obj, ok := value.(map[string]any); ok {
switch obj["type"] {
case "user":
fmt.Printf("Found user: %v\n", obj["name"])
case "order":
fmt.Printf("Found order: %v\n", obj["id"])
}
}
return nil
})
if err != nil {
fmt.Printf("error: %v\n", err)
}
Output: Found user: John Found order: A123 Found user: Jane Found order: B456
func ReadObject ¶
ReadObject reads a JSON object and returns it as map[string]any
Example (Direct) ¶
input := `{
"name": "John",
"age": 30,
"hobbies": ["reading", "music"],
"address": {
"city": "New York",
"zip": "10001"
}
}`
scanner := NewScanner([]byte(input))
obj, err := ReadObject(scanner)
if err != nil {
fmt.Printf("error: %v\n", err)
return
}
fmt.Printf("%#v\n", obj)
Output: map[string]interface {}{"address":map[string]interface {}{"city":"New York", "zip":"10001"}, "age":30, "hobbies":[]interface {}{"reading", "music"}, "name":"John"}
func ReadObjectCallback ¶
ReadObjectCallback reads a JSON object and invokes the callback function for each key-value pair. The callback receives the key as a string and the value as an interface{}. This allows for memory-efficient processing of JSON objects without storing the entire structure.
Example:
err := ReadObjectCallback(scanner, func(key string, value any) error {
if key == "name" {
fmt.Printf("name: %v\n", value)
}
return nil
})
Example ¶
input := `{
"name": "John",
"age": 30,
"address": {
"city": "New York",
"zip": "10001",
"location": {
"lat": 40.7128,
"lon": -74.0060
}
},
"orders": [
{"id": "A123", "total": 50.00},
{"id": "B456", "total": 30.00}
]
}`
scanner := NewScanner([]byte(input))
err := ReadObjectCallback(scanner, func(key string, value any) error {
switch key {
case "name", "age":
fmt.Printf("%s: %v\n", key, value)
case "address":
// Handle nested object
if addr, ok := value.(map[string]any); ok {
fmt.Printf("city: %v\n", addr["city"])
// Handle deeply nested object
if loc, ok := addr["location"].(map[string]any); ok {
fmt.Printf("coordinates: %v,%v\n", loc["lat"], loc["lon"])
}
}
case "orders":
// Handle array of objects
if orders, ok := value.([]any); ok {
for _, order := range orders {
if o, ok := order.(map[string]any); ok {
fmt.Printf("order: %v = $%v\n", o["id"], o["total"])
}
}
}
}
return nil
})
if err != nil {
fmt.Printf("error: %v\n", err)
}
Output: name: John age: 30 city: New York coordinates: 40.7128,-74.006 order: A123 = $50 order: B456 = $30
func ReadValue ¶
ReadValue reads any JSON value and returns it as a Go value. The mapping of JSON types to Go types is as follows:
- JSON null -> nil
- JSON boolean -> bool
- JSON number -> float64
- JSON string -> string
- JSON array -> []any
- JSON object -> map[string]any
This function is recursive and will handle nested structures of any depth, limited only by available stack space.
Example ¶
// ReadValue can parse any JSON value directly
inputs := []string{
`42`,
`3.14159`,
`"hello"`,
`true`,
`[1,2,3]`,
`{"name":"John"}`,
}
for _, input := range inputs {
scanner := NewScanner([]byte(input))
value, err := ReadValue(scanner)
if err != nil {
fmt.Printf("error: %v\n", err)
continue
}
fmt.Printf("%T: %v\n", value, value)
}
Output: float64: 42 float64: 3.14159 string: hello bool: true []interface {}: [1 2 3] map[string]interface {}: map[name:John]
Types ¶
type ArrMarshaler ¶
type ArrMarshaler interface {
MarshalJSN(w ArrayWriter) error
}
ArrMarshaler is implemented by types that can marshal themselves into a JSON array. This interface provides full control over the array's JSON representation.
type ArrayWriter ¶
type ArrayWriter interface {
// Element writes supported value as an array element.
Element(v any)
}
ArrayWriter defines the interface for writing JSON arrays
type FloatPrecision ¶
type FloatPrecision struct {
Precision int
}
FloatPrecision specifies the number of decimal places to use when formatting floating-point numbers
type ObjMarshaler ¶
type ObjMarshaler interface {
MarshalJSN(w ObjectWriter) error
}
ObjMarshaler is implemented by types that can marshal themselves into a JSON object. This interface provides full control over the object's JSON representation.
type ObjectWriter ¶
type ObjectWriter interface {
// Member writes a key-value pair as an object member.
Member(key string, v any)
}
ObjectWriter defines the interface for writing JSON objects
type Scanner ¶
type Scanner struct {
// contains filtered or unexported fields
}
Scanner is a simple parser for JSON data
func NewScanner ¶
NewScanner creates a new scanner and skips the BOM and optional whitespace at the start of the data
type ScannerFlag ¶
type ScannerFlag int
const ( ScannerFlagDoNotSkipBOM ScannerFlag = 1 << iota ScannerFlagDoNotSkipInitialWhitespace )
type StrMarshaler ¶
StrMarshaler is implemented by types that can marshal themselves into a JSON string value. This is useful for types that need custom string representation in JSON.
type UnsupportedTypeError ¶
UnsupportedTypeError is returned when marshaling encounters a type that cannot be converted into JSON.
func (*UnsupportedTypeError) Error ¶
func (e *UnsupportedTypeError) Error() string