diff options
Diffstat (limited to 'json.go')
-rw-r--r-- | json.go | 102 |
1 files changed, 83 insertions, 19 deletions
@@ -1,36 +1,100 @@ package json import ( - "strings" + "fmt" - "go.neonxp.dev/json/model" - "go.neonxp.dev/json/parser" + "go.neonxp.dev/json/internal/lexer" ) -// Marshal Node tree to []byte -func Marshal(node model.Node) ([]byte, error) { - return node.MarshalJSON() +type JSON struct { + Factory NodeFactory } -// Unmarshal data to Node tree -func Unmarshal(data []byte) (model.Node, error) { - return parser.Parse(string(data)) +func (j *JSON) Unmarshal(input string) (Node, error) { + lex := lexer.NewLexer(input) + go lex.Run(lexer.InitJson) + return j.parse(lex.Output) } -// Query returns node by query string (dot notation) -func Query(json string, query string) (model.Node, error) { - n, err := parser.Parse(json) +func (j *JSON) MustUnmarshal(input string) Node { + n, err := j.Unmarshal(input) if err != nil { - return nil, err + panic(err) } - return model.Query(n, strings.Split(query, ".")) + return n } -// QueryArray returns node by array query -func QueryArray(json string, query []string) (model.Node, error) { - n, err := parser.Parse(json) +func (j *JSON) Marshal(n Node) string { + return n.String() +} + +func (j *JSON) Node(value any) (Node, error) { + switch value := value.(type) { + case string: + n, err := j.Factory(StringType) + if err != nil { + return nil, err + } + n.(StringNode).SetString(value) + return n, nil + case float64: + n, err := j.Factory(NumberType) + if err != nil { + return nil, err + } + n.(NumberNode).SetNumber(value) + return n, nil + case int: + n, err := j.Factory(NumberType) + if err != nil { + return nil, err + } + n.(NumberNode).SetNumber(float64(value)) + return n, nil + case bool: + n, err := j.Factory(BooleanType) + if err != nil { + return nil, err + } + n.(BooleanNode).SetBool(value) + return n, nil + case nil: + return j.Factory(NullType) + case map[string]Node: + n, err := j.Factory(ObjectType) + if err != nil { + return nil, err + } + on := n.(ObjectNode) + for k, v := range value { + on.SetKeyValue(k, v) + } + return on, nil + case []Node: + n, err := j.Factory(ArrayType) + if err != nil { + return nil, err + } + an := n.(ArrayNode) + for _, v := range value { + an.Append(v) + } + return an, nil + default: + return nil, fmt.Errorf("invalid type %t", value) + } +} + +func (j *JSON) MustNode(value any) Node { + n, err := j.Node(value) if err != nil { - return nil, err + panic(err) + } + return n +} + +func New(factory NodeFactory) *JSON { + return &JSON{ + Factory: factory, } - return model.Query(n, query) } |