aboutsummaryrefslogtreecommitdiff
path: root/internal/ast/processor.go
diff options
context:
space:
mode:
author2026-03-09 23:05:42 +0300
committer2026-03-09 23:05:42 +0300
commit00394a80501960ad26787b5c44435ed5ed67ad84 (patch)
tree672eb918c552c858f32e9533dc3799af6b75769f /internal/ast/processor.go
parent'-' sign in words accepted (diff)
downloadconf-0.1.0.tar.gz
conf-0.1.0.tar.bz2
conf-0.1.0.tar.xz
conf-0.1.0.zip
Полностью переписал библиотеку. Перевёл с EBNF на PEG.v0.1.0
Diffstat (limited to '')
-rw-r--r--internal/ast/processor.go119
1 files changed, 0 insertions, 119 deletions
diff --git a/internal/ast/processor.go b/internal/ast/processor.go
deleted file mode 100644
index 55dce59..0000000
--- a/internal/ast/processor.go
+++ /dev/null
@@ -1,119 +0,0 @@
-package ast
-
-import (
- "fmt"
- "strconv"
-
- "go.neonxp.ru/conf/internal/parser"
- "go.neonxp.ru/conf/model"
-)
-
-func ToDoc(config *Node) (model.Body, error) {
- if len(config.Children) < 1 {
- return nil, fmt.Errorf("invalid ast tree")
- }
-
- doc := config.Children[0]
-
- return processDoc(doc), nil
-}
-
-func processDoc(docNode *Node) model.Body {
- doc := make(model.Body, 0, len(docNode.Children))
- for _, stmt := range docNode.Children {
- processStmt(&doc, stmt)
- }
- return doc
-}
-
-func processStmt(doc *model.Body, stmt *Node) {
- ident := extractIdent(stmt.Children[0])
- nodeBody := stmt.Children[1]
- switch nodeBody.Symbol {
- case parser.Command:
- *doc = append(*doc, processDirective(ident, nodeBody))
- case parser.Assignment:
- *doc = append(*doc, processSetting(ident, nodeBody))
- }
-}
-
-func processDirective(ident string, directive *Node) *model.Directive {
- result := &model.Directive{
- Name: ident,
- }
-
- for _, child := range directive.Children {
- // Can be arguments OR body OR both
- switch child.Symbol {
- case parser.Values:
- result.Arguments = extractValues(child)
- case parser.Body:
- // Children[0] = '{', Children[1] = Body, Children[2] = '}'
- result.Body = processDoc(child.Children[1])
- }
- }
-
- return result
-}
-
-func processSetting(ident string, setting *Node) *model.Setting {
- result := &model.Setting{
- Key: ident,
- Value: extractValues(setting.Children[1]), // Children[0] = '=', Children[1] = Values, Children[2] = ';'
- }
-
- return result
-}
-
-func extractIdent(word *Node) string {
- return word.Children[0].Source
-}
-
-func extractValues(args *Node) []model.Value {
- result := make([]model.Value, len(args.Children))
- for i, child := range args.Children {
- v, err := extractValue(child)
- if err != nil {
- result[i] = err
- continue
- }
- result[i] = v
- }
-
- return result
-}
-
-func extractValue(value *Node) (any, error) {
- v := value.Children[0]
- s := v.Children[0].Source
- switch v.Symbol {
- case parser.Word:
- return model.Word(s), nil
- case parser.String:
- return unquote(s), nil
- case parser.Number:
- d, err := strconv.Atoi(s)
- if err == nil {
- return d, nil
- }
- fl, err := strconv.ParseFloat(s, 32)
- if err == nil {
- return fl, nil
- }
- return nil, fmt.Errorf("invalid number: %s (%s)", v.Source, s)
- case parser.Boolean:
- return s == "true", nil
- default:
- return nil, fmt.Errorf("unknown value type: %s (%s)", v.Symbol, s)
- }
-}
-
-func unquote(str string) string {
- if len(str) == 0 {
- return ""
- }
- if str[0:1] == `"` || str[0:1] == "'" || str[0:1] == "`" {
- return str[1 : len(str)-1]
- }
- return str
-}