1use pest_derive::Parser;
2
3#[derive(Parser)]
4#[grammar = "grammar.pest"]
5struct JavaScriptParser;
6
7#[cfg(test)]
8mod tests {
9 use crate::*;
10 use pest::Parser;
11
12 fn parse(input: &str) {
13 JavaScriptParser::parse(Rule::program, input).unwrap();
14 }
15
16 fn parse_rule(input: &str, rule: Rule) {
17 JavaScriptParser::parse(rule, input).unwrap();
18 }
19
20 #[test]
21 fn it_works() {
22 parse("1 + 1;")
23 }
24
25 #[test]
26 fn booleans() {
27 parse("true;");
28 parse("false;");
29 }
30
31 #[test]
32 fn boolean_checking() {
33 parse("true == true;");
34 parse("true == false;");
35 parse("false == true;");
36 parse("false == false;");
37 }
38
39 #[test]
40 fn scientific_notation() {
41 parse("1e1;");
42 parse("1e-1;");
43 parse("1e+1;");
44 parse("1e0;");
45 parse("1e-0;");
46 parse("1e+0;");
47 }
48
49 #[test]
50 fn arrays() {
51 parse("[];");
52 parse("[1];");
53 parse("[1, 2];");
54 parse("[1, 2, 3];");
55 }
56
57 #[test]
58 fn objects() {
59 parse("{};");
60 parse("{a: 1};");
61 parse("{a: 1, b: 2};");
62 parse("{a: 1, b: 2, c: 3};");
63 parse("({a: 1, b: 2, c: 3});");
64 }
65
66 #[test]
67 fn functions() {
68 parse("function() {}");
69 parse("function() { return 1; }");
70 parse("function sum(a, b) { return a + b; }");
71 }
72
73 #[test]
74 fn assignments() {
75 parse("const a;");
76 parse("const a = b;");
77 parse("let c = d;");
78 parse("var e = f;");
79 parse("foo = bar");
80 parse("foo += bar");
81 parse("foo -= bar");
82 parse("foo *= bar");
83 parse("foo /= bar");
84 parse("foo %= bar");
85 parse("foo **= bar");
86 parse("foo <<= bar");
87 parse("foo >>= bar");
88 parse("foo >>>= bar");
89 parse("foo &= bar");
90 parse("foo ^= bar");
91 parse("foo |= bar");
92 }
93
94 #[test]
95 fn operators() {
96 parse_rule("1 + 1", Rule::expression);
97 parse_rule("1 - 1", Rule::expression);
98 parse_rule("1 * 1", Rule::expression);
99 parse_rule("1 / 1;", Rule::expression);
100 parse_rule("1 % 1;", Rule::expression);
101 parse_rule("1 ** 1;", Rule::expression);
102 parse_rule("1 << 1;", Rule::expression);
103 parse_rule("1 >> 1;", Rule::expression);
104 parse_rule("1 >>> 1;", Rule::expression);
105 parse_rule("1 & 1;", Rule::expression);
106 parse_rule("1 | 1;", Rule::expression);
107 parse_rule("1 ^ 1;", Rule::expression);
108 parse_rule("1 && 1;", Rule::expression);
109 parse_rule("1 || 1;", Rule::expression);
110 parse_rule("1 ?? 1;", Rule::expression);
111 parse_rule("1 == 1;", Rule::expression);
112 parse_rule("1 === 1;", Rule::expression);
113 parse_rule("1 != 1;", Rule::expression);
114 parse_rule("1 !== 1;", Rule::expression);
115 parse_rule("1 < 1;", Rule::expression);
116 parse_rule("1 <= 1;", Rule::expression);
117 parse_rule("1 > 1;", Rule::expression);
118 parse_rule("1 >= 1;", Rule::expression);
119 }
120
121 #[test]
122 fn new_lines() {
123 parse("function append(a, b) {\nreturn a + b;\n}");
124 }
125
126 #[test]
127 fn arrow_function() {
128 parse("const sum = (a, b) => a + b;");
129 parse("const sum = (a, b) => {\nreturn a + b;\n}");
130 }
131
132 #[test]
133 fn if_statements() {
134 parse("if (true) { return 1; }");
135 parse("if (false) { return 1; }");
136 parse("if (true) { return 1; } else { return 2; }");
137 parse("if (true) { return 1; } else if (true) { return 3; } else { return 2; }");
138 }
139
140 #[test]
141 fn do_statement() {
142 parse("while (true) { return 1; }");
143 }
144}