Parse ns
This commit is contained in:
parent
ac83d3070b
commit
1317e52bbf
|
@ -318,6 +318,49 @@
|
||||||
|
|
||||||
(panic parser "Struct entries must be single words or keyword+expression pairs" #{::token/rbrace})))))
|
(panic parser "Struct entries must be single words or keyword+expression pairs" #{::token/rbrace})))))
|
||||||
|
|
||||||
|
(defn- parse-ns [parser]
|
||||||
|
(let [name (expect* #{::token/word} "Expected ns name" (advance parser))
|
||||||
|
origin (expect* #{::token/lbrace} "Expected { after ns name" (:parser name))]
|
||||||
|
(cond
|
||||||
|
(not (:success name)) (panic parser "Expected ns name" #{::token/newline})
|
||||||
|
|
||||||
|
(not (:success origin)) (panic (:parser name) "Expected { after ns name")
|
||||||
|
|
||||||
|
:else
|
||||||
|
(loop [parser (accept-many #{::token/newline ::token/comma} (advance (:parser name)))
|
||||||
|
members {}
|
||||||
|
current_member nil]
|
||||||
|
(let [curr (current parser)]
|
||||||
|
(case (token-type parser)
|
||||||
|
::token/rbrace (let [ms (add-member members current_member)]
|
||||||
|
(assoc (advance parser) ::ast
|
||||||
|
{::ast/type ::ast/ns
|
||||||
|
:name (::ast name)
|
||||||
|
:members ms}))
|
||||||
|
|
||||||
|
(::token/comma ::token/newline)
|
||||||
|
(recur
|
||||||
|
(accept-many #{::token/comma ::token/newline} parser)
|
||||||
|
(add-member members current_member) nil)
|
||||||
|
|
||||||
|
(::token/rbracket ::token/rparen)
|
||||||
|
(panic parser (str "Mismatched enclosure in ns: " (::token/lexeme curr)))
|
||||||
|
|
||||||
|
::token/eof
|
||||||
|
(panic (assoc origin ::errors (::errors parser)) "Unterminated ns" ::token/eof)
|
||||||
|
|
||||||
|
::token/word
|
||||||
|
(if (not current_member) (let [parsed (parse-word parser) word (get-in parsed [::ast :word])]
|
||||||
|
(recur parsed members {(keyword word) (::ast parsed)}))
|
||||||
|
(panic parser "ns entries must be single words or keyword+expression pairs." #{::token/rbrace}))
|
||||||
|
|
||||||
|
::token/keyword
|
||||||
|
(if (not current_member) (let [kw (parse-atom parser) expr (parse-expr kw #{::token/comma ::token/newline ::token/rbrace})]
|
||||||
|
(recur expr members {(:value (::ast kw)) (::ast expr)}))
|
||||||
|
(panic parser "ns entries must be single words or keyword+expression pairs." #{::token/rbrace}))
|
||||||
|
|
||||||
|
(panic parser "ns entries must be single words or keyword+expression pairs" #{::token/rbrace})))))))
|
||||||
|
|
||||||
(defn- parse-block [origin]
|
(defn- parse-block [origin]
|
||||||
(loop [parser (accept-many #{::token/newline ::token/semicolon} (advance origin))
|
(loop [parser (accept-many #{::token/newline ::token/semicolon} (advance origin))
|
||||||
exprs []
|
exprs []
|
||||||
|
@ -697,6 +740,8 @@
|
||||||
|
|
||||||
::token/cond (parse-cond parser)
|
::token/cond (parse-cond parser)
|
||||||
|
|
||||||
|
::token/ns (parse-ns parser)
|
||||||
|
|
||||||
;; TODO: improve handling of comments?
|
;; TODO: improve handling of comments?
|
||||||
;; Scanner now just skips comments
|
;; Scanner now just skips comments
|
||||||
;; ::token/comment (advance parser)
|
;; ::token/comment (advance parser)
|
||||||
|
@ -717,11 +762,11 @@
|
||||||
(parser)
|
(parser)
|
||||||
(parse-script)))
|
(parse-script)))
|
||||||
|
|
||||||
(comment
|
(do
|
||||||
(def pp pp/pprint)
|
(def pp pp/pprint)
|
||||||
(def source "match foo with {
|
(def source "ns foo {
|
||||||
1 -> :foo
|
:bar 42
|
||||||
else -> bar
|
:baz 23
|
||||||
}
|
}
|
||||||
|
|
||||||
")
|
")
|
||||||
|
@ -772,7 +817,7 @@
|
||||||
* This lets you do one let (with everything building up) and then a cond with bespoke errors/panics
|
* This lets you do one let (with everything building up) and then a cond with bespoke errors/panics
|
||||||
* This also still lets you encapsulate parsererrors with poisoned nodes
|
* This also still lets you encapsulate parsererrors with poisoned nodes
|
||||||
|
|
||||||
")
|
")
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
Loading…
Reference in New Issue
Block a user