2023-02-28 14:51:54 -05:00
|
|
|
|
module Tests.Lexer
|
|
|
|
|
|
|
|
|
|
import Quox.Name
|
2023-03-17 16:51:28 -04:00
|
|
|
|
import Quox.Parser.Lexer
|
2023-02-28 14:51:54 -05:00
|
|
|
|
import TAP
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
private
|
|
|
|
|
data Failure = LexError Lexer.Error
|
|
|
|
|
| WrongLex (List Token) (List Token)
|
|
|
|
|
| ExpectedFail (List Token)
|
|
|
|
|
|
|
|
|
|
private
|
|
|
|
|
ToInfo Failure where
|
|
|
|
|
toInfo (LexError err) =
|
|
|
|
|
[("type", "LexError"),
|
|
|
|
|
("info", show err)]
|
|
|
|
|
toInfo (WrongLex want got) =
|
|
|
|
|
[("type", "WrongLex"),
|
|
|
|
|
("want", show want),
|
|
|
|
|
("got", show got)]
|
|
|
|
|
toInfo (ExpectedFail got) =
|
|
|
|
|
[("type", "ExpectedFail"),
|
|
|
|
|
("got", show got)]
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
private
|
|
|
|
|
denewline : String -> String
|
|
|
|
|
denewline = pack . map (\case '\n' => ''; c => c) . unpack
|
|
|
|
|
|
|
|
|
|
private
|
|
|
|
|
lexes : String -> List Token -> Test
|
2023-03-04 15:02:51 -05:00
|
|
|
|
lexes str toks = test "「\{denewline str}」" $ do
|
|
|
|
|
res <- bimap LexError (map val) $ lex str
|
|
|
|
|
unless (toks == res) $ throwError $ WrongLex toks res
|
2023-02-28 14:51:54 -05:00
|
|
|
|
|
|
|
|
|
private
|
|
|
|
|
lexFail : String -> Test
|
2023-03-04 15:02:51 -05:00
|
|
|
|
lexFail str = test "「\{denewline str}」 # fails" $
|
|
|
|
|
either (const $ Right ()) (Left . ExpectedFail . map val) $ lex str
|
2023-02-28 14:51:54 -05:00
|
|
|
|
|
|
|
|
|
export
|
|
|
|
|
tests : Test
|
|
|
|
|
tests = "lexer" :- [
|
|
|
|
|
"comments" :- [
|
|
|
|
|
lexes "" [],
|
|
|
|
|
lexes " " [],
|
|
|
|
|
lexes "-- line comment" [],
|
2023-03-08 10:46:29 -05:00
|
|
|
|
lexes "name -- line comment" [Name "name"],
|
2023-09-24 11:36:20 -04:00
|
|
|
|
lexes
|
|
|
|
|
"""
|
|
|
|
|
-- line comment
|
|
|
|
|
nameBetween -- and another
|
|
|
|
|
"""
|
|
|
|
|
[Name "nameBetween"],
|
2023-02-28 14:51:54 -05:00
|
|
|
|
lexes "{- block comment -}" [],
|
|
|
|
|
lexes "{- {- nested -} block comment -}" []
|
|
|
|
|
],
|
|
|
|
|
|
|
|
|
|
"identifiers & keywords" :- [
|
2023-03-08 10:46:29 -05:00
|
|
|
|
lexes "abc" [Name "abc"],
|
|
|
|
|
lexes "abc def" [Name "abc", Reserved "def"],
|
|
|
|
|
lexes "abc_def" [Name "abc_def"],
|
|
|
|
|
lexes "abc-def" [Name "abc-def"],
|
|
|
|
|
lexes "abc{-comment-}def" [Name "abc", Reserved "def"],
|
|
|
|
|
lexes "λ" [Reserved "λ"],
|
|
|
|
|
lexes "fun" [Reserved "λ"],
|
|
|
|
|
lexes "δ" [Reserved "δ"],
|
|
|
|
|
lexes "dfun" [Reserved "δ"],
|
|
|
|
|
lexes "funky" [Name "funky"],
|
|
|
|
|
lexes "δελτα" [Name "δελτα"],
|
|
|
|
|
lexes "★★" [Name "★★"],
|
|
|
|
|
lexes "Types" [Name "Types"],
|
2023-03-17 16:51:28 -04:00
|
|
|
|
lexes "a.b.c.d.e" [Name $ MakePName [< "a","b","c","d"] "e"],
|
2023-03-08 10:46:29 -05:00
|
|
|
|
lexes "normalïse" [Name "normalïse"],
|
2023-02-28 14:51:54 -05:00
|
|
|
|
-- ↑ replace i + combining ¨ with precomposed ï
|
2023-03-08 10:46:29 -05:00
|
|
|
|
lexes "map#" [Name "map#"],
|
2023-09-24 11:36:20 -04:00
|
|
|
|
lexes "map#[" [Name "map#", Reserved "["], -- don't actually do this
|
|
|
|
|
lexes "map #[" [Name "map", Reserved "#["],
|
2023-03-08 10:46:29 -05:00
|
|
|
|
lexes "write!" [Name "write!"],
|
|
|
|
|
lexes "uhh??!?!?!?" [Name "uhh??!?!?!?"],
|
2023-02-28 14:51:54 -05:00
|
|
|
|
|
2023-09-24 11:36:20 -04:00
|
|
|
|
lexFail "abc.fun.ghi",
|
|
|
|
|
lexFail "abc.λ.ghi",
|
|
|
|
|
lexFail "abc.ω.ghi",
|
2023-03-08 10:46:29 -05:00
|
|
|
|
|
|
|
|
|
lexes "+" [Name "+"],
|
|
|
|
|
lexes "*" [Name "*"],
|
|
|
|
|
lexes "**" [Reserved "×"],
|
|
|
|
|
lexes "***" [Name "***"],
|
|
|
|
|
lexes "+**" [Name "+**"],
|
|
|
|
|
lexes "+#" [Name "+#"],
|
2023-03-17 16:51:28 -04:00
|
|
|
|
lexes "+.+.+" [Name $ MakePName [< "+", "+"] "+"],
|
|
|
|
|
lexes "a.+" [Name $ MakePName [< "a"] "+"],
|
|
|
|
|
lexes "+.a" [Name $ MakePName [< "+"] "a"],
|
2023-03-08 10:46:29 -05:00
|
|
|
|
|
|
|
|
|
lexes "+a" [Name "+", Name "a"],
|
|
|
|
|
|
2023-03-17 16:54:09 -04:00
|
|
|
|
lexes "x." [Name "x", Reserved "."],
|
|
|
|
|
lexes "&." [Name "&", Reserved "."],
|
|
|
|
|
lexes ".x" [Reserved ".", Name "x"],
|
|
|
|
|
lexes "a.b.c." [Name $ MakePName [< "a", "b"] "c", Reserved "."],
|
2023-03-08 10:46:29 -05:00
|
|
|
|
|
|
|
|
|
lexes "case" [Reserved "case"],
|
|
|
|
|
lexes "caseω" [Reserved "caseω"],
|
|
|
|
|
lexes "case#" [Reserved "caseω"],
|
|
|
|
|
lexes "case1" [Reserved "case1"],
|
2023-04-02 09:22:39 -04:00
|
|
|
|
lexes "case0" [Reserved "case0"],
|
2023-03-08 10:46:29 -05:00
|
|
|
|
lexes "case##" [Name "case##"],
|
|
|
|
|
|
2023-12-04 12:48:25 -05:00
|
|
|
|
lexes "let" [Reserved "let"],
|
|
|
|
|
lexes "letω" [Reserved "letω"],
|
|
|
|
|
lexes "let#" [Reserved "letω"],
|
|
|
|
|
lexes "let1" [Reserved "let1"],
|
|
|
|
|
lexes "let0" [Reserved "let0"],
|
|
|
|
|
lexes "let##" [Name "let##"],
|
|
|
|
|
|
2023-03-08 10:46:29 -05:00
|
|
|
|
lexes "_" [Reserved "_"],
|
|
|
|
|
lexes "_a" [Name "_a"],
|
|
|
|
|
lexes "a_" [Name "a_"],
|
|
|
|
|
|
|
|
|
|
lexes "a'" [Name "a'"],
|
2023-03-17 16:54:09 -04:00
|
|
|
|
lexes "+'" [Name "+'"],
|
|
|
|
|
|
2023-05-21 14:09:34 -04:00
|
|
|
|
lexes "a₁" [Name "a₁"],
|
|
|
|
|
lexes "a⁰" [Name "a", Sup 0],
|
|
|
|
|
lexes "a^0" [Name "a", Sup 0],
|
|
|
|
|
|
2023-03-17 16:54:09 -04:00
|
|
|
|
lexes "0.x" [Nat 0, Reserved ".", Name "x"],
|
|
|
|
|
lexes "1.x" [Nat 1, Reserved ".", Name "x"],
|
|
|
|
|
lexes "ω.x" [Reserved "ω", Reserved ".", Name "x"],
|
|
|
|
|
lexes "#.x" [Reserved "ω", Reserved ".", Name "x"]
|
2023-02-28 14:51:54 -05:00
|
|
|
|
],
|
|
|
|
|
|
|
|
|
|
"syntax characters" :- [
|
2023-03-08 10:46:29 -05:00
|
|
|
|
lexes "()" [Reserved "(", Reserved ")"],
|
|
|
|
|
lexes "(a)" [Reserved "(", Name "a", Reserved ")"],
|
2023-05-21 14:09:34 -04:00
|
|
|
|
lexFail "(^)",
|
2023-03-08 10:46:29 -05:00
|
|
|
|
lexes "{a,b}"
|
|
|
|
|
[Reserved "{", Name "a", Reserved ",", Name "b", Reserved "}"],
|
|
|
|
|
lexes "{+,-}"
|
|
|
|
|
[Reserved "{", Name "+", Reserved ",", Name "-", Reserved "}"]
|
2023-02-28 14:51:54 -05:00
|
|
|
|
],
|
|
|
|
|
|
|
|
|
|
"tags" :- [
|
2023-03-08 10:46:29 -05:00
|
|
|
|
lexes #" 'a "# [Tag "a"],
|
|
|
|
|
lexes #" 'abc "# [Tag "abc"],
|
|
|
|
|
lexes #" '+ "# [Tag "+"],
|
|
|
|
|
lexes #" '$$$ "# [Tag "$$$"],
|
|
|
|
|
lexes #" 'tag.with.dots "# [Tag "tag.with.dots"],
|
|
|
|
|
lexes #" '"multi word tag" "# [Tag "multi word tag"],
|
|
|
|
|
lexes #" '"" "# [Tag ""],
|
2023-03-04 15:02:51 -05:00
|
|
|
|
lexFail #" ' "#,
|
|
|
|
|
lexFail #" '' "#
|
2023-02-28 14:51:54 -05:00
|
|
|
|
],
|
|
|
|
|
|
|
|
|
|
"strings" :- [
|
2023-11-05 09:38:13 -05:00
|
|
|
|
lexes #" "" "# [Str ""],
|
|
|
|
|
lexes #" "abc" "# [Str "abc"],
|
|
|
|
|
lexes #" "\"" "# [Str "\""],
|
|
|
|
|
lexes #" "\\" "# [Str "\\"],
|
|
|
|
|
lexes #" "\\\"" "# [Str "\\\""],
|
|
|
|
|
lexes #" "\t" "# [Str "\t"],
|
|
|
|
|
lexes #" "\n" "# [Str "\n"],
|
|
|
|
|
lexes #" "🐉" "# [Str "🐉"],
|
|
|
|
|
lexes #" "\x1f409;" "# [Str "🐉"],
|
|
|
|
|
lexFail #" "\q" "#,
|
|
|
|
|
lexFail #" "\" "#
|
2023-02-28 14:51:54 -05:00
|
|
|
|
],
|
|
|
|
|
|
2023-11-05 09:38:13 -05:00
|
|
|
|
"naturals" :- [
|
|
|
|
|
lexes "0" [Nat 0],
|
|
|
|
|
lexes "123" [Nat 123],
|
|
|
|
|
lexes "69_420" [Nat 69420],
|
|
|
|
|
lexes "0x123" [Nat 0x123],
|
|
|
|
|
lexes "0xbeef" [Nat 0xbeef],
|
|
|
|
|
lexes "0xBEEF" [Nat 0xBEEF],
|
|
|
|
|
lexes "0XBEEF" [Nat 0xBEEF],
|
|
|
|
|
lexes "0xbaba_baba" [Nat 0xbabababa],
|
|
|
|
|
lexFail "123abc",
|
|
|
|
|
lexFail "0x123abcghi"
|
|
|
|
|
],
|
2023-03-08 10:46:29 -05:00
|
|
|
|
|
2023-02-28 14:51:54 -05:00
|
|
|
|
"universes" :- [
|
|
|
|
|
lexes "Type0" [TYPE 0],
|
2023-05-21 14:09:34 -04:00
|
|
|
|
lexes "Type⁰" [Reserved "★", Sup 0],
|
2023-02-28 14:51:54 -05:00
|
|
|
|
lexes "Type9999999" [TYPE 9999999],
|
2023-05-21 14:09:34 -04:00
|
|
|
|
lexes "★⁰" [Reserved "★", Sup 0],
|
|
|
|
|
lexes "★⁶⁹" [Reserved "★", Sup 69],
|
2023-02-28 14:51:54 -05:00
|
|
|
|
lexes "★4" [TYPE 4],
|
2023-03-08 10:46:29 -05:00
|
|
|
|
lexes "Type" [Reserved "★"],
|
|
|
|
|
lexes "★" [Reserved "★"]
|
2023-02-28 14:51:54 -05:00
|
|
|
|
]
|
|
|
|
|
]
|