Skip to content

File Operation Methods ​

The Processor provides JSON file read/write and streaming-load methods covering three data sources: files, io.Reader, and io.Writer. File methods all run secure path validation before operating (see the Function Reference).

File Loading ​

LoadFromFile ​

Signature: func (p *Processor) LoadFromFile(filePath string, cfg ...Config) (string, error)

Loads JSON data from a file and returns the raw string (byte order and whitespace preserved, no re-encoding). Bytes read are bounded by MaxJSONSize.

go
data, err := p.LoadFromFile("config.json")
if err != nil {
    panic(err)
}
fmt.Println(data) // Raw JSON string

LoadFromFileAsData (now private) ​

API change notice

LoadFromFileAsData has become an internal method (loadFromFileAsData) and is no longer exported as public API. Use the LoadFromFile + Parse combination instead:

go
jsonStr, err := p.LoadFromFile("data.json")
if err != nil {
    panic(err)
}
var data any
err = p.Parse(jsonStr, &data)
// data is a map[string]any or []any
if obj, ok := data.(map[string]any); ok {
    fmt.Println(obj["name"])
}

Reader Loading ​

LoadFromReader ​

Signature: func (p *Processor) LoadFromReader(reader io.Reader, cfg ...Config) (string, error)

Loads JSON data from an io.Reader and returns the raw string. Reads are bounded by MaxJSONSize — a good fit for streaming sources such as os.File, HTTP bodies, and pipes.

go
file, _ := os.Open("data.json")
defer file.Close()

data, err := p.LoadFromReader(file)
if err != nil {
    panic(err)
}

LoadFromReaderAsData (now private) ​

API change notice

LoadFromReaderAsData has become an internal method (loadFromReaderAsData) and is no longer exported as public API. Use the LoadFromReader + Parse combination instead:

go
file, _ := os.Open("data.json")
defer file.Close()

jsonStr, err := p.LoadFromReader(file)
if err != nil {
    panic(err)
}
var data any
err = p.Parse(jsonStr, &data)

File Writing ​

SaveToFile ​

Signature: func (p *Processor) SaveToFile(filePath string, data any, cfg ...Config) error

Saves data as a JSON file. Creates parent directories automatically and uses atomic writes (temp file + rename). String / []byte inputs are pre-parsed to avoid double escaping.

go
err := p.SaveToFile("data.json", map[string]any{"name": "CyberGo"})

// Save pretty output with PrettyConfig
err = p.SaveToFile("data.json", data, json.PrettyConfig())

Full Example: SaveToFile + LoadFromFile Round Trip

go
package main

import (
	"fmt"
	"os"

	"github.com/cybergodev/json"
)

func main() {
	p, err := json.New()
	if err != nil {
		panic(err)
	}
	defer p.Close()

	tmp, err := os.CreateTemp("", "cybergo-*.json")
	if err != nil {
		panic(err)
	}
	path := tmp.Name()
	tmp.Close()
	defer os.Remove(path)

	err = p.SaveToFile(path, map[string]any{"name": "Alice", "age": 30})
	if err != nil {
		panic(err)
	}

	data, err := p.LoadFromFile(path)
	if err != nil {
		panic(err)
	}
	fmt.Println(data)
	// Output: {"age":30,"name":"Alice"}
}

MarshalToFile ​

Signature: func (p *Processor) MarshalToFile(path string, data any, cfg ...Config) error

Encodes data as JSON and writes it to a file. Creates parent directories automatically; atomic writes. It shares the same "encode + atomic write" pipeline as SaveToFile: likewise pre-parses string / []byte inputs to avoid double escaping, and likewise honors the passed cfg in full (Pretty / Indent / EscapeHTML etc. all take effect) — the two now differ only in the operation name inside error messages; the historical behavioral difference is gone.

go
err := p.MarshalToFile("output.json", data)

// Pretty save
err = p.MarshalToFile("output.json", data, json.PrettyConfig())

Full Example: MarshalToFile + UnmarshalFromFile Struct Round Trip

go
package main

import (
	"fmt"
	"os"

	"github.com/cybergodev/json"
)

type User struct {
	Name string `json:"name"`
	Age  int    `json:"age"`
}

func main() {
	p, err := json.New()
	if err != nil {
		panic(err)
	}
	defer p.Close()

	tmp, err := os.CreateTemp("", "cybergo-*.json")
	if err != nil {
		panic(err)
	}
	path := tmp.Name()
	tmp.Close()
	defer os.Remove(path)

	err = p.MarshalToFile(path, User{Name: "Alice", Age: 30})
	if err != nil {
		panic(err)
	}

	var user User
	err = p.UnmarshalFromFile(path, &user)
	if err != nil {
		panic(err)
	}
	fmt.Printf("%s, %d\n", user.Name, user.Age)
	// Output: Alice, 30
}

UnmarshalFromFile ​

Signature: func (p *Processor) UnmarshalFromFile(path string, v any, cfg ...Config) error

Reads JSON from a file and decodes it into a target variable. Reads are bounded by MaxJSONSize.

go
type AppConfig struct {
    Host string `json:"host"`
    Port int    `json:"port"`
}

var config AppConfig
err := p.UnmarshalFromFile("config.json", &config)
if err != nil {
    panic(err)
}

SaveToWriter ​

Signature: func (p *Processor) SaveToWriter(writer io.Writer, data any, cfg ...Config) error

Encodes data as JSON and writes it to an io.Writer. String / []byte inputs are likewise pre-parsed to avoid double escaping; no file path is involved, so no path validation runs.

go
var buf bytes.Buffer
err := p.SaveToWriter(&buf, data, json.PrettyConfig())

Full Example: Writing to bytes.Buffer

go
package main

import (
	"bytes"
	"fmt"

	"github.com/cybergodev/json"
)

func main() {
	p, err := json.New()
	if err != nil {
		panic(err)
	}
	defer p.Close()

	var buf bytes.Buffer
	err = p.SaveToWriter(&buf, map[string]any{"name": "Alice", "age": 30}, json.PrettyConfig())
	if err != nil {
		panic(err)
	}
	fmt.Print(buf.String())
	// Output:
	// {
	//   "age": 30,
	//   "name": "Alice"
	// }
}

File Iteration ​

The Processor provides the ForeachFile family, which iterates a JSON collection directly from a file — a convenience combo of LoadFromFile + Foreach:

MethodPurpose
ForeachFile(path, fn, cfg...)Iterate the file's top-level array / object
ForeachFileWithPath(path, pathExpr, fn, cfg...)Iterate the collection at a given path inside the file
ForeachFileChunked(path, chunkSize, fn, cfg...)Iterate large arrays chunk by chunk
ForeachFileNested(path, fn, cfg...)Recursively iterate all nested structures
go
err := p.ForeachFile("users.json", func(key any, item *json.IterableValue) error {
    fmt.Println(item.GetString("name"))
    return nil
})

Callbacks support item.Break() for early termination. For streaming and large-file optimization details see Streaming.

Choosing a Method ​

ScenarioRecommended method
Need the raw stringLoadFromFile / LoadFromReader
Need parsed dataLoadFromFile + Parse / LoadFromReader + Parse
Save a Go value to a fileSaveToFile / MarshalToFile
Read a file and decode into a structUnmarshalFromFile
Write to a WriterSaveToWriter
Iterate a collection in a fileForeachFile family

See Also ​

  • Parse & Validate - Parse/Valid parsing methods
  • File Functions - Package-level file read/write functions (incl. path security validation in detail)
  • Streaming - Streaming processors and large-file iteration in detail