summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorLuke Shumaker <lukeshu@lukeshu.com>2023-02-14 11:44:36 -0700
committerLuke Shumaker <lukeshu@lukeshu.com>2023-02-16 21:19:46 -0700
commit851452243879498117cd7e71ac12856af44657cb (patch)
tree8542d06063bd773031c8550271f945cab624b68d
parenta6cd78ec94f76feba180fa75e942bb5cdeae115f (diff)
reencode: Don't have the ReEncoderConfig member be public
-rw-r--r--ReleaseNotes.md24
-rw-r--r--compat/json/compat.go43
-rw-r--r--encode.go2
-rw-r--r--reencode.go38
4 files changed, 61 insertions, 46 deletions
diff --git a/ReleaseNotes.md b/ReleaseNotes.md
index e00bf10..bee16c4 100644
--- a/ReleaseNotes.md
+++ b/ReleaseNotes.md
@@ -4,16 +4,20 @@
User-facing changes:
- - `Number` and `RawMessage` type aliases are now available, so that
- a user of lowmemjson's native APIs does not need to import
- `encoding/json` or compat/json in order to use them.
-
- - Encoder, ReEncoder: If there was an error writing to the output
- stream, it may have returned a `*ReEncodeSyntaxError` even though
- it's not a syntax issue, or may have returned the underlying
- error without wrapping it. If there is an error writing to the
- output, Encoder and ReEncoder now return `*EncodeWriteError` and
- `*ReEncodeWriteError` respectively.
+ - Change: ReEncoder: The ReEncoderConfig struct member is no longer
+ public.
+
+ - Feature: `Number` and `RawMessage` type aliases are now
+ available, so that a user of lowmemjson's native APIs does not
+ need to import `encoding/json` or compat/json in order to use
+ them.
+
+ - Bigfix: Encoder, ReEncoder: If there was an error writing to the
+ output stream, it may have returned a `*ReEncodeSyntaxError` even
+ though it's not a syntax issue, or may have returned the
+ underlying error without wrapping it. If there is an error
+ writing to the output, Encoder and ReEncoder now return
+ `*EncodeWriteError` and `*ReEncodeWriteError` respectively.
# v0.3.5 (2023-02-10)
diff --git a/compat/json/compat.go b/compat/json/compat.go
index 3678135..c96470d 100644
--- a/compat/json/compat.go
+++ b/compat/json/compat.go
@@ -72,8 +72,11 @@ func Marshal(v any) ([]byte, error) {
}
type Encoder struct {
- out io.Writer
- buf bytes.Buffer
+ out io.Writer
+ buf bytes.Buffer
+
+ cfg lowmemjson.ReEncoderConfig
+
encoder *lowmemjson.Encoder
formatter *lowmemjson.ReEncoder
}
@@ -81,17 +84,23 @@ type Encoder struct {
func NewEncoder(w io.Writer) *Encoder {
ret := &Encoder{
out: w,
- }
- ret.formatter = lowmemjson.NewReEncoder(&ret.buf, lowmemjson.ReEncoderConfig{
- AllowMultipleValues: true,
- Compact: true,
- ForceTrailingNewlines: true,
- })
- ret.encoder = lowmemjson.NewEncoder(ret.formatter)
+ cfg: lowmemjson.ReEncoderConfig{
+ AllowMultipleValues: true,
+
+ Compact: true,
+ ForceTrailingNewlines: true,
+ },
+ }
+ ret.refreshConfig()
return ret
}
+func (enc *Encoder) refreshConfig() {
+ enc.formatter = lowmemjson.NewReEncoder(&enc.buf, enc.cfg)
+ enc.encoder = lowmemjson.NewEncoder(enc.formatter)
+}
+
func (enc *Encoder) Encode(v any) error {
if err := convertEncodeError(enc.encoder.Encode(v)); err != nil {
enc.buf.Reset()
@@ -104,17 +113,19 @@ func (enc *Encoder) Encode(v any) error {
}
func (enc *Encoder) SetEscapeHTML(on bool) {
- var escaper lowmemjson.BackslashEscaper
- if !on {
- escaper = lowmemjson.EscapeDefaultNonHTMLSafe
+ if on {
+ enc.cfg.BackslashEscape = lowmemjson.EscapeDefault
+ } else {
+ enc.cfg.BackslashEscape = lowmemjson.EscapeDefaultNonHTMLSafe
}
- enc.formatter.BackslashEscape = escaper
+ enc.refreshConfig()
}
func (enc *Encoder) SetIndent(prefix, indent string) {
- enc.formatter.Compact = prefix == "" && indent == ""
- enc.formatter.Prefix = prefix
- enc.formatter.Indent = indent
+ enc.cfg.Compact = prefix == "" && indent == ""
+ enc.cfg.Prefix = prefix
+ enc.cfg.Indent = indent
+ enc.refreshConfig()
}
// ReEncode wrappers /////////////////////////////////////////////////
diff --git a/encode.go b/encode.go
index ebb4568..2e10134 100644
--- a/encode.go
+++ b/encode.go
@@ -83,7 +83,7 @@ func (enc *Encoder) Encode(obj any) (err error) {
if enc.isRoot {
enc.w.par.Reset()
}
- escaper := enc.w.BackslashEscape
+ escaper := enc.w.cfg.BackslashEscape
if escaper == nil {
escaper = EscapeDefault
}
diff --git a/reencode.go b/reencode.go
index f100275..32796f6 100644
--- a/reencode.go
+++ b/reencode.go
@@ -72,9 +72,9 @@ type ReEncoderConfig struct {
// bufio.Writer.
func NewReEncoder(out io.Writer, cfg ReEncoderConfig) *ReEncoder {
return &ReEncoder{
- ReEncoderConfig: cfg,
- out: fastio.NewAllWriter(out),
- specu: new(speculation),
+ cfg: cfg,
+ out: fastio.NewAllWriter(out),
+ specu: new(speculation),
}
}
@@ -87,7 +87,7 @@ func NewReEncoder(out io.Writer, cfg ReEncoderConfig) *ReEncoder {
//
// The memory use of a ReEncoder is O(CompactIfUnder+depth).
type ReEncoder struct {
- ReEncoderConfig
+ cfg ReEncoderConfig
out fastio.AllWriter
// state: .Write's and .WriteString's utf8-decoding buffer
@@ -239,7 +239,7 @@ func (enc *ReEncoder) Close() error {
}
return enc.err
}
- if enc.AllowMultipleValues {
+ if enc.cfg.AllowMultipleValues {
enc.par.Reset()
}
}
@@ -283,7 +283,7 @@ rehandle:
return enc.written, enc.err
}
if t == jsonparse.RuneTypeEOF {
- if enc.AllowMultipleValues && len(enc.barriers) == 0 {
+ if enc.cfg.AllowMultipleValues && len(enc.barriers) == 0 {
enc.par.Reset()
goto rehandle
} else {
@@ -328,7 +328,7 @@ func (enc *ReEncoder) stackSize() int {
}
func (enc *ReEncoder) handleRune(c rune, t jsonparse.RuneType, stackSize int) error {
- if enc.CompactIfUnder == 0 || enc.Compact || enc.Indent == "" {
+ if enc.cfg.CompactIfUnder == 0 || enc.cfg.Compact || enc.cfg.Indent == "" {
return enc.handleRuneNoSpeculation(c, t)
}
@@ -342,10 +342,10 @@ func (enc *ReEncoder) handleRune(c rune, t jsonparse.RuneType, stackSize int) er
enc.specu.speculating = true
enc.specu.endWhenStackSize = stackSize - 1
enc.specu.fmt = ReEncoder{
- ReEncoderConfig: enc.ReEncoderConfig,
- out: &enc.specu.compact,
+ cfg: enc.cfg,
+ out: &enc.specu.compact,
}
- enc.specu.fmt.Compact = true
+ enc.specu.fmt.cfg.Compact = true
enc.specu.buf = append(enc.specu.buf, inputTuple{
c: c,
t: t,
@@ -369,7 +369,7 @@ func (enc *ReEncoder) handleRune(c rune, t jsonparse.RuneType, stackSize int) er
return err
}
switch {
- case enc.specu.compact.Len() >= enc.CompactIfUnder: // stop speculating; use indent
+ case enc.specu.compact.Len() >= enc.cfg.CompactIfUnder: // stop speculating; use indent
buf := append([]inputTuple(nil), enc.specu.buf...)
enc.specu.Reset()
if err := enc.handleRuneMain(buf[0].c, buf[0].t); err != nil {
@@ -414,7 +414,7 @@ func (enc *ReEncoder) handleRunePre(c rune, t jsonparse.RuneType) (error, bool)
if err := enc.emitByte('\n'); err != nil {
return err, false
}
- case enc.Indent != "" && !enc.Compact:
+ case enc.cfg.Indent != "" && !enc.cfg.Compact:
if err := enc.emitByte('\n'); err != nil {
return err, false
}
@@ -458,11 +458,11 @@ func (enc *ReEncoder) handleRunePre(c rune, t jsonparse.RuneType) (error, bool)
// whitespace
switch {
- case enc.Compact:
+ case enc.cfg.Compact:
if t == jsonparse.RuneTypeSpace {
return nil, false
}
- case enc.Indent != "":
+ case enc.cfg.Indent != "":
switch t {
case jsonparse.RuneTypeSpace:
// let us manage whitespace, don't pass it through
@@ -500,7 +500,7 @@ func (enc *ReEncoder) handleRunePre(c rune, t jsonparse.RuneType) (error, bool)
// handleRuneMain handles the new rune itself, not buffered things.
func (enc *ReEncoder) handleRuneMain(c rune, t jsonparse.RuneType) error {
- escaper := enc.BackslashEscape
+ escaper := enc.cfg.BackslashEscape
if escaper == nil {
escaper = EscapeDefault
}
@@ -549,7 +549,7 @@ func (enc *ReEncoder) handleRuneMain(c rune, t jsonparse.RuneType) error {
case jsonparse.RuneTypeEOF: // EOF implied by the start of the next top-level value
enc.wasNumber = enc.lastNonSpace.IsNumber()
switch {
- case enc.ForceTrailingNewlines && len(enc.barriers) == 0:
+ case enc.cfg.ForceTrailingNewlines && len(enc.barriers) == 0:
t = jsonparse.RuneTypeError // enc.lastNonSpace : an NL isn't needed (we already printed one)
err = enc.emitByte('\n')
default:
@@ -585,13 +585,13 @@ func (enc *ReEncoder) emitNlIndent() error {
if err := enc.emitByte('\n'); err != nil {
return err
}
- if enc.Prefix != "" {
- if err := enc.emit(enc.out.WriteString(enc.Prefix)); err != nil {
+ if enc.cfg.Prefix != "" {
+ if err := enc.emit(enc.out.WriteString(enc.cfg.Prefix)); err != nil {
return err
}
}
for i := 0; i < enc.curIndent; i++ {
- if err := enc.emit(enc.out.WriteString(enc.Indent)); err != nil {
+ if err := enc.emit(enc.out.WriteString(enc.cfg.Indent)); err != nil {
return err
}
}