lazylead 0.10.2 → 0.11.0

Sign up to get free protection for your applications and to get access to all the features.
Files changed (36) hide show
  1. checksums.yaml +4 -4
  2. data/.githooks/commit-msg +13 -0
  3. data/.rultor.yml +1 -0
  4. data/Rakefile +9 -1
  5. data/lazylead.gemspec +8 -7
  6. data/lib/lazylead/cli/app.rb +1 -1
  7. data/lib/lazylead/model.rb +24 -3
  8. data/lib/lazylead/opts.rb +11 -0
  9. data/lib/lazylead/schedule.rb +8 -1
  10. data/lib/lazylead/system/jira.rb +4 -3
  11. data/lib/lazylead/task/accuracy/accuracy.rb +32 -4
  12. data/lib/lazylead/task/accuracy/has_label.rb +48 -0
  13. data/lib/lazylead/task/accuracy/logs_link.rb +2 -2
  14. data/lib/lazylead/task/accuracy/memes.rb +77 -0
  15. data/lib/lazylead/task/accuracy/records.rb +3 -1
  16. data/lib/lazylead/task/accuracy/records_link.rb +49 -0
  17. data/lib/lazylead/task/accuracy/wiki_url.rb +46 -0
  18. data/lib/lazylead/version.rb +1 -1
  19. data/lib/messages/svn_grep.erb +1 -0
  20. data/test/lazylead/exchange_test.rb +21 -14
  21. data/test/lazylead/opts_test.rb +16 -0
  22. data/test/lazylead/retry_test.rb +85 -0
  23. data/test/lazylead/system/jira_test.rb +13 -5
  24. data/test/lazylead/task/accuracy/accuracy_test.rb +5 -0
  25. data/test/lazylead/task/accuracy/has_label_test.rb +54 -0
  26. data/test/lazylead/task/accuracy/memes_test.rb +77 -0
  27. data/test/lazylead/task/accuracy/records_llink_test.rb +55 -0
  28. data/test/lazylead/task/accuracy/records_test.rb +16 -0
  29. data/test/lazylead/task/accuracy/score_test.rb +7 -0
  30. data/test/lazylead/task/accuracy/screenshots_test.rb +2 -0
  31. data/test/lazylead/task/accuracy/wiki_url_test.rb +58 -0
  32. data/test/lazylead/task/svn/grep_test.rb +1 -2
  33. data/test/lazylead/task/svn/touch_test.rb +1 -1
  34. data/test/sqlite_test.rb +1 -1
  35. data/test/test.rb +47 -0
  36. metadata +42 -13
@@ -39,7 +39,9 @@ module Lazylead
39
39
 
40
40
  # Ensure that ticket has an attachment with video-file extension
41
41
  def matches?(attach)
42
- @ext.any? { |e| e.eql? File.extname(attach.attrs["filename"]).downcase }
42
+ return true if @ext.any? { |e| e.eql? File.extname(attach.attrs["filename"]).downcase }
43
+ return false if attach.attrs["mimeType"].nil?
44
+ @ext.any? { |e| attach.attrs["mimeType"].include? e[1..] }
43
45
  end
44
46
  end
45
47
  end
