1package jmespath
2
3import (
4	"fmt"
5	"testing"
6
7	"github.com/jmespath/go-jmespath/internal/testify/assert"
8)
9
10var parsingErrorTests = []struct {
11	expression string
12	msg        string
13}{
14	{"foo.", "Incopmlete expression"},
15	{"[foo", "Incopmlete expression"},
16	{"]", "Invalid"},
17	{")", "Invalid"},
18	{"}", "Invalid"},
19	{"foo..bar", "Invalid"},
20	{`foo."bar`, "Forwards lexer errors"},
21	{`{foo: bar`, "Incomplete expression"},
22	{`{foo bar}`, "Invalid"},
23	{`[foo bar]`, "Invalid"},
24	{`foo@`, "Invalid"},
25	{`&&&&&&&&&&&&t(`, "Invalid"},
26	{`[*][`, "Invalid"},
27}
28
29func TestParsingErrors(t *testing.T) {
30	assert := assert.New(t)
31	parser := NewParser()
32	for _, tt := range parsingErrorTests {
33		_, err := parser.Parse(tt.expression)
34		assert.NotNil(err, fmt.Sprintf("Expected parsing error: %s, for expression: %s", tt.msg, tt.expression))
35	}
36}
37
38var prettyPrinted = `ASTProjection {
39  children: {
40    ASTField {
41      value: "foo"
42    }
43    ASTSubexpression {
44      children: {
45        ASTSubexpression {
46          children: {
47            ASTField {
48              value: "bar"
49            }
50            ASTField {
51              value: "baz"
52            }
53        }
54        ASTField {
55          value: "qux"
56        }
57    }
58}
59`
60
61var prettyPrintedCompNode = `ASTFilterProjection {
62  children: {
63    ASTField {
64      value: "a"
65    }
66    ASTIdentity {
67    }
68    ASTComparator {
69      value: tLTE
70      children: {
71        ASTField {
72          value: "b"
73        }
74        ASTField {
75          value: "c"
76        }
77    }
78}
79`
80
81func TestPrettyPrintedAST(t *testing.T) {
82	assert := assert.New(t)
83	parser := NewParser()
84	parsed, _ := parser.Parse("foo[*].bar.baz.qux")
85	assert.Equal(parsed.PrettyPrint(0), prettyPrinted)
86}
87
88func TestPrettyPrintedCompNode(t *testing.T) {
89	assert := assert.New(t)
90	parser := NewParser()
91	parsed, _ := parser.Parse("a[?b<=c]")
92	assert.Equal(parsed.PrettyPrint(0), prettyPrintedCompNode)
93}
94
95func BenchmarkParseIdentifier(b *testing.B) {
96	runParseBenchmark(b, exprIdentifier)
97}
98
99func BenchmarkParseSubexpression(b *testing.B) {
100	runParseBenchmark(b, exprSubexpr)
101}
102
103func BenchmarkParseDeeplyNested50(b *testing.B) {
104	runParseBenchmark(b, deeplyNested50)
105}
106
107func BenchmarkParseDeepNested50Pipe(b *testing.B) {
108	runParseBenchmark(b, deeplyNested50Pipe)
109}
110
111func BenchmarkParseDeepNested50Index(b *testing.B) {
112	runParseBenchmark(b, deeplyNested50Index)
113}
114
115func BenchmarkParseQuotedIdentifier(b *testing.B) {
116	runParseBenchmark(b, exprQuotedIdentifier)
117}
118
119func BenchmarkParseQuotedIdentifierEscapes(b *testing.B) {
120	runParseBenchmark(b, quotedIdentifierEscapes)
121}
122
123func BenchmarkParseRawStringLiteral(b *testing.B) {
124	runParseBenchmark(b, rawStringLiteral)
125}
126
127func BenchmarkParseDeepProjection104(b *testing.B) {
128	runParseBenchmark(b, deepProjection104)
129}
130
131func runParseBenchmark(b *testing.B, expression string) {
132	parser := NewParser()
133	for i := 0; i < b.N; i++ {
134		parser.Parse(expression)
135	}
136}
137