travis-conditions 0.0.2 → 1.0.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- checksums.yaml +4 -4
- data/CHANGELOG.md +65 -0
- data/Gemfile.lock +1 -1
- data/NOTES.md +107 -0
- data/README.md +261 -13
- data/bin/travis-conditions +34 -0
- data/lib/travis/conditions.rb +10 -16
- data/lib/travis/conditions/v0.rb +30 -0
- data/lib/travis/conditions/v0/data.rb +57 -0
- data/lib/travis/conditions/v0/eval.rb +70 -0
- data/lib/travis/conditions/v0/parser.rb +204 -0
- data/lib/travis/conditions/v1.rb +19 -0
- data/lib/travis/conditions/v1/boolean.rb +71 -0
- data/lib/travis/conditions/v1/data.rb +75 -0
- data/lib/travis/conditions/v1/eval.rb +114 -0
- data/lib/travis/conditions/v1/helper.rb +30 -0
- data/lib/travis/conditions/v1/parser.rb +214 -0
- data/lib/travis/conditions/version.rb +1 -1
- data/spec/conditions_spec.rb +15 -0
- data/spec/v0/conditions_spec.rb +15 -0
- data/spec/{data_spec.rb → v0/data_spec.rb} +6 -1
- data/spec/{eval_spec.rb → v0/eval_spec.rb} +1 -1
- data/spec/v0/fixtures/failures.txt +342 -0
- data/spec/v0/fixtures/passes.txt +1685 -0
- data/spec/{parser_spec.rb → v0/parser_spec.rb} +1 -1
- data/spec/v1/conditions_spec.rb +44 -0
- data/spec/v1/data_spec.rb +30 -0
- data/spec/v1/eval_spec.rb +349 -0
- data/spec/v1/fixtures/failures.txt +336 -0
- data/spec/v1/fixtures/passes.txt +1634 -0
- data/spec/v1/parser/boolean_spec.rb +215 -0
- data/spec/v1/parser/call_spec.rb +68 -0
- data/spec/v1/parser/comma_spec.rb +28 -0
- data/spec/v1/parser/cont_spec.rb +41 -0
- data/spec/v1/parser/eq_spec.rb +16 -0
- data/spec/v1/parser/in_list_spec.rb +60 -0
- data/spec/v1/parser/is_pred_spec.rb +24 -0
- data/spec/v1/parser/list_spec.rb +36 -0
- data/spec/v1/parser/operand_spec.rb +16 -0
- data/spec/v1/parser/parens_spec.rb +28 -0
- data/spec/v1/parser/quoted_spec.rb +24 -0
- data/spec/v1/parser/re_spec.rb +16 -0
- data/spec/v1/parser/regex_spec.rb +12 -0
- data/spec/v1/parser/space_spec.rb +40 -0
- data/spec/v1/parser/term_spec.rb +84 -0
- data/spec/v1/parser/val_spec.rb +24 -0
- data/spec/v1/parser/var_spec.rb +16 -0
- data/spec/v1/parser_spec.rb +486 -0
- data/spec/v1/user_spec.rb +223 -0
- metadata +48 -9
- data/lib/travis/conditions/data.rb +0 -45
- data/lib/travis/conditions/eval.rb +0 -68
- data/lib/travis/conditions/parser.rb +0 -202
@@ -0,0 +1,215 @@
|
|
1
|
+
class BooleanParser
|
2
|
+
extend Forwardable
|
3
|
+
include Travis::Conditions::V1::Boolean
|
4
|
+
include Travis::Conditions::V1::Helper
|
5
|
+
|
6
|
+
def_delegators :str, :scan, :skip, :string, :pos, :peek
|
7
|
+
attr_reader :str
|
8
|
+
|
9
|
+
VAR = /[A-Z]{1}/
|
10
|
+
|
11
|
+
def initialize(str)
|
12
|
+
@str = StringScanner.new(str)
|
13
|
+
end
|
14
|
+
|
15
|
+
def term
|
16
|
+
space { scan(VAR) }
|
17
|
+
end
|
18
|
+
end
|
19
|
+
|
20
|
+
describe BooleanParser, 'expr' do
|
21
|
+
let(:str) { |e| e.description }
|
22
|
+
let(:subject) { described_class.new(str).expr }
|
23
|
+
|
24
|
+
# one term
|
25
|
+
|
26
|
+
it 'A' do
|
27
|
+
should eq 'A'
|
28
|
+
end
|
29
|
+
|
30
|
+
it '(A)' do
|
31
|
+
should eq 'A'
|
32
|
+
end
|
33
|
+
|
34
|
+
it 'not A' do
|
35
|
+
should eq [:not, 'A']
|
36
|
+
end
|
37
|
+
|
38
|
+
it 'not (A)' do
|
39
|
+
should eq [:not, 'A']
|
40
|
+
end
|
41
|
+
|
42
|
+
it '(not A)' do
|
43
|
+
should eq [:not, 'A']
|
44
|
+
end
|
45
|
+
|
46
|
+
it '!A' do
|
47
|
+
should eq [:not, 'A']
|
48
|
+
end
|
49
|
+
|
50
|
+
it '! A' do
|
51
|
+
should eq [:not, 'A']
|
52
|
+
end
|
53
|
+
|
54
|
+
it '!(A)' do
|
55
|
+
should eq [:not, 'A']
|
56
|
+
end
|
57
|
+
|
58
|
+
it '! (A)' do
|
59
|
+
should eq [:not, 'A']
|
60
|
+
end
|
61
|
+
|
62
|
+
# two terms
|
63
|
+
|
64
|
+
it 'A and B' do
|
65
|
+
should eq [:and, 'A', 'B']
|
66
|
+
end
|
67
|
+
|
68
|
+
it '(A) and B' do
|
69
|
+
should eq [:and, 'A', 'B']
|
70
|
+
end
|
71
|
+
|
72
|
+
it 'A and (B)' do
|
73
|
+
should eq [:and, 'A', 'B']
|
74
|
+
end
|
75
|
+
|
76
|
+
it '(A) and (B)' do
|
77
|
+
should eq [:and, 'A', 'B']
|
78
|
+
end
|
79
|
+
|
80
|
+
it 'not A and B' do
|
81
|
+
should eq [:and, [:not, 'A'], 'B']
|
82
|
+
end
|
83
|
+
|
84
|
+
it 'A and not B' do
|
85
|
+
should eq [:and, 'A', [:not, 'B']]
|
86
|
+
end
|
87
|
+
|
88
|
+
it 'not A and not B' do
|
89
|
+
should eq [:and, [:not, 'A'], [:not, 'B']]
|
90
|
+
end
|
91
|
+
|
92
|
+
it 'not (A) and B' do
|
93
|
+
should eq [:and, [:not, 'A'], 'B']
|
94
|
+
end
|
95
|
+
|
96
|
+
it '(A) and not B' do
|
97
|
+
should eq [:and, 'A', [:not, 'B']]
|
98
|
+
end
|
99
|
+
|
100
|
+
it 'not (A) and not B' do
|
101
|
+
should eq [:and, [:not, 'A'], [:not, 'B']]
|
102
|
+
end
|
103
|
+
|
104
|
+
it 'not (A) and (B)' do
|
105
|
+
should eq [:and, [:not, 'A'], 'B']
|
106
|
+
end
|
107
|
+
|
108
|
+
it '(A) and not (B)' do
|
109
|
+
should eq [:and, 'A', [:not, 'B']]
|
110
|
+
end
|
111
|
+
|
112
|
+
it 'not (A) and not (B)' do
|
113
|
+
should eq [:and, [:not, 'A'], [:not, 'B']]
|
114
|
+
end
|
115
|
+
|
116
|
+
it '(not A) and B' do
|
117
|
+
should eq [:and, [:not, 'A'], 'B']
|
118
|
+
end
|
119
|
+
|
120
|
+
it '(A) and not B' do
|
121
|
+
should eq [:and, 'A', [:not, 'B']]
|
122
|
+
end
|
123
|
+
|
124
|
+
it '(not A) and not B' do
|
125
|
+
should eq [:and, [:not, 'A'], [:not, 'B']]
|
126
|
+
end
|
127
|
+
|
128
|
+
it '(not A) and (B)' do
|
129
|
+
should eq [:and, [:not, 'A'], 'B']
|
130
|
+
end
|
131
|
+
|
132
|
+
it '(A) and (not B)' do
|
133
|
+
should eq [:and, 'A', [:not, 'B']]
|
134
|
+
end
|
135
|
+
|
136
|
+
it '(not A) and (not B)' do
|
137
|
+
should eq [:and, [:not, 'A'], [:not, 'B']]
|
138
|
+
end
|
139
|
+
|
140
|
+
it '(! A) && !B' do
|
141
|
+
should eq [:and, [:not, 'A'], [:not, 'B']]
|
142
|
+
end
|
143
|
+
|
144
|
+
# three terms
|
145
|
+
|
146
|
+
it 'A and B and C' do
|
147
|
+
should eq [:and, [:and, 'A', 'B'], 'C']
|
148
|
+
end
|
149
|
+
|
150
|
+
it 'A and B or C' do
|
151
|
+
should eq [:or, [:and, 'A', 'B'], 'C']
|
152
|
+
end
|
153
|
+
|
154
|
+
it 'A or B and C' do
|
155
|
+
should eq [:or, 'A', [:and, 'B', 'C']]
|
156
|
+
end
|
157
|
+
|
158
|
+
it 'A or B or C' do
|
159
|
+
should eq [:or, [:or, 'A', 'B'], 'C']
|
160
|
+
end
|
161
|
+
|
162
|
+
it '(A and B and C)' do
|
163
|
+
should eq [:and, [:and, 'A', 'B'], 'C']
|
164
|
+
end
|
165
|
+
|
166
|
+
it '(A and B) and C' do
|
167
|
+
should eq [:and, [:and, 'A', 'B'], 'C']
|
168
|
+
end
|
169
|
+
|
170
|
+
it 'A and (B and C)' do
|
171
|
+
should eq [:and, 'A', [:and, 'B', 'C']]
|
172
|
+
end
|
173
|
+
|
174
|
+
it '(A or B) and C' do
|
175
|
+
should eq [:and, [:or, 'A', 'B'], 'C']
|
176
|
+
end
|
177
|
+
|
178
|
+
it 'A and (B or C)' do
|
179
|
+
should eq [:and, 'A', [:or, 'B', 'C']]
|
180
|
+
end
|
181
|
+
|
182
|
+
it '(not A and not B and not C)' do
|
183
|
+
should eq [:and, [:and, [:not, 'A'], [:not, 'B']], [:not, 'C']]
|
184
|
+
end
|
185
|
+
|
186
|
+
it 'not (not A and not B and not C)' do
|
187
|
+
should eq [:not, [:and, [:and, [:not, 'A'], [:not, 'B']], [:not, 'C']]]
|
188
|
+
end
|
189
|
+
|
190
|
+
it '(not A or not B) and not C' do
|
191
|
+
should eq [:and, [:or, [:not, 'A'], [:not, 'B']], [:not, 'C']]
|
192
|
+
end
|
193
|
+
|
194
|
+
it 'not (not A or not B) and not C' do
|
195
|
+
should eq [:and, [:not, [:or, [:not, 'A'], [:not, 'B']]], [:not, 'C']]
|
196
|
+
end
|
197
|
+
|
198
|
+
it 'not(not A and not (not B or not C))' do
|
199
|
+
should eq [:not, [:and, [:not, 'A'], [:not, [:or, [:not, 'B'], [:not, 'C']]]]]
|
200
|
+
end
|
201
|
+
|
202
|
+
# six terms
|
203
|
+
|
204
|
+
it 'A or B and C or D and E or F' do
|
205
|
+
should eq [:or, [:or, [:or, 'A', [:and, 'B', 'C']], [:and, 'D', 'E']], 'F']
|
206
|
+
end
|
207
|
+
|
208
|
+
it '(A or B) and C or D and (E or F)' do
|
209
|
+
should eq [:or, [:and, [:or, 'A', 'B'], 'C'], [:and, 'D', [:or, 'E', 'F']]]
|
210
|
+
end
|
211
|
+
|
212
|
+
it '(A or B) and (C or D) and (E or F)' do
|
213
|
+
should eq [:and, [:and, [:or, 'A', 'B'], [:or, 'C', 'D']], [:or, 'E', 'F']]
|
214
|
+
end
|
215
|
+
end
|
@@ -0,0 +1,68 @@
|
|
1
|
+
describe Travis::Conditions::V1::Parser, 'call' do
|
2
|
+
let(:str) { |e| e.description }
|
3
|
+
let(:subject) { described_class.new(str).call }
|
4
|
+
|
5
|
+
it 'env()' do
|
6
|
+
should eq [:call, :env, []]
|
7
|
+
end
|
8
|
+
|
9
|
+
it 'env(foo)' do
|
10
|
+
should eq [:call, :env, [[:val, 'foo']]]
|
11
|
+
end
|
12
|
+
|
13
|
+
it 'env(type)' do
|
14
|
+
should eq [:call, :env, [[:var, :type]]]
|
15
|
+
end
|
16
|
+
|
17
|
+
it 'env(env(foo))' do
|
18
|
+
should eq [:call, :env, [[:call, :env, [[:val, 'foo']]]]]
|
19
|
+
end
|
20
|
+
|
21
|
+
it 'env(env(env(foo)))' do
|
22
|
+
should eq [:call, :env, [[:call, :env, [[:call, :env, [[:val, 'foo']]]]]]]
|
23
|
+
end
|
24
|
+
|
25
|
+
it 'env(foo, bar)' do
|
26
|
+
should eq [:call, :env, [[:val, 'foo'], [:val, 'bar']]]
|
27
|
+
end
|
28
|
+
|
29
|
+
it 'env("foo")' do
|
30
|
+
should eq [:call, :env, [[:val, 'foo']]]
|
31
|
+
end
|
32
|
+
|
33
|
+
it 'env("foo", "bar")' do
|
34
|
+
should eq [:call, :env, [[:val, 'foo'], [:val, 'bar']]]
|
35
|
+
end
|
36
|
+
|
37
|
+
it "env('foo')" do
|
38
|
+
should eq [:call, :env, [[:val, 'foo']]]
|
39
|
+
end
|
40
|
+
|
41
|
+
it "env('foo', 'bar')" do
|
42
|
+
should eq [:call, :env, [[:val, 'foo'], [:val, 'bar']]]
|
43
|
+
end
|
44
|
+
|
45
|
+
it 'concat()' do
|
46
|
+
should eq [:call, :concat, []]
|
47
|
+
end
|
48
|
+
|
49
|
+
it 'concat(foo)' do
|
50
|
+
should eq [:call, :concat, [[:val, 'foo']]]
|
51
|
+
end
|
52
|
+
|
53
|
+
it 'concat(foo, bar)' do
|
54
|
+
should eq [:call, :concat, [[:val, 'foo'], [:val, 'bar']]]
|
55
|
+
end
|
56
|
+
|
57
|
+
it 'concat(foo, env(bar))' do
|
58
|
+
should eq [:call, :concat, [[:val, 'foo'], [:call, :env, [[:val, 'bar']]]]]
|
59
|
+
end
|
60
|
+
|
61
|
+
it 'concat(branch, foo)' do
|
62
|
+
should eq [:call, :concat, [[:var, :branch], [:val, 'foo']]]
|
63
|
+
end
|
64
|
+
|
65
|
+
it 'bar()' do
|
66
|
+
should be_nil
|
67
|
+
end
|
68
|
+
end
|
@@ -0,0 +1,28 @@
|
|
1
|
+
describe Travis::Conditions::V1::Parser, 'comma' do
|
2
|
+
let(:str) { |e| e.description }
|
3
|
+
|
4
|
+
let(:subject) do
|
5
|
+
p = described_class.new(str)
|
6
|
+
[p.word.tap { p.comma }, p.word]
|
7
|
+
end
|
8
|
+
|
9
|
+
it 'foo,bar' do
|
10
|
+
should eq ['foo', 'bar']
|
11
|
+
end
|
12
|
+
|
13
|
+
it 'foo, bar' do
|
14
|
+
should eq ['foo', 'bar']
|
15
|
+
end
|
16
|
+
|
17
|
+
it 'foo ,bar' do
|
18
|
+
should eq ['foo', 'bar']
|
19
|
+
end
|
20
|
+
|
21
|
+
it 'foo , bar' do
|
22
|
+
should eq ['foo', 'bar']
|
23
|
+
end
|
24
|
+
|
25
|
+
it 'foo' do
|
26
|
+
should eq ['foo', nil]
|
27
|
+
end
|
28
|
+
end
|
@@ -0,0 +1,41 @@
|
|
1
|
+
describe Travis::Conditions::V1::Parser, 'line continuation' do
|
2
|
+
let(:str) { |e| e.description }
|
3
|
+
let(:subject) { described_class.new(str).parse }
|
4
|
+
|
5
|
+
# backslashes
|
6
|
+
|
7
|
+
it "1 = 1 AND\\\n2 = 2" do
|
8
|
+
should eq \
|
9
|
+
[:and,
|
10
|
+
[:eq, [:val, '1'], [:val, '1']],
|
11
|
+
[:eq, [:val, '2'], [:val, '2']]]
|
12
|
+
end
|
13
|
+
|
14
|
+
it "1 = 1 AND \\\n 2 = 2" do
|
15
|
+
should eq \
|
16
|
+
[:and,
|
17
|
+
[:eq, [:val, '1'], [:val, '1']],
|
18
|
+
[:eq, [:val, '2'], [:val, '2']]]
|
19
|
+
end
|
20
|
+
|
21
|
+
it "1 = 1 AND \\ \n 2 = 2" do
|
22
|
+
should eq \
|
23
|
+
[:and,
|
24
|
+
[:eq, [:val, '1'], [:val, '1']],
|
25
|
+
[:eq, [:val, '2'], [:val, '2']]]
|
26
|
+
end
|
27
|
+
|
28
|
+
it "\\\n1 = 1 AND\\\n2 = 2" do
|
29
|
+
should eq \
|
30
|
+
[:and,
|
31
|
+
[:eq, [:val, '1'], [:val, '1']],
|
32
|
+
[:eq, [:val, '2'], [:val, '2']]]
|
33
|
+
end
|
34
|
+
|
35
|
+
it "\\\n1 = 1 AND\\\n2 = 2\\\n" do
|
36
|
+
should eq \
|
37
|
+
[:and,
|
38
|
+
[:eq, [:val, '1'], [:val, '1']],
|
39
|
+
[:eq, [:val, '2'], [:val, '2']]]
|
40
|
+
end
|
41
|
+
end
|
@@ -0,0 +1,16 @@
|
|
1
|
+
describe Travis::Conditions::V1::Parser, 'eq' do
|
2
|
+
let(:str) { |e| e.description }
|
3
|
+
let(:subject) { described_class.new(str).eq }
|
4
|
+
|
5
|
+
it '=' do
|
6
|
+
should eq :eq
|
7
|
+
end
|
8
|
+
|
9
|
+
it '==' do
|
10
|
+
should eq :eq
|
11
|
+
end
|
12
|
+
|
13
|
+
it '!=' do
|
14
|
+
should eq :not_eq
|
15
|
+
end
|
16
|
+
end
|
@@ -0,0 +1,60 @@
|
|
1
|
+
describe Travis::Conditions::V1::Parser, 'in_list' do
|
2
|
+
let(:str) { |e| e.description }
|
3
|
+
let(:subject) { described_class.new(str).in_list('foo') }
|
4
|
+
|
5
|
+
it 'in (foo)' do
|
6
|
+
should eq [:in, 'foo', [[:val, 'foo']]]
|
7
|
+
end
|
8
|
+
|
9
|
+
it 'in (type)' do
|
10
|
+
should eq [:in, 'foo', [[:var, :type]]]
|
11
|
+
end
|
12
|
+
|
13
|
+
it 'in (env(foo))' do
|
14
|
+
should eq [:in, 'foo', [[:call, :env, [[:val, 'foo']]]]]
|
15
|
+
end
|
16
|
+
|
17
|
+
it 'in (env(env(foo)))' do
|
18
|
+
should eq [:in, 'foo', [[:call, :env, [[:call, :env, [[:val, 'foo']]]]]]]
|
19
|
+
end
|
20
|
+
|
21
|
+
it 'in ( foo,bar)' do
|
22
|
+
should eq [:in, 'foo', [[:val, 'foo'], [:val, 'bar']]]
|
23
|
+
end
|
24
|
+
|
25
|
+
it 'in (foo, bar )' do
|
26
|
+
should eq [:in, 'foo', [[:val, 'foo'], [:val, 'bar']]]
|
27
|
+
end
|
28
|
+
|
29
|
+
it 'in (foo ,bar)' do
|
30
|
+
should eq [:in, 'foo', [[:val, 'foo'], [:val, 'bar']]]
|
31
|
+
end
|
32
|
+
|
33
|
+
it 'in ("foo")' do
|
34
|
+
should eq [:in, 'foo', [[:val, 'foo']]]
|
35
|
+
end
|
36
|
+
|
37
|
+
it 'not in (foo )' do
|
38
|
+
should eq [:not_in, 'foo', [[:val, 'foo']]]
|
39
|
+
end
|
40
|
+
|
41
|
+
it 'not in ( foo,bar)' do
|
42
|
+
should eq [:not_in, 'foo', [[:val, 'foo'], [:val, 'bar']]]
|
43
|
+
end
|
44
|
+
|
45
|
+
it 'not in (foo, bar )' do
|
46
|
+
should eq [:not_in, 'foo', [[:val, 'foo'], [:val, 'bar']]]
|
47
|
+
end
|
48
|
+
|
49
|
+
it 'not in (foo ,bar)' do
|
50
|
+
should eq [:not_in, 'foo', [[:val, 'foo'], [:val, 'bar']]]
|
51
|
+
end
|
52
|
+
|
53
|
+
it 'not in ("foo")' do
|
54
|
+
should eq [:not_in, 'foo', [[:val, 'foo']]]
|
55
|
+
end
|
56
|
+
|
57
|
+
it 'in ()' do
|
58
|
+
expect { subject }.to raise_error Travis::Conditions::ParseError, 'expected a list of values at position 4 in: "in ()"'
|
59
|
+
end
|
60
|
+
end
|
@@ -0,0 +1,24 @@
|
|
1
|
+
describe Travis::Conditions::V1::Parser, 'is_pred' do
|
2
|
+
let(:str) { |e| e.description }
|
3
|
+
let(:subject) { described_class.new(str).is_pred(:type) }
|
4
|
+
|
5
|
+
it 'is present' do
|
6
|
+
should eq [:is, :type, :present]
|
7
|
+
end
|
8
|
+
|
9
|
+
it 'is present' do
|
10
|
+
should eq [:is, :type, :present]
|
11
|
+
end
|
12
|
+
|
13
|
+
it 'IS present' do
|
14
|
+
should eq [:is, :type, :present]
|
15
|
+
end
|
16
|
+
|
17
|
+
it 'is blank' do
|
18
|
+
should eq [:is, :type, :blank]
|
19
|
+
end
|
20
|
+
|
21
|
+
it 'IS blank' do
|
22
|
+
should eq [:is, :type, :blank]
|
23
|
+
end
|
24
|
+
end
|