@@ -0,0 +1,49 @@
1
+ # frozen_string_literal: true
2
+
3
+ # The MIT License
4
+ #
5
+ # Copyright (c) 2019-2021 Yurii Dubinka
6
+ #
7
+ # Permission is hereby granted, free of charge, to any person obtaining a copy
8
+ # of this software and associated documentation files (the "Software"),
9
+ # to deal in the Software without restriction, including without limitation
10
+ # the rights to use, copy, modify, merge, publish, distribute, sublicense,
11
+ # and/or sell copies of the Software, and to permit persons to whom
12
+ # the Software is furnished to do so, subject to the following conditions:
13
+ #
14
+ # The above copyright notice and this permission notice shall be included
15
+ # in all copies or substantial portions of the Software.
16
+ #
17
+ # THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
18
+ # IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
19
+ # FITNESS FOR A PARTICULAR PURPOSE AND NON-INFRINGEMENT. IN NO EVENT SHALL THE
20
+ # AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
21
+ # LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE,
22
+ # ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE
23
+ # OR OTHER DEALINGS IN THE SOFTWARE.
24
+
25
+ require_relative "records"
26
+
27
+ module Lazylead
28
+ # Check that ticket has links to video record(s) with reproducing results.
29
+ class RecordsLink < Lazylead::Records
30
+ def initialize(*urls)
31
+ super([])
32
+ @urls = urls
33
+ end
34
+
35
+ def passed(issue)
36
+ link?(issue) || super(issue)
37
+ end
38
+
39
+ def link?(issue)
40
+ return false if issue.description.nil?
41
+ issue.description
42
+ .split("\n")
43
+ .reject(&:blank?)
44
+ .flat_map(&:split)
45
+ .reject(&:blank?)
46
+ .any? { |word| @urls.any? { |u| word.start_with? u } }
47
+ end
48
+ end
49
+ end
@@ -0,0 +1,46 @@
1
+ # frozen_string_literal: true
2
+
3
+ # The MIT License
4
+ #
5
+ # Copyright (c) 2019-2021 Yurii Dubinka
6
+ #
7
+ # Permission is hereby granted, free of charge, to any person obtaining a copy
8
+ # of this software and associated documentation files (the "Software"),
9
+ # to deal in the Software without restriction, including without limitation
10
+ # the rights to use, copy, modify, merge, publish, distribute, sublicense,
11
+ # and/or sell copies of the Software, and to permit persons to whom
12
+ # the Software is furnished to do so, subject to the following conditions:
13
+ #
14
+ # The above copyright notice and this permission notice shall be included
15
+ # in all copies or substantial portions of the Software.
16
+ #
17
+ # THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
18
+ # IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
19
+ # FITNESS FOR A PARTICULAR PURPOSE AND NON-INFRINGEMENT. IN NO EVENT SHALL THE
20
+ # AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
21
+ # LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE,
22
+ # ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE
23
+ # OR OTHER DEALINGS IN THE SOFTWARE.
24
+
25
+ require_relative "wiki"
26
+
27
+ module Lazylead
28
+ # Check that ticket has a web link to external system with design.
29
+ class WikiUrl < Lazylead::Wiki
30
+ def initialize(url)
31
+ super()
32
+ @url = url
33
+ end
34
+
35
+ def passed(issue)
36
+ link?(issue) || super(issue)
37
+ end
38
+
39
+ def link?(issue)
40
+ issue.remote_links
41
+ .reject { |l| l.attrs.nil? || l.attrs.empty? }
42
+ .reject { |l| l.attrs["object"].nil? || l.attrs["object"]["url"].nil? }
43
+ .any? { |l| l.attrs["object"]["url"].start_with? @url }
44
+ end
45
+ end
46
+ end
@@ -23,5 +23,5 @@
23
23
  # OR OTHER DEALINGS IN THE SOFTWARE.
24
24
 
25
25
  module Lazylead
26
- VERSION = "0.10.2"
26
+ VERSION = "0.11.0"
27
27
  end
@@ -66,6 +66,7 @@
66
66
 
67
67
  td {
68
68
  padding: 2px;
69
+ vertical-align: top;
69
70
  }
70
71
 
71
72
  .commit * {
@@ -26,6 +26,7 @@ require_relative "../test"
26
26
  require_relative "../../lib/lazylead/log"
27
27
  require_relative "../../lib/lazylead/salt"
28
28
  require_relative "../../lib/lazylead/home"
29
+ require_relative "../../lib/lazylead/opts"
29
30
  require_relative "../../lib/lazylead/exchange"
30
31
  require_relative "../../lib/lazylead/system/jira"
31
32
 
@@ -37,11 +38,13 @@ module Lazylead
37
38
  "exchange_password",
38
39
  "exchange_to"
39
40
  Exchange.new(Log.new, NoSalt.new).send(
40
- to: ENV["exchange_to"],
41
- tickets: NoAuthJira.new("https://jira.spring.io")
42
- .issues("key = DATAJDBC-480"),
43
- "subject" => "[DD] PDTN!",
44
- "template" => "lib/messages/due_date_expired.erb"
41
+ Opts.new(
42
+ to: ENV["exchange_to"],
43
+ tickets: NoAuthJira.new("https://jira.spring.io")
44
+ .issues("key = DATAJDBC-480"),
45
+ "subject" => "[DD] PDTN!",
46
+ "template" => "lib/messages/due_date_expired.erb"
47
+ )
45
48
  )
46
49
  end
47
50
 
@@ -58,11 +61,13 @@ module Lazylead
58
61
  "exchange_user" => ENV["enc_exchange_usr"],
59
62
  "exchange_password" => ENV["enc_exchange_psw"]
60
63
  ).send(
61
- to: ENV["exchange_to"],
62
- tickets: NoAuthJira.new("https://jira.spring.io")
63
- .issues("key = DATAJDBC-480"),
64
- "subject" => "[DD] Enc PDTN!",
65
- "template" => "lib/messages/due_date_expired.erb"
64
+ Opts.new(
65
+ to: ENV["exchange_to"],
66
+ tickets: NoAuthJira.new("https://jira.spring.io")
67
+ .issues("key = DATAJDBC-480"),
68
+ "subject" => "[DD] Enc PDTN!",
69
+ "template" => "lib/messages/due_date_expired.erb"
70
+ )
66
71
  )
