allure-ruby-commons 2.13.8.1 → 2.19.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/README.md +46 -15
- data/lib/allure-ruby-commons.rb +206 -144
- data/lib/allure_ruby_commons/allure_lifecycle.rb +36 -8
- data/lib/allure_ruby_commons/config.rb +18 -23
- data/lib/allure_ruby_commons/file_writer.rb +16 -5
- data/lib/allure_ruby_commons/model/01_jsonable.rb +0 -2
- data/lib/allure_ruby_commons/model/executable_item.rb +11 -4
- data/lib/allure_ruby_commons/model/test_result.rb +11 -3
- data/lib/allure_ruby_commons/result_utils.rb +36 -15
- data/lib/allure_ruby_commons/step_annotation.rb +39 -0
- data/lib/allure_ruby_commons/testplan.rb +35 -0
- metadata +7 -4
checksums.yaml
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
---
|
|
2
2
|
SHA256:
|
|
3
|
-
metadata.gz:
|
|
4
|
-
data.tar.gz:
|
|
3
|
+
metadata.gz: d63128392504c90df6eccbf93a5f3f0cd39e09d0a09c0b5365fc42ee54a07d90
|
|
4
|
+
data.tar.gz: e70469671849de4218ed7bd79368cde5cc6d8cdd8bbe495882c13b4cb58c1212
|
|
5
5
|
SHA512:
|
|
6
|
-
metadata.gz:
|
|
7
|
-
data.tar.gz:
|
|
6
|
+
metadata.gz: 79249df603728c94f5a88cfe9879410b331ec1485f2a57be91a6805f10a2fb37211a98653a2719d33c74c5994ecbaa582deac15c6edd399dfde71da9db1af48d
|
|
7
|
+
data.tar.gz: 3f72dfec99534df2e5b661799814d36010074fa36d2702947dfbb80084cd22180915a4a96ac9d6da3b98c1ba685d335bacd0459b43f2a3ee59f910fadc4f198d
|
data/README.md
CHANGED
|
@@ -20,12 +20,23 @@ Following configuration options are supported:
|
|
|
20
20
|
|
|
21
21
|
```ruby
|
|
22
22
|
Allure.configure do |config|
|
|
23
|
-
config.results_directory = "/
|
|
23
|
+
config.results_directory = "report/allure-results"
|
|
24
24
|
config.clean_results_directory = true
|
|
25
25
|
config.logging_level = Logger::INFO
|
|
26
|
+
config.logger = Logger.new($stdout, Logger::DEBUG)
|
|
27
|
+
config.environment = "staging"
|
|
28
|
+
|
|
26
29
|
# these are used for creating links to bugs or test cases where {} is replaced with keys of relevant items
|
|
27
30
|
config.link_tms_pattern = "http://www.jira.com/browse/{}"
|
|
28
31
|
config.link_issue_pattern = "http://www.jira.com/browse/{}"
|
|
32
|
+
|
|
33
|
+
# additional metadata
|
|
34
|
+
# environment.properties
|
|
35
|
+
config.environment_properties = {
|
|
36
|
+
custom_attribute: "foo"
|
|
37
|
+
}
|
|
38
|
+
# categories.json
|
|
39
|
+
config.categories = File.new("my_custom_categories.json")
|
|
29
40
|
end
|
|
30
41
|
```
|
|
31
42
|
|
|
@@ -35,6 +46,29 @@ Getting the configuration object:
|
|
|
35
46
|
Allure.configuration
|
|
36
47
|
```
|
|
37
48
|
|
|
49
|
+
### Allure execution environment
|
|
50
|
+
|
|
51
|
+
It is possible to set up custom allure environment which will be used as custom parameter `environment` in every test case. This is useful if you run same tests on different environments and generate single report. This way different runs are not put as retry. Environment can be configured in following ways:
|
|
52
|
+
|
|
53
|
+
* via `ALLURE_ENVIRONMENT` environment variable
|
|
54
|
+
* via `configure` method
|
|
55
|
+
|
|
56
|
+
### Environment properties
|
|
57
|
+
|
|
58
|
+
To add additional environment information to the report it is possible to set configuration property `environment_properties`.
|
|
59
|
+
|
|
60
|
+
Option can be set to hash or block returning a hash:
|
|
61
|
+
|
|
62
|
+
```ruby
|
|
63
|
+
# hash
|
|
64
|
+
config.environment_properties = {
|
|
65
|
+
custom_attribute: "foo"
|
|
66
|
+
}
|
|
67
|
+
|
|
68
|
+
# lambda
|
|
69
|
+
config.environment_properties = -> { { custom_attributes: "foo"} }
|
|
70
|
+
```
|
|
71
|
+
|
|
38
72
|
### Log level
|
|
39
73
|
|
|
40
74
|
Log level can be also configured via environment variable `ALLURE_LOG_LEVEL` which accepts one of the following values: `DEBUG INFO WARN ERROR FATAL UNKNOWN`.
|
|
@@ -54,22 +88,19 @@ Allure.add_attachment(name: "attachment", source: "/path/to/test.txt", type: All
|
|
|
54
88
|
Allure.add_link(name: "Custom Url", url: "http://www.github.com")
|
|
55
89
|
```
|
|
56
90
|
|
|
57
|
-
##
|
|
58
|
-
|
|
59
|
-
Install dependencies:
|
|
91
|
+
## Steps
|
|
60
92
|
|
|
61
|
-
|
|
62
|
-
|
|
63
|
-
```
|
|
64
|
-
|
|
65
|
-
Run tests:
|
|
93
|
+
It is possible to mark method definitions to be automatically added to report as steps. The class just needs to extend `AllureStepAnnotation`
|
|
94
|
+
and `step` method needs to be used before the method definition.
|
|
66
95
|
|
|
67
|
-
```
|
|
68
|
-
|
|
69
|
-
|
|
96
|
+
```ruby
|
|
97
|
+
class TestHelper
|
|
98
|
+
extend AllureStepAnnotation
|
|
70
99
|
|
|
71
|
-
|
|
100
|
+
step("Singleton step")
|
|
101
|
+
def self.class_method; end
|
|
72
102
|
|
|
73
|
-
|
|
74
|
-
|
|
103
|
+
step("Standard step")
|
|
104
|
+
def standard_method; end
|
|
105
|
+
end
|
|
75
106
|
```
|
data/lib/allure-ruby-commons.rb
CHANGED
|
@@ -8,178 +8,240 @@ require_rel "allure_ruby_commons/**/*rb"
|
|
|
8
8
|
|
|
9
9
|
# Namespace for classes that handle allure report generation and different framework adaptors
|
|
10
10
|
module Allure
|
|
11
|
-
|
|
12
|
-
|
|
13
|
-
|
|
14
|
-
|
|
15
|
-
|
|
16
|
-
|
|
11
|
+
# Set lifecycle object
|
|
12
|
+
# @param [AllureLifecycle] lifecycle
|
|
13
|
+
# @return [void]
|
|
14
|
+
def self.lifecycle=(lifecycle)
|
|
15
|
+
Thread.current[:lifecycle] = lifecycle
|
|
16
|
+
end
|
|
17
17
|
|
|
18
|
-
|
|
19
|
-
# @param [AllureLifecycle] lifecycle
|
|
20
|
-
# @return [void]
|
|
21
|
-
def lifecycle=(lifecycle)
|
|
22
|
-
Thread.current[:lifecycle] = lifecycle
|
|
23
|
-
end
|
|
18
|
+
extend self # rubocop:disable Style/ModuleFunction
|
|
24
19
|
|
|
25
|
-
|
|
26
|
-
|
|
27
|
-
|
|
28
|
-
|
|
29
|
-
|
|
20
|
+
# Get thread specific allure lifecycle object
|
|
21
|
+
# @return [AllureLifecycle]
|
|
22
|
+
def lifecycle
|
|
23
|
+
Thread.current[:lifecycle] ||= AllureLifecycle.new
|
|
24
|
+
end
|
|
30
25
|
|
|
31
|
-
|
|
32
|
-
|
|
33
|
-
|
|
34
|
-
|
|
35
|
-
|
|
36
|
-
yield(configuration)
|
|
37
|
-
end
|
|
26
|
+
# Get allure configuration
|
|
27
|
+
# @return [Config]
|
|
28
|
+
def configuration
|
|
29
|
+
Config.instance
|
|
30
|
+
end
|
|
38
31
|
|
|
39
|
-
|
|
40
|
-
|
|
41
|
-
|
|
42
|
-
|
|
43
|
-
|
|
44
|
-
|
|
32
|
+
# Set allure configuration
|
|
33
|
+
# @yieldparam [Config]
|
|
34
|
+
# @yieldreturn [void]
|
|
35
|
+
# @return [void]
|
|
36
|
+
def configure
|
|
37
|
+
yield(configuration)
|
|
38
|
+
end
|
|
45
39
|
|
|
46
|
-
|
|
47
|
-
|
|
48
|
-
|
|
49
|
-
|
|
50
|
-
|
|
51
|
-
|
|
40
|
+
# Add epic to current test case
|
|
41
|
+
# @param [String] value
|
|
42
|
+
# @return [void]
|
|
43
|
+
def epic(value)
|
|
44
|
+
replace_label(ResultUtils::EPIC_LABEL_NAME, value)
|
|
45
|
+
end
|
|
52
46
|
|
|
53
|
-
|
|
54
|
-
|
|
55
|
-
|
|
56
|
-
|
|
57
|
-
|
|
58
|
-
|
|
47
|
+
# Add feature to current test case
|
|
48
|
+
# @param [String] value
|
|
49
|
+
# @return [void]
|
|
50
|
+
def feature(value)
|
|
51
|
+
replace_label(ResultUtils::FEATURE_LABEL_NAME, value)
|
|
52
|
+
end
|
|
59
53
|
|
|
60
|
-
|
|
61
|
-
|
|
62
|
-
|
|
63
|
-
|
|
64
|
-
|
|
65
|
-
|
|
54
|
+
# Add story to current test case
|
|
55
|
+
# @param [String] value
|
|
56
|
+
# @return [void]
|
|
57
|
+
def story(value)
|
|
58
|
+
replace_label(ResultUtils::STORY_LABEL_NAME, value)
|
|
59
|
+
end
|
|
66
60
|
|
|
67
|
-
|
|
68
|
-
|
|
69
|
-
|
|
70
|
-
|
|
71
|
-
|
|
72
|
-
|
|
73
|
-
test_case.labels.push(Label.new(name, value))
|
|
74
|
-
end
|
|
75
|
-
end
|
|
61
|
+
# Add suite to current test case
|
|
62
|
+
# @param [String] value
|
|
63
|
+
# @return [void]
|
|
64
|
+
def suite(value)
|
|
65
|
+
replace_label(ResultUtils::SUITE_LABEL_NAME, value)
|
|
66
|
+
end
|
|
76
67
|
|
|
77
|
-
|
|
78
|
-
|
|
79
|
-
|
|
80
|
-
|
|
81
|
-
|
|
82
|
-
|
|
83
|
-
end
|
|
84
|
-
end
|
|
68
|
+
# Add tag to current test case
|
|
69
|
+
# @param [String] value
|
|
70
|
+
# @return [void]
|
|
71
|
+
def tag(value)
|
|
72
|
+
label(ResultUtils::TAG_LABEL_NAME, value)
|
|
73
|
+
end
|
|
85
74
|
|
|
86
|
-
|
|
87
|
-
|
|
88
|
-
|
|
89
|
-
|
|
90
|
-
|
|
91
|
-
|
|
92
|
-
|
|
75
|
+
# Add label to current test case
|
|
76
|
+
# @param [String] name
|
|
77
|
+
# @param [String] value
|
|
78
|
+
# @return [void]
|
|
79
|
+
def label(name, value)
|
|
80
|
+
lifecycle.update_test_case do |test_case|
|
|
81
|
+
test_case.labels.push(Label.new(name, value))
|
|
93
82
|
end
|
|
83
|
+
end
|
|
94
84
|
|
|
95
|
-
|
|
96
|
-
|
|
97
|
-
|
|
98
|
-
|
|
99
|
-
|
|
100
|
-
|
|
101
|
-
|
|
102
|
-
|
|
85
|
+
# Replace label in current test case
|
|
86
|
+
#
|
|
87
|
+
# @param [String] name
|
|
88
|
+
# @param [String] value
|
|
89
|
+
# @return [void]
|
|
90
|
+
def replace_label(name, value)
|
|
91
|
+
lifecycle.update_test_case do |test_case|
|
|
92
|
+
present = test_case.labels.detect { |l| l.name == name }
|
|
93
|
+
return label(name, value) unless present
|
|
94
|
+
|
|
95
|
+
test_case.labels.map! { |l| l.name == name ? Label.new(name, value) : l }
|
|
103
96
|
end
|
|
97
|
+
end
|
|
104
98
|
|
|
105
|
-
|
|
106
|
-
|
|
107
|
-
|
|
108
|
-
|
|
109
|
-
|
|
110
|
-
|
|
99
|
+
# Add description to current test case
|
|
100
|
+
# @param [String] description
|
|
101
|
+
# @return [void]
|
|
102
|
+
def add_description(description)
|
|
103
|
+
lifecycle.update_test_case do |test_case|
|
|
104
|
+
test_case.description = description
|
|
111
105
|
end
|
|
106
|
+
end
|
|
112
107
|
|
|
113
|
-
|
|
114
|
-
|
|
115
|
-
|
|
116
|
-
|
|
117
|
-
|
|
118
|
-
|
|
108
|
+
# Add html description to current test case
|
|
109
|
+
# @param [String] description_html
|
|
110
|
+
# @return [void]
|
|
111
|
+
def description_html(description_html)
|
|
112
|
+
lifecycle.update_test_case do |test_case|
|
|
113
|
+
test_case.description_html = description_html
|
|
119
114
|
end
|
|
115
|
+
end
|
|
120
116
|
|
|
121
|
-
|
|
122
|
-
|
|
123
|
-
|
|
124
|
-
|
|
125
|
-
|
|
126
|
-
|
|
127
|
-
|
|
128
|
-
test_case.links.push(Link.new(type, name || url, url))
|
|
129
|
-
end
|
|
117
|
+
# Add parameter to current test case
|
|
118
|
+
# @param [String] name
|
|
119
|
+
# @param [String] value
|
|
120
|
+
# @return [void]
|
|
121
|
+
def parameter(name, value)
|
|
122
|
+
lifecycle.update_test_case do |test_case|
|
|
123
|
+
test_case.parameters.push(Parameter.new(name, value))
|
|
130
124
|
end
|
|
125
|
+
end
|
|
131
126
|
|
|
132
|
-
|
|
133
|
-
|
|
134
|
-
|
|
135
|
-
|
|
136
|
-
|
|
137
|
-
|
|
138
|
-
|
|
139
|
-
|
|
127
|
+
# Add tms link to current test case
|
|
128
|
+
# @param [String] name
|
|
129
|
+
# @param [String] url
|
|
130
|
+
# @return [void]
|
|
131
|
+
def tms(name, url)
|
|
132
|
+
add_link(name: name, url: url, type: ResultUtils::TMS_LINK_TYPE)
|
|
133
|
+
end
|
|
134
|
+
|
|
135
|
+
# Add issue linkt to current test case
|
|
136
|
+
# @param [String] name
|
|
137
|
+
# @param [String] url
|
|
138
|
+
# @return [void]
|
|
139
|
+
def issue(name, url)
|
|
140
|
+
add_link(name: name, url: url, type: ResultUtils::ISSUE_LINK_TYPE)
|
|
141
|
+
end
|
|
142
|
+
|
|
143
|
+
# Add link to current test case
|
|
144
|
+
# @param [String ] url
|
|
145
|
+
# @param [String] name
|
|
146
|
+
# @param [String] type type of the link used to display link icon
|
|
147
|
+
# @return [void]
|
|
148
|
+
def add_link(url:, name: nil, type: "custom")
|
|
149
|
+
lifecycle.update_test_case do |test_case|
|
|
150
|
+
test_case.links.push(Link.new(type, name || url, url))
|
|
140
151
|
end
|
|
152
|
+
end
|
|
141
153
|
|
|
142
|
-
|
|
143
|
-
|
|
144
|
-
|
|
145
|
-
|
|
146
|
-
|
|
154
|
+
# Add attachment to current test case or step
|
|
155
|
+
# @param [String] name Attachment name
|
|
156
|
+
# @param [File, String] source File or string to save as attachment
|
|
157
|
+
# @param [String] type attachment type defined in {ContentType} or any other valid mime type
|
|
158
|
+
# @param [Boolean] test_case add attachment to current test case instead of test step
|
|
159
|
+
# @return [void]
|
|
160
|
+
def add_attachment(name:, source:, type:, test_case: false)
|
|
161
|
+
lifecycle.add_attachment(name: name, source: source, type: type, test_case: test_case)
|
|
162
|
+
end
|
|
163
|
+
|
|
164
|
+
# Manually create environment.properties file
|
|
165
|
+
# if this method is called before test run started and
|
|
166
|
+
# option clean_results_directory is enabled, the file will be deleted
|
|
167
|
+
# @param [Hash<Symbol, String>, Proc] environment
|
|
168
|
+
# @return [void]
|
|
169
|
+
def add_environment(environment)
|
|
170
|
+
lifecycle.write_environment(environment)
|
|
171
|
+
end
|
|
172
|
+
|
|
173
|
+
# Manually create categories.json file
|
|
174
|
+
# if this method is called before test run started and
|
|
175
|
+
# option clean_results_directory is enabled, the file will be deleted
|
|
176
|
+
# @param [File, Array<Category>] categories
|
|
177
|
+
# @return [void]
|
|
178
|
+
def add_categories(categories)
|
|
179
|
+
lifecycle.write_categories(categories)
|
|
180
|
+
end
|
|
181
|
+
|
|
182
|
+
# Set test case status detail to flaky
|
|
183
|
+
#
|
|
184
|
+
# @return [void]
|
|
185
|
+
def set_flaky
|
|
186
|
+
lifecycle.update_test_case do |test_case|
|
|
187
|
+
test_case.status_details.flaky = true
|
|
147
188
|
end
|
|
189
|
+
end
|
|
148
190
|
|
|
149
|
-
|
|
150
|
-
|
|
151
|
-
|
|
152
|
-
|
|
153
|
-
|
|
191
|
+
# Set test case status detail to muted
|
|
192
|
+
#
|
|
193
|
+
# @return [void]
|
|
194
|
+
def set_muted
|
|
195
|
+
lifecycle.update_test_case do |test_case|
|
|
196
|
+
test_case.status_details.muted = true
|
|
154
197
|
end
|
|
198
|
+
end
|
|
155
199
|
|
|
156
|
-
|
|
157
|
-
|
|
158
|
-
|
|
159
|
-
|
|
160
|
-
|
|
161
|
-
|
|
162
|
-
lifecycle.stop_test_step
|
|
200
|
+
# Set test case status detail to known
|
|
201
|
+
#
|
|
202
|
+
# @return [void]
|
|
203
|
+
def set_known
|
|
204
|
+
lifecycle.update_test_case do |test_case|
|
|
205
|
+
test_case.status_details.known = true
|
|
163
206
|
end
|
|
207
|
+
end
|
|
208
|
+
|
|
209
|
+
# Add step with provided name and optional status to current test step, fixture or test case
|
|
210
|
+
# @param [String] name
|
|
211
|
+
# @param [Symbol] status {Status}, {Status::PASSED} by default
|
|
212
|
+
# @return [void]
|
|
213
|
+
def step(name:, status: nil)
|
|
214
|
+
lifecycle.add_test_step(StepResult.new(name: name, status: status || Status::PASSED, stage: Stage::FINISHED))
|
|
215
|
+
lifecycle.stop_test_step
|
|
216
|
+
end
|
|
217
|
+
|
|
218
|
+
# Run passed block as step with given name and return result of yield
|
|
219
|
+
# @param [String] name
|
|
220
|
+
# @yield [] step block
|
|
221
|
+
# @return [Object]
|
|
222
|
+
def run_step(name)
|
|
223
|
+
lifecycle.start_test_step(StepResult.new(name: name, stage: Stage::RUNNING))
|
|
224
|
+
result = yield
|
|
225
|
+
lifecycle.update_test_step { |step| step.status = Status::PASSED }
|
|
226
|
+
|
|
227
|
+
result
|
|
228
|
+
rescue StandardError => e
|
|
229
|
+
lifecycle.update_test_step do |step|
|
|
230
|
+
step.status = ResultUtils.status(e)
|
|
231
|
+
step.status_details = ResultUtils.status_details(e)
|
|
232
|
+
end
|
|
233
|
+
raise(e)
|
|
234
|
+
ensure
|
|
235
|
+
lifecycle.stop_test_step
|
|
236
|
+
end
|
|
164
237
|
|
|
165
|
-
|
|
166
|
-
|
|
167
|
-
|
|
168
|
-
|
|
169
|
-
|
|
170
|
-
|
|
171
|
-
|
|
172
|
-
lifecycle.update_test_step { |step| step.status = Status::PASSED }
|
|
173
|
-
|
|
174
|
-
result
|
|
175
|
-
rescue StandardError => e
|
|
176
|
-
lifecycle.update_test_step do |step|
|
|
177
|
-
step.status = ResultUtils.status(e)
|
|
178
|
-
step.status_details = ResultUtils.status_details(e)
|
|
179
|
-
end
|
|
180
|
-
raise(e)
|
|
181
|
-
ensure
|
|
182
|
-
lifecycle.stop_test_step
|
|
238
|
+
# Add parameter to current test step
|
|
239
|
+
# @param [String] name
|
|
240
|
+
# @param [String] value
|
|
241
|
+
# @return [void]
|
|
242
|
+
def step_parameter(name, value)
|
|
243
|
+
lifecycle.update_test_step do |step|
|
|
244
|
+
step.parameters.push(Parameter.new(name, value))
|
|
183
245
|
end
|
|
184
246
|
end
|
|
185
247
|
end
|
|
@@ -8,14 +8,19 @@ module Allure
|
|
|
8
8
|
class AllureLifecycle # rubocop:disable Metrics/ClassLength
|
|
9
9
|
extend Forwardable
|
|
10
10
|
|
|
11
|
-
|
|
11
|
+
# Allure lifecycle instance
|
|
12
|
+
#
|
|
13
|
+
# @param [Allure::Config] configuration
|
|
14
|
+
def initialize(config = Config.instance)
|
|
12
15
|
@test_context = []
|
|
13
16
|
@step_context = []
|
|
14
|
-
@
|
|
15
|
-
@
|
|
17
|
+
@config = config
|
|
18
|
+
@logger = config.logger
|
|
16
19
|
end
|
|
17
20
|
|
|
18
|
-
|
|
21
|
+
attr_reader :config
|
|
22
|
+
|
|
23
|
+
def_delegators :file_writer, :write_attachment
|
|
19
24
|
|
|
20
25
|
# Start test result container
|
|
21
26
|
# @param [Allure::TestResultContainer] test_result_container
|
|
@@ -215,6 +220,27 @@ module Allure
|
|
|
215
220
|
write_attachment(source, attachment)
|
|
216
221
|
end
|
|
217
222
|
|
|
223
|
+
# Add environment.properties file
|
|
224
|
+
#
|
|
225
|
+
# @param [Hash, Proc] env
|
|
226
|
+
# @return [void]
|
|
227
|
+
def write_environment(env = config.environment_properties)
|
|
228
|
+
return unless env
|
|
229
|
+
|
|
230
|
+
env_properties = env.respond_to?(:call) ? env.call : env
|
|
231
|
+
file_writer.write_environment(env_properties)
|
|
232
|
+
end
|
|
233
|
+
|
|
234
|
+
# Add categories.json
|
|
235
|
+
#
|
|
236
|
+
# @param [File, Array<Category>] categories
|
|
237
|
+
# @return [void]
|
|
238
|
+
def write_categories(categories = config.categories)
|
|
239
|
+
return unless categories
|
|
240
|
+
|
|
241
|
+
file_writer.write_categories(categories)
|
|
242
|
+
end
|
|
243
|
+
|
|
218
244
|
# Add step to current fixture|step|test case
|
|
219
245
|
# @param [Allure::StepResult] step_result
|
|
220
246
|
# @return [Allure::StepResult]
|
|
@@ -227,14 +253,16 @@ module Allure
|
|
|
227
253
|
# Clean results directory
|
|
228
254
|
# @return [void]
|
|
229
255
|
def clean_results_dir
|
|
230
|
-
|
|
231
|
-
FileUtils.rm_f(Dir.glob("#{c.results_directory}/**/*")) if c.clean_results_directory
|
|
232
|
-
end
|
|
256
|
+
FileUtils.rm_f(Dir.glob("#{config.results_directory}/**/*")) if config.clean_results_directory
|
|
233
257
|
end
|
|
234
258
|
|
|
235
259
|
private
|
|
236
260
|
|
|
237
|
-
|
|
261
|
+
attr_reader :logger
|
|
262
|
+
|
|
263
|
+
def file_writer
|
|
264
|
+
@file_writer ||= FileWriter.new(config.results_directory)
|
|
265
|
+
end
|
|
238
266
|
|
|
239
267
|
def current_executable
|
|
240
268
|
current_test_step || @current_fixture || @current_test_case
|
|
@@ -10,41 +10,36 @@ module Allure
|
|
|
10
10
|
|
|
11
11
|
# @return [Array<String>] valid log levels
|
|
12
12
|
LOGLEVELS = %w[DEBUG INFO WARN ERROR FATAL UNKNOWN].freeze
|
|
13
|
-
# @return [String] test plan path env var name
|
|
14
|
-
TESTPLAN_PATH = "ALLURE_TESTPLAN_PATH"
|
|
15
13
|
|
|
16
|
-
|
|
14
|
+
attr_writer :environment, :logger
|
|
15
|
+
|
|
16
|
+
attr_accessor :results_directory,
|
|
17
|
+
:logging_level,
|
|
18
|
+
:link_tms_pattern,
|
|
19
|
+
:link_issue_pattern,
|
|
20
|
+
:clean_results_directory,
|
|
21
|
+
:environment_properties,
|
|
22
|
+
:categories
|
|
17
23
|
|
|
18
24
|
def initialize
|
|
19
25
|
@results_directory = "reports/allure-results"
|
|
20
26
|
@logging_level = LOGLEVELS.index(ENV.fetch("ALLURE_LOG_LEVEL", "INFO")) || Logger::INFO
|
|
21
27
|
end
|
|
22
28
|
|
|
23
|
-
# Allure
|
|
29
|
+
# Allure environment
|
|
24
30
|
#
|
|
25
|
-
# @return [
|
|
26
|
-
def
|
|
27
|
-
@
|
|
28
|
-
end
|
|
31
|
+
# @return [String]
|
|
32
|
+
def environment
|
|
33
|
+
return(@environment) if defined?(@environment)
|
|
29
34
|
|
|
30
|
-
|
|
31
|
-
#
|
|
32
|
-
# @return [Array]
|
|
33
|
-
def test_names
|
|
34
|
-
@test_names ||= tests&.map { |test| test[:selector] }
|
|
35
|
+
@environment ||= ENV["ALLURE_ENVIRONMENT"]
|
|
35
36
|
end
|
|
36
37
|
|
|
37
|
-
|
|
38
|
-
|
|
39
|
-
# Tests to execute from allure testplan.json
|
|
38
|
+
# Logger instance
|
|
40
39
|
#
|
|
41
|
-
# @return [
|
|
42
|
-
def
|
|
43
|
-
@
|
|
44
|
-
Oj.load_file(ENV[TESTPLAN_PATH], symbol_keys: true)&.fetch(:tests) if ENV[TESTPLAN_PATH]
|
|
45
|
-
end
|
|
46
|
-
rescue Oj::ParseError
|
|
47
|
-
nil
|
|
40
|
+
# @return [Logger]
|
|
41
|
+
def logger
|
|
42
|
+
@logger ||= Logger.new($stdout, level: logging_level)
|
|
48
43
|
end
|
|
49
44
|
end
|
|
50
45
|
end
|
|
@@ -13,19 +13,28 @@ module Allure
|
|
|
13
13
|
ENVIRONMENT_FILE = "environment.properties"
|
|
14
14
|
# @return [String] categories definition json
|
|
15
15
|
CATEGORIES_FILE = "categories.json"
|
|
16
|
+
# @return [Hash] Oj json options
|
|
17
|
+
OJ_OPTIONS = { mode: :custom, use_to_hash: true, ascii_only: true }.freeze
|
|
18
|
+
|
|
19
|
+
# File writer instance
|
|
20
|
+
#
|
|
21
|
+
# @param [String] results_directory
|
|
22
|
+
def initialize(results_directory)
|
|
23
|
+
@results_directory = results_directory
|
|
24
|
+
end
|
|
16
25
|
|
|
17
26
|
# Write test result
|
|
18
27
|
# @param [Allure::TestResult] test_result
|
|
19
28
|
# @return [void]
|
|
20
29
|
def write_test_result(test_result)
|
|
21
|
-
write("#{test_result.uuid}#{TEST_RESULT_SUFFIX}", Oj.dump(test_result))
|
|
30
|
+
write("#{test_result.uuid}#{TEST_RESULT_SUFFIX}", Oj.dump(test_result, OJ_OPTIONS))
|
|
22
31
|
end
|
|
23
32
|
|
|
24
33
|
# Write test result container
|
|
25
34
|
# @param [Allure::TestResultContainer] test_container_result
|
|
26
35
|
# @return [void]
|
|
27
36
|
def write_test_result_container(test_container_result)
|
|
28
|
-
write("#{test_container_result.uuid}#{TEST_RESULT_CONTAINER_SUFFIX}", Oj.dump(test_container_result))
|
|
37
|
+
write("#{test_container_result.uuid}#{TEST_RESULT_CONTAINER_SUFFIX}", Oj.dump(test_container_result, OJ_OPTIONS))
|
|
29
38
|
end
|
|
30
39
|
|
|
31
40
|
# Write allure attachment file
|
|
@@ -52,19 +61,21 @@ module Allure
|
|
|
52
61
|
if categories.is_a?(File)
|
|
53
62
|
copy(categories.path, CATEGORIES_FILE)
|
|
54
63
|
else
|
|
55
|
-
write(CATEGORIES_FILE, Oj.dump(categories))
|
|
64
|
+
write(CATEGORIES_FILE, Oj.dump(categories, OJ_OPTIONS))
|
|
56
65
|
end
|
|
57
66
|
end
|
|
58
67
|
|
|
59
68
|
private
|
|
60
69
|
|
|
70
|
+
attr_reader :results_directory
|
|
71
|
+
|
|
61
72
|
def output_dir
|
|
62
|
-
@output_dir ||= FileUtils.mkpath(
|
|
73
|
+
@output_dir ||= FileUtils.mkpath(results_directory).first
|
|
63
74
|
end
|
|
64
75
|
|
|
65
76
|
def write(name, source)
|
|
66
77
|
filename = File.join(output_dir, name)
|
|
67
|
-
File.
|
|
78
|
+
File.write(filename, source)
|
|
68
79
|
end
|
|
69
80
|
|
|
70
81
|
def copy(from, to)
|
|
@@ -27,9 +27,16 @@ module Allure
|
|
|
27
27
|
@parameters = options[:parameters] || []
|
|
28
28
|
end
|
|
29
29
|
|
|
30
|
-
attr_accessor
|
|
31
|
-
|
|
32
|
-
|
|
33
|
-
|
|
30
|
+
attr_accessor :name,
|
|
31
|
+
:status,
|
|
32
|
+
:status_details,
|
|
33
|
+
:stage,
|
|
34
|
+
:description,
|
|
35
|
+
:description_html,
|
|
36
|
+
:steps,
|
|
37
|
+
:attachments,
|
|
38
|
+
:parameters,
|
|
39
|
+
:start,
|
|
40
|
+
:stop
|
|
34
41
|
end
|
|
35
42
|
end
|
|
@@ -5,6 +5,7 @@ module Allure
|
|
|
5
5
|
class TestResult < ExecutableItem
|
|
6
6
|
# @param [String] uuid
|
|
7
7
|
# @param [String] history_id
|
|
8
|
+
# @param [String] environment
|
|
8
9
|
# @param [Hash] options
|
|
9
10
|
# @option options [String] :name
|
|
10
11
|
# @option options [String] :full_name
|
|
@@ -18,15 +19,22 @@ module Allure
|
|
|
18
19
|
# @option options [Array<Allure::Link>] :links ([])
|
|
19
20
|
# @option options [Array<Allure::Attachment>] :attachments ([])
|
|
20
21
|
# @option options [Array<Allure::Parameter>] :parameters ([])
|
|
21
|
-
def initialize(uuid: UUID.generate, history_id: UUID.generate, **options)
|
|
22
|
+
def initialize(uuid: UUID.generate, history_id: UUID.generate, environment: nil, **options)
|
|
22
23
|
super
|
|
24
|
+
|
|
25
|
+
@name = options[:name]
|
|
23
26
|
@uuid = uuid
|
|
24
|
-
@history_id = history_id
|
|
27
|
+
@history_id = Digest::MD5.hexdigest("#{history_id}#{environment}")
|
|
25
28
|
@full_name = options[:full_name] || "Unnamed"
|
|
26
29
|
@labels = options[:labels] || []
|
|
27
30
|
@links = options[:links] || []
|
|
31
|
+
@parameters << Parameter.new("environment", environment) if environment
|
|
28
32
|
end
|
|
29
33
|
|
|
30
|
-
attr_accessor :uuid,
|
|
34
|
+
attr_accessor :uuid,
|
|
35
|
+
:history_id,
|
|
36
|
+
:full_name,
|
|
37
|
+
:labels,
|
|
38
|
+
:links
|
|
31
39
|
end
|
|
32
40
|
end
|
|
@@ -1,6 +1,7 @@
|
|
|
1
1
|
# frozen_string_literal: true
|
|
2
2
|
|
|
3
3
|
require "socket"
|
|
4
|
+
require "uri"
|
|
4
5
|
|
|
5
6
|
module Allure
|
|
6
7
|
# Variouse helper methods
|
|
@@ -59,6 +60,13 @@ module Allure
|
|
|
59
60
|
Label.new(FRAMEWORK_LABEL_NAME, value)
|
|
60
61
|
end
|
|
61
62
|
|
|
63
|
+
# Epic label
|
|
64
|
+
# @param [String] value
|
|
65
|
+
# @return [Allure::Label]
|
|
66
|
+
def epic_label(value)
|
|
67
|
+
Label.new(EPIC_LABEL_NAME, value)
|
|
68
|
+
end
|
|
69
|
+
|
|
62
70
|
# Feature label
|
|
63
71
|
# @param [String] value
|
|
64
72
|
# @return [Allure::Label]
|
|
@@ -66,6 +74,13 @@ module Allure
|
|
|
66
74
|
Label.new(FEATURE_LABEL_NAME, value)
|
|
67
75
|
end
|
|
68
76
|
|
|
77
|
+
# Story label
|
|
78
|
+
# @param [String] value
|
|
79
|
+
# @return [Allure::Label]
|
|
80
|
+
def story_label(value)
|
|
81
|
+
Label.new(STORY_LABEL_NAME, value)
|
|
82
|
+
end
|
|
83
|
+
|
|
69
84
|
# Package label
|
|
70
85
|
# @param [String] value
|
|
71
86
|
# @return [Allure::Label]
|
|
@@ -94,13 +109,6 @@ module Allure
|
|
|
94
109
|
Label.new(SUB_SUITE_LABEL_NAME, value)
|
|
95
110
|
end
|
|
96
111
|
|
|
97
|
-
# Story label
|
|
98
|
-
# @param [String] value
|
|
99
|
-
# @return [Allure::Label]
|
|
100
|
-
def story_label(value)
|
|
101
|
-
Label.new(STORY_LABEL_NAME, value)
|
|
102
|
-
end
|
|
103
|
-
|
|
104
112
|
# Test case label
|
|
105
113
|
# @param [String] value
|
|
106
114
|
# @return [Allure::Label]
|
|
@@ -124,16 +132,20 @@ module Allure
|
|
|
124
132
|
|
|
125
133
|
# TMS link
|
|
126
134
|
# @param [String] value
|
|
135
|
+
# @param [String] link_pattern
|
|
127
136
|
# @return [Allure::Link]
|
|
128
|
-
def tms_link(value)
|
|
129
|
-
|
|
137
|
+
def tms_link(name, value, link_pattern)
|
|
138
|
+
link_name = url?(value) ? name : value
|
|
139
|
+
Link.new(TMS_LINK_TYPE, link_name, url(value, link_pattern))
|
|
130
140
|
end
|
|
131
141
|
|
|
132
142
|
# Issue link
|
|
133
143
|
# @param [String] value
|
|
144
|
+
# @param [String] link_pattern
|
|
134
145
|
# @return [Allure::Link]
|
|
135
|
-
def issue_link(value)
|
|
136
|
-
|
|
146
|
+
def issue_link(name, value, link_pattern)
|
|
147
|
+
link_name = url?(value) ? name : value
|
|
148
|
+
Link.new(ISSUE_LINK_TYPE, link_name, url(value, link_pattern))
|
|
137
149
|
end
|
|
138
150
|
|
|
139
151
|
# Get status based on exception type
|
|
@@ -162,12 +174,21 @@ module Allure
|
|
|
162
174
|
|
|
163
175
|
private
|
|
164
176
|
|
|
165
|
-
|
|
166
|
-
|
|
177
|
+
# Check if value is full url
|
|
178
|
+
#
|
|
179
|
+
# @param [String] value
|
|
180
|
+
# @return [Boolean]
|
|
181
|
+
def url?(value)
|
|
182
|
+
URI.parse(value.to_s).scheme
|
|
167
183
|
end
|
|
168
184
|
|
|
169
|
-
|
|
170
|
-
|
|
185
|
+
# Construct url from pattern
|
|
186
|
+
#
|
|
187
|
+
# @param [String] value
|
|
188
|
+
# @param [String] link_pattern
|
|
189
|
+
# @return [String]
|
|
190
|
+
def url(value, link_pattern)
|
|
191
|
+
link_pattern.sub("{}", value)
|
|
171
192
|
end
|
|
172
193
|
end
|
|
173
194
|
end
|
|
@@ -0,0 +1,39 @@
|
|
|
1
|
+
# frozen_string_literal: true
|
|
2
|
+
|
|
3
|
+
# Adds support for annotating methods as allure steps
|
|
4
|
+
#
|
|
5
|
+
module AllureStepAnnotation
|
|
6
|
+
# Mark method definition as allure step
|
|
7
|
+
#
|
|
8
|
+
# @param [String] step_name
|
|
9
|
+
# @return [void]
|
|
10
|
+
def step(step_name = "")
|
|
11
|
+
@allure_step = step_name
|
|
12
|
+
end
|
|
13
|
+
|
|
14
|
+
private
|
|
15
|
+
|
|
16
|
+
def singleton_method_added(method_name)
|
|
17
|
+
return super unless @allure_step
|
|
18
|
+
|
|
19
|
+
original_method = singleton_method(method_name)
|
|
20
|
+
step_name = @allure_step.empty? ? method_name.to_s : @allure_step
|
|
21
|
+
@allure_step = nil
|
|
22
|
+
|
|
23
|
+
define_singleton_method(method_name) do |*args, &block|
|
|
24
|
+
Allure.run_step(step_name) { original_method.call(*args, &block) }
|
|
25
|
+
end
|
|
26
|
+
end
|
|
27
|
+
|
|
28
|
+
def method_added(method_name)
|
|
29
|
+
return super unless @allure_step
|
|
30
|
+
|
|
31
|
+
original_method = instance_method(method_name)
|
|
32
|
+
step_name = @allure_step.empty? ? method_name.to_s : @allure_step
|
|
33
|
+
@allure_step = nil
|
|
34
|
+
|
|
35
|
+
define_method(method_name) do |*args, &block|
|
|
36
|
+
Allure.run_step(step_name) { original_method.bind_call(self, *args, &block) }
|
|
37
|
+
end
|
|
38
|
+
end
|
|
39
|
+
end
|
|
@@ -0,0 +1,35 @@
|
|
|
1
|
+
# frozen_string_literal: true
|
|
2
|
+
|
|
3
|
+
module Allure
|
|
4
|
+
class TestPlan
|
|
5
|
+
# @return [String] test plan path env var name
|
|
6
|
+
TESTPLAN_PATH = "ALLURE_TESTPLAN_PATH"
|
|
7
|
+
|
|
8
|
+
class << self
|
|
9
|
+
# Allure id's of executable tests
|
|
10
|
+
#
|
|
11
|
+
# @return [Array]
|
|
12
|
+
def test_ids
|
|
13
|
+
@test_ids ||= tests&.map { |test| test[:id] }
|
|
14
|
+
end
|
|
15
|
+
|
|
16
|
+
# Test names of executable tests
|
|
17
|
+
#
|
|
18
|
+
# @return [Array]
|
|
19
|
+
def test_names
|
|
20
|
+
@test_names ||= tests&.map { |test| test[:selector] }
|
|
21
|
+
end
|
|
22
|
+
|
|
23
|
+
private
|
|
24
|
+
|
|
25
|
+
# Tests to execute from allure testplan.json
|
|
26
|
+
#
|
|
27
|
+
# @return [Array<Hash>]
|
|
28
|
+
def tests
|
|
29
|
+
@tests ||= Oj.load_file(ENV[TESTPLAN_PATH], symbol_keys: true)&.fetch(:tests) if ENV[TESTPLAN_PATH]
|
|
30
|
+
rescue Oj::ParseError
|
|
31
|
+
nil
|
|
32
|
+
end
|
|
33
|
+
end
|
|
34
|
+
end
|
|
35
|
+
end
|
metadata
CHANGED
|
@@ -1,14 +1,14 @@
|
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
|
2
2
|
name: allure-ruby-commons
|
|
3
3
|
version: !ruby/object:Gem::Version
|
|
4
|
-
version: 2.
|
|
4
|
+
version: 2.19.0
|
|
5
5
|
platform: ruby
|
|
6
6
|
authors:
|
|
7
7
|
- Andrejs Cunskis
|
|
8
8
|
autorequire:
|
|
9
9
|
bindir: bin
|
|
10
10
|
cert_chain: []
|
|
11
|
-
date:
|
|
11
|
+
date: 2022-11-08 00:00:00.000000000 Z
|
|
12
12
|
dependencies:
|
|
13
13
|
- !ruby/object:Gem::Dependency
|
|
14
14
|
name: mime-types
|
|
@@ -118,6 +118,8 @@ files:
|
|
|
118
118
|
- lib/allure_ruby_commons/model/test_result.rb
|
|
119
119
|
- lib/allure_ruby_commons/model/test_result_container.rb
|
|
120
120
|
- lib/allure_ruby_commons/result_utils.rb
|
|
121
|
+
- lib/allure_ruby_commons/step_annotation.rb
|
|
122
|
+
- lib/allure_ruby_commons/testplan.rb
|
|
121
123
|
homepage: https://github.com/allure-framework/allure-ruby
|
|
122
124
|
licenses:
|
|
123
125
|
- Apache-2.0
|
|
@@ -127,6 +129,7 @@ metadata:
|
|
|
127
129
|
documentation_uri: https://github.com/allure-framework/allure-ruby/blob/master/allure-ruby-commons/README.md
|
|
128
130
|
source_code_uri: https://github.com/allure-framework/allure-ruby/tree/master/allure-ruby-commons
|
|
129
131
|
wiki_uri: https://github.com/allure-framework/allure-ruby/wiki
|
|
132
|
+
rubygems_mfa_required: 'false'
|
|
130
133
|
post_install_message:
|
|
131
134
|
rdoc_options: []
|
|
132
135
|
require_paths:
|
|
@@ -135,14 +138,14 @@ required_ruby_version: !ruby/object:Gem::Requirement
|
|
|
135
138
|
requirements:
|
|
136
139
|
- - ">="
|
|
137
140
|
- !ruby/object:Gem::Version
|
|
138
|
-
version: 2.
|
|
141
|
+
version: 2.7.0
|
|
139
142
|
required_rubygems_version: !ruby/object:Gem::Requirement
|
|
140
143
|
requirements:
|
|
141
144
|
- - ">="
|
|
142
145
|
- !ruby/object:Gem::Version
|
|
143
146
|
version: '0'
|
|
144
147
|
requirements: []
|
|
145
|
-
rubygems_version: 3.
|
|
148
|
+
rubygems_version: 3.3.7
|
|
146
149
|
signing_key:
|
|
147
150
|
specification_version: 4
|
|
148
151
|
summary: Common library for allure results generation
|