diff --git a/project.clj b/project.clj index 567d2df..9a0e304 100644 --- a/project.clj +++ b/project.clj @@ -1,4 +1,4 @@ -(defproject carocad/parcera "0.4.2" +(defproject carocad/parcera "0.4.4" :description "Grammar-based Clojure parser" :url "https://github.com/carocad/parcera" :license {:name "LGPLv3" diff --git a/src/clojure/parcera/antlr/java.clj b/src/clojure/parcera/antlr/java.clj index 525038d..85c225a 100644 --- a/src/clojure/parcera/antlr/java.clj +++ b/src/clojure/parcera/antlr/java.clj @@ -52,30 +52,32 @@ stop (.getStop this)] (cond ;; happens when the parser rule is a single lexer rule - (= start stop) - {::start {:row (.getLine start) - :column (.getCharPositionInLine start)} - ::end {:row (.getLine start) - :column (.getStopIndex start)}} + (identical? start stop) + {:parcera.core/start {:row (.getLine start) + :column (.getCharPositionInLine start)} + :parcera.core/end {:row (.getLine start) + :column (Math/addExact (.getCharPositionInLine start) + (.length (.getText start)))}} ;; no end found - happens on errors (nil? stop) - {::start {:row (.getLine start) - :column (.getCharPositionInLine start)}} + {:parcera.core/start {:row (.getLine start) + :column (.getCharPositionInLine start)}} :else - {::start {:row (.getLine start) - :column (.getCharPositionInLine start)} - ::end {:row (.getLine stop) - :column (.getCharPositionInLine stop)}})))) + {:parcera.core/start {:row (.getLine start) + :column (.getCharPositionInLine start)} + :parcera.core/end {:row (.getLine stop) + :column (Math/addExact (.getCharPositionInLine stop) + (.length (.getText stop)))}})))) (extend-type ErrorNodeImpl antlr/LocationInfo (span [^ErrorNodeImpl this] (let [token (.-symbol this)] - {::start {:row (.getLine token) - :column (.getCharPositionInLine token)}}))) + {:parcera.core/start {:row (.getLine token) + :column (.getCharPositionInLine token)}}))) (extend-type ClojureParser diff --git a/test/parcera/test/core.cljc b/test/parcera/test/core.cljc index 079828c..06c025a 100644 --- a/test/parcera/test/core.cljc +++ b/test/parcera/test/core.cljc @@ -72,7 +72,25 @@ ;(is (clear input)))) (as-> "\\ϕ" input (and (is (valid? input)) (is (roundtrip input)))))) -;(is (clear input)))))) + + +(deftest metadata + (testing "simple definitions" + (let [input ":bar" + ast (parcera/ast input) + location (meta (second ast))] + (is (= (:row (::parcera/start location)) 1)) + (is (= (:column (::parcera/start location)) 0)) + (is (= (:row (::parcera/start location)) 1)) + (is (= (:column (::parcera/end location)) + (count input))))) + + (testing "syntax error" + (let [input "hello/world/" + ast (parcera/ast input) + location (meta (second ast))] + (is (parcera/failure? ast)) + (is (some? (:message (::parcera/start location))))))) (deftest data-structures