67
72
  end
68
73
 
@@ -78,10 +83,12 @@ module Lazylead
78
83
  "exchange_user" => ENV["enc_exchange_usr"],
79
84
  "exchange_password" => ENV["enc_exchange_psw"]
80
85
  ).send(
81
- to: ENV["exchange_to"],
82
- "attachments" => "readme.md",
83
- "subject" => "[LL] Attachments",
84
- "template" => "lib/messages/savepoint.erb"
86
+ Opts.new(
87
+ to: ENV["exchange_to"],
88
+ "attachments" => "readme.md",
89
+ "subject" => "[LL] Attachments",
90
+ "template" => "lib/messages/savepoint.erb"
91
+ )
85
92
  )
86
93
  end
87
94
  end
@@ -113,5 +113,21 @@ module Lazylead
113
113
  test "nil is not a numeric" do
114
114
  refute Opts.new("key" => nil).numeric? "key"
115
115
  end
116
+
117
+ test "find by text key" do
118
+ assert_equal "val", Opts.new("key" => "val").find("key")
119
+ end
120
+
121
+ test "find by symbol key" do
122
+ assert_equal "val", Opts.new(key: "val").find(:key)
123
+ end
124
+
125
+ test "find by symbol key but with text key" do
126
+ assert_equal "val", Opts.new("key" => "val").find(:key)
127
+ end
128
+
129
+ test "find default" do
130
+ assert_equal "val", Opts.new.find(:key, "val")
131
+ end
116
132
  end
117
133
  end
@@ -0,0 +1,85 @@
1
+ # frozen_string_literal: true
2
+
3
+ # The MIT License
4
+ #
5
+ # Copyright (c) 2019-2021 Yurii Dubinka
6
+ #
7
+ # Permission is hereby granted, free of charge, to any person obtaining a copy
8
+ # of this software and associated documentation files (the "Software"),
9
+ # to deal in the Software without restriction, including without limitation
10
+ # the rights to use, copy, modify, merge, publish, distribute, sublicense,
11
+ # and/or sell copies of the Software, and to permit persons to whom
12
+ # the Software is furnished to do so, subject to the following conditions:
13
+ #
14
+ # The above copyright notice and this permission notice shall be included
15
+ # in all copies or substantial portions of the Software.
16
+ #
17
+ # THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
18
+ # IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
19
+ # FITNESS FOR A PARTICULAR PURPOSE AND NON-INFRINGEMENT. IN NO EVENT SHALL THE
20
+ # AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
21
+ # LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE,
22
+ # ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE
23
+ # OR OTHER DEALINGS IN THE SOFTWARE.
24
+
25
+ require_relative "../test"
26
+ require_relative "../../lib/lazylead/log"
27
+ require_relative "../../lib/lazylead/model"
28
+
29
+ module Lazylead
30
+ # Fake lazylead task for unit testing purposes.
31
+ class FakeTask
32
+ attr_reader :attempts
33
+
34
+ # Ctor.
35
+ # @param proc
36
+ # The logic to be executed in task.
37
+ # The logic may successfully finished or fail due to the exception.
38
+ # @param opts
39
+ # The task properties defined in the database by the user.
40
+ # @see Task#props
41
+ def initialize(proc, opts)
42
+ @proc = proc
43
+ @opts = opts
44
+ @attempts = 0
45
+ end
46
+
47
+ # Execute the fake task logic and count the attempt.
48
+ def exec
49
+ @attempts += 1
50
+ @proc.call
51
+ end
52
+
53
+ # The task properties.
54
+ def props
55
+ @opts
56
+ end
57
+ end
58
+
59
+ class RetryTest < Lazylead::Test
60
+ test "retry 3 times if error" do
61
+ assert_equal 3,
62
+ ORM::Retry.new(
63
+ FakeTask.new(
64
+ proc { raise "shit happens, you know..." },
65
+ "attempt" => "3"
66
+ )
67
+ ).exec.attempts
68
+ end
69
+
70
+ test "no retry if task successful" do
71
+ assert_equal 1, ORM::Retry.new(FakeTask.new(proc { "ok" }, "attempt" => "3")).exec.attempts
72
+ end
73
+
74
+ test "retry and sleep if error" do
75
+ assert_equal 2,
76
+ ORM::Retry.new(
77
+ FakeTask.new(
78
+ proc { raise "network issue" },
79
+ "attempt" => "2",
80
+ "attempt_wait" => "0.01" # => 0.01 second
81
+ )
82
+ ).exec.attempts
83
+ end
84
+ end
85
+ end
@@ -143,7 +143,7 @@ module Lazylead
143
143
  end
144
144
 
145
145
  test "description is correct" do
146
- assert_words %w[DATACMNS-1639\ moved\ entity\ instantiators],
146
+ assert_words ["DATACMNS-1639 moved entity instantiators"],
147
147
  NoAuthJira.new("https://jira.spring.io")
148
148
  .issues("key=DATAJDBC-480")
149
149
  .first
@@ -151,7 +151,7 @@ module Lazylead
151
151
  end
152
152
 
153
153
  test "component is correct" do
154
- assert_equal %w[Stream\ Module],
154
+ assert_equal ["Stream Module"],
155
155
  NoAuthJira.new("https://jira.spring.io")
156
156
  .issues("key=XD-3766")
157
157
  .first
@@ -181,9 +181,10 @@ module Lazylead
181
181
  end
182
182
 
183
183
  test "bulk search in few iterations" do
184
- assert NoAuthJira.new("https://jira.spring.io")
185
- .issues("key>DATAJDBC-500")
186
- .size >= 118
184
+ assert_equal 3,
185
+ NoAuthJira.new("https://jira.spring.io")
186
+ .issues("key>DATAJDBC-500 and key < DATAJDBC-504", max_results: 1)
187
+ .size
187
188
  end
188
189
 
189
190
  test "connected based on string properties" do
@@ -202,5 +203,12 @@ module Lazylead
202
203
  .first
203
204
  .sprint("customfield_10480")
204
205
  end
206
+
207
+ test "bulk search in few iterations with limit" do
208
+ assert_equal 3,
209
+ NoAuthJira.new("https://jira.spring.io")
210
+ .issues("key > DATAJDBC-500", max_results: 1, "limit" => 3)
211
+ .size
212
+ end
205
213
  end
206
214
  end
@@ -48,6 +48,11 @@ module Lazylead
48
48
  "57" => "#19DD1E",
49
49
  "90" => "#0FA81A"
50
50
  }.to_json.to_s,
51
+ "memes" => {
52
+ "0-9.9" => "https://meme.com?id=awful1.gif,https://meme.com?id=awful2.gif",
53
+ "70-89.9" => "https://meme.com?id=nice.gif",
54
+ "90-100" => "https://meme.com?id=wow.gif"
55
+ }.to_json.to_s,
51
56
  "docs" => "https://github.com/dgroup/lazylead/blob/master/.github/ISSUE_TEMPLATE/bug_report.md",
52
57
  "jql" => "key in (DATAJDBC-490, DATAJDBC-492, DATAJDBC-493)",
53
58
  "max_results" => 200,
@@ -0,0 +1,54 @@
1
+ # frozen_string_literal: true
2
+
3
+ # The MIT License
4
+ #
5
+ # Copyright (c) 2019-2021 Yurii Dubinka
6
+ #
7
+ # Permission is hereby granted, free of charge, to any person obtaining a copy
8
+ # of this software and associated documentation files (the "Software"),
9
+ # to deal in the Software without restriction, including without limitation
10
+ # the rights to use, copy, modify, merge, publish, distribute, sublicense,
11
+ # and/or sell copies of the Software, and to permit persons to whom
12
+ # the Software is furnished to do so, subject to the following conditions:
13
+ #
14
+ # The above copyright notice and this permission notice shall be included
15
+ # in all copies or substantial portions of the Software.
16
+ #
17
+ # THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
18
+ # IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
19
+ # FITNESS FOR A PARTICULAR PURPOSE AND NON-INFRINGEMENT. IN NO EVENT SHALL THE
20
+ # AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
21
+ # LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE,
22
+ # ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE
23
+ # OR OTHER DEALINGS IN THE SOFTWARE.
24
+
25
+ require_relative "../../../test"
26
+ require_relative "../../../../lib/lazylead/task/accuracy/has_label"
27
+
28
+ module Lazylead
29
+ class HasLabelTest < Lazylead::Test
30
+ test "label is present" do
31
+ assert HasLabel.new("Invalid_Reopen").passed(
32
+ OpenStruct.new(
33
+ labels: %w[Invalid_Reopen 10%]
34
+ )
35
+ )
36
+ end
37
+
38
+ test "label is absent" do
39
+ refute HasLabel.new("Invalid_Reopen").passed(
40
+ OpenStruct.new(
41
+ labels: %w[E2E top_priority 10%]
42
+ )
43
+ )
44
+ end
45
+
46
+ test "labels are absent in ticket" do
47
+ refute HasLabel.new("Invalid_Reopen").passed(
48
+ OpenStruct.new(
49
+ labels: []
50
+ )
51
+ )
52
+ end
53
+ end
54
+ end
@@ -0,0 +1,77 @@
1
+ # frozen_string_literal: true
2
+
3
+ # The MIT License
4
+ #
5
+ # Copyright (c) 2019-2021 Yurii Dubinka
6
+ #
7
+ # Permission is hereby granted, free of charge, to any person obtaining a copy
8
+ # of this software and associated documentation files (the "Software"),
9
+ # to deal in the Software without restriction, including without limitation
10
+ # the rights to use, copy, modify, merge, publish, distribute, sublicense,
11
+ # and/or sell copies of the Software, and to permit persons to whom
12
+ # the Software is furnished to do so, subject to the following conditions:
13
+ #
14
+ # The above copyright notice and this permission notice shall be included
15
+ # in all copies or substantial portions of the Software.
16
+ #
17
+ # THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
18
+ # IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
19
+ # FITNESS FOR A PARTICULAR PURPOSE AND NON-INFRINGEMENT. IN NO EVENT SHALL THE
20
+ # AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
21
+ # LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE,
22
+ # ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE
23
+ # OR OTHER DEALINGS IN THE SOFTWARE.
24
+
25
+ require_relative "../../../test"
26
+ require_relative "../../../../lib/lazylead/task/accuracy/memes"
27
+
28
+ module Lazylead
29
+ class MemesTest < Lazylead::Test
30
+ test "detect range" do
31
+ assert_array(
32
+ [
33
+ [0.0, 9.9, %w[https://meme.com?id=awful1.gif https://meme.com?id=awful2.gif]],
34
+ [70.0, 89.9, ["https://meme.com?id=nice.gif"]],
35
+ [90.0, 100.0, ["https://meme.com?id=wow.gif"]]
36
+ ],
37
+ Lazylead::Memes.new(
38
+ {
39
+ "0-9.9" => "https://meme.com?id=awful1.gif,https://meme.com?id=awful2.gif",
40
+ "70-89.9" => "https://meme.com?id=nice.gif",
41
+ "90-100" => "https://meme.com?id=wow.gif"
42
+ }.to_json.to_s
43
+ ).range
44
+ )
45
+ end
46
+
47
+ test "find by score" do
48
+ assert_equal "https://meme.com?id=nice.gif",
49
+ Lazylead::Memes.new(
50
+ {
51
+ "0-9.9" => "https://meme.com?id=awful1.gif,https://meme.com?id=awful2.gif",
52
+ "70-89.9" => "https://meme.com?id=nice.gif",
53
+ "90-100" => "https://meme.com?id=wow.gif"
54
+ }.to_json.to_s
55
+ ).find(80)
56
+ end
57
+
58
+ test "not found" do
59
+ assert_blank Lazylead::Memes.new(
60
+ {
61
+ "0-9.9" => "https://meme.com?id=awful1.gif,https://meme.com?id=awful2.gif",
62
+ "70-89.9" => "https://meme.com?id=nice.gif"
63
+ }.to_json.to_s
64
+ ).find(40)
65
+ end
66
+
67
+ test "positive_assert_array" do
68
+ assert_array [[1, 2, %w[a b]]],
69
+ [[1, 2, %w[a b]]]
70
+ end
71
+
72
+ test "negative_assert_array" do
73
+ refute array? [[1, 2, %w[a b]]],
74
+ [[1, 2, %w[c d]]]
75
+ end
76
+ end
77
+ end