xcpretty-security-patched 0.3.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.
Files changed (75) hide show
  1. checksums.yaml +7 -0
  2. data/.gitignore +19 -0
  3. data/.hound.yml +2 -0
  4. data/.kick +17 -0
  5. data/.rubocop.yml +239 -0
  6. data/.travis.yml +12 -0
  7. data/CHANGELOG.md +269 -0
  8. data/CONTRIBUTING.md +64 -0
  9. data/Gemfile +9 -0
  10. data/LICENSE.txt +61 -0
  11. data/README.md +95 -0
  12. data/Rakefile +18 -0
  13. data/assets/report.html.erb +173 -0
  14. data/bin/xcpretty +90 -0
  15. data/features/assets/RACCommandSpec_enabled_signal_should_send_YES_while_executing_is_YES.png +0 -0
  16. data/features/assets/apple_raw.png +0 -0
  17. data/features/custom_formatter.feature +15 -0
  18. data/features/custom_reporter.feature +29 -0
  19. data/features/fixtures/xcodebuild.log +5963 -0
  20. data/features/html_report.feature +54 -0
  21. data/features/json_compilation_database_report.feature +33 -0
  22. data/features/junit_report.feature +49 -0
  23. data/features/knock_format.feature +11 -0
  24. data/features/simple_format.feature +238 -0
  25. data/features/steps/custom_reporter_steps.rb +16 -0
  26. data/features/steps/formatting_steps.rb +386 -0
  27. data/features/steps/html_steps.rb +32 -0
  28. data/features/steps/json_steps.rb +45 -0
  29. data/features/steps/junit_steps.rb +39 -0
  30. data/features/steps/report_steps.rb +27 -0
  31. data/features/steps/xcpretty_steps.rb +31 -0
  32. data/features/support/env.rb +123 -0
  33. data/features/tap_format.feature +31 -0
  34. data/features/test_format.feature +49 -0
  35. data/features/xcpretty.feature +14 -0
  36. data/lib/xcpretty/ansi.rb +72 -0
  37. data/lib/xcpretty/formatters/formatter.rb +200 -0
  38. data/lib/xcpretty/formatters/knock.rb +35 -0
  39. data/lib/xcpretty/formatters/rspec.rb +33 -0
  40. data/lib/xcpretty/formatters/simple.rb +200 -0
  41. data/lib/xcpretty/formatters/tap.rb +40 -0
  42. data/lib/xcpretty/parser.rb +596 -0
  43. data/lib/xcpretty/printer.rb +28 -0
  44. data/lib/xcpretty/reporters/html.rb +93 -0
  45. data/lib/xcpretty/reporters/json_compilation_database.rb +51 -0
  46. data/lib/xcpretty/reporters/junit.rb +102 -0
  47. data/lib/xcpretty/reporters/reporter.rb +62 -0
  48. data/lib/xcpretty/snippet.rb +38 -0
  49. data/lib/xcpretty/syntax.rb +58 -0
  50. data/lib/xcpretty/term.rb +14 -0
  51. data/lib/xcpretty/version.rb +4 -0
  52. data/lib/xcpretty.rb +38 -0
  53. data/spec/fixtures/NSStringTests.m +64 -0
  54. data/spec/fixtures/constants.rb +707 -0
  55. data/spec/fixtures/custom_formatter.rb +18 -0
  56. data/spec/fixtures/custom_reporter.rb +30 -0
  57. data/spec/fixtures/oneliner.m +1 -0
  58. data/spec/fixtures/raw_kiwi_compilation_fail.txt +24 -0
  59. data/spec/fixtures/raw_kiwi_fail.txt +1896 -0
  60. data/spec/fixtures/raw_specta_fail.txt +3110 -0
  61. data/spec/spec_helper.rb +7 -0
  62. data/spec/support/matchers/colors.rb +21 -0
  63. data/spec/xcpretty/ansi_spec.rb +47 -0
  64. data/spec/xcpretty/formatters/formatter_spec.rb +151 -0
  65. data/spec/xcpretty/formatters/rspec_spec.rb +56 -0
  66. data/spec/xcpretty/formatters/simple_spec.rb +178 -0
  67. data/spec/xcpretty/parser_spec.rb +636 -0
  68. data/spec/xcpretty/printer_spec.rb +55 -0
  69. data/spec/xcpretty/reporters/junit_spec.rb +20 -0
  70. data/spec/xcpretty/reporters/reporter_spec.rb +40 -0
  71. data/spec/xcpretty/snippet_spec.rb +46 -0
  72. data/spec/xcpretty/syntax_spec.rb +39 -0
  73. data/spec/xcpretty/term_spec.rb +26 -0
  74. data/xcpretty.gemspec +37 -0
  75. metadata +250 -0
@@ -0,0 +1,386 @@
1
+ # encoding: utf-8
2
+ Given(/^I have a file to compile$/) do
3
+ add_run_input SAMPLE_COMPILE
4
+ end
5
+
6
+ Given(/^I have a file to compile with ccache$/) do
7
+ add_run_input SAMPLE_COMPILE_CCACHE
8
+ end
9
+
10
+ Given(/^I have a xib to compile$/) do
11
+ add_run_input SAMPLE_COMPILE_XIB
12
+ end
13
+
14
+ Given(/^I have a storyboard to compile$/) do
15
+ add_run_input SAMPLE_COMPILE_STORYBOARD
16
+ end
17
+
18
+ Given(/^I have a precompiled header$/) do
19
+ add_run_input SAMPLE_PRECOMPILE
20
+ end
21
+
22
+ Given(/^I have an aggregate target to build$/) do
23
+ add_run_input SAMPLE_AGGREGATE_TARGET
24
+ end
25
+
26
+ Given(/^I have a file to analyze$/) do
27
+ add_run_input SAMPLE_ANALYZE
28
+ end
29
+
30
+ Given(/^I have a file to shallow analyze$/) do
31
+ add_run_input SAMPLE_ANALYZE_SHALLOW
32
+ end
33
+
34
+ Given(/^I have a failing test in my suite$/) do
35
+ add_run_input SAMPLE_OLD_SPECTA_FAILURE
36
+ end
37
+
38
+ Given(/^I have a swift fatal error in a test in my suite$/) do
39
+ add_run_input SAMPLE_SWIFT_FATAL_ERROR_IN_TEST_MAKE_TESTS_RESTARTING
40
+ end
41
+
42
+ Given(/^all of my tests will pass in my suite$/) do
43
+ 3.times { add_run_input SAMPLE_OCUNIT_TEST }
44
+ end
45
+
46
+ Given(/^I have a passing test in my suite$/) do
47
+ add_run_input SAMPLE_OCUNIT_TEST
48
+ end
49
+
50
+ Given(/^I have a slow\-ish test in my suite$/) do
51
+ add_run_input SAMPLE_SLOWISH_TEST
52
+ end
53
+
54
+ Given(/^I have a slow test in my suite$/) do
55
+ add_run_input SAMPLE_SLOW_TEST
56
+ end
57
+
58
+ Given(/^the tests have started running$/) do
59
+ add_run_input SAMPLE_OCUNIT_TEST_RUN_BEGINNING
60
+ end
61
+
62
+ Given(/^I start a test suite$/) do
63
+ add_run_input SAMPLE_OCUNIT_SUITE_BEGINNING
64
+ end
65
+
66
+ Given(/^the test suite has finished$/) do
67
+ add_run_input SAMPLE_OCUNIT_SUITE_COMPLETION
68
+ add_run_input SAMPLE_EXECUTED_TESTS
69
+ end
70
+
71
+ Given(/^I have a file to code sign$/) do
72
+ add_run_input SAMPLE_CODESIGN
73
+ end
74
+
75
+ Given(/^I have a framework to code sign$/) do
76
+ add_run_input SAMPLE_CODESIGN_FRAMEWORK
77
+ end
78
+
79
+ Given(/^I have a target which will not be code signed$/) do
80
+ add_run_input SAMPLE_WILL_NOT_BE_CODE_SIGNED
81
+ end
82
+
83
+ Given(/^I have a file to preprocess$/) do
84
+ add_run_input SAMPLE_PREPROCESS
85
+ end
86
+
87
+ Given(/^I have a file to copy with PBXCp/) do
88
+ add_run_input SAMPLE_PBXCP
89
+ end
90
+
91
+ Given(/^podfile.lock wasn't in sync$/) do
92
+ add_run_input SAMPLE_PODS_ERROR
93
+ end
94
+
95
+ Given(/^there was a syntax error$/) do
96
+ add_run_input SAMPLE_COMPILE_ERROR
97
+ end
98
+
99
+ Given(/^there was a missing file$/) do
100
+ add_run_input SAMPLE_FILE_MISSING_ERROR
101
+ end
102
+
103
+ Given(/^there were warnings in the code$/) do
104
+ add_run_input SAMPLE_FORMAT_WARNING
105
+ end
106
+
107
+ Given(/^the linker has failed with undefined symbols$/) do
108
+ add_run_input SAMPLE_UNDEFINED_SYMBOLS
109
+ end
110
+
111
+ Given(/^I have a pending test in my suite$/) do
112
+ add_run_input SAMPLE_PENDING_KIWI_TEST
113
+ end
114
+
115
+ Given(/^I have a measuring test in my suite$/) do
116
+ add_run_input SAMPLE_MEASURING_TEST
117
+ end
118
+
119
+ Given(/^I have a tiff file to validate$/) do
120
+ add_run_input SAMPLE_TIFFUTIL
121
+ end
122
+
123
+ Given(/^I have a file to touch$/) do
124
+ add_run_input SAMPLE_TOUCH
125
+ end
126
+
127
+ Given(/^I have a screenshot in the output folder/) do
128
+ copy_file_to_screenshot_dir(SAMPLE_SCREENSHOT_FILE)
129
+ end
130
+
131
+ Given(/^I have an unrelated image in the output folder/) do
132
+ copy_file_to_screenshot_dir(SAMPLE_UNRELATED_IMAGE_FILE)
133
+ end
134
+
135
+ Given(/^I have completed a build$/) do
136
+ add_run_input SAMPLE_BUILD_SUCCEEDED
137
+ end
138
+
139
+ Given(/^I have completed a clean$/) do
140
+ add_run_input SAMPLE_CLEAN_SUCCEEDED
141
+ end
142
+
143
+ Given(/^the provisioning profile doesn't support capability$/) do
144
+ add_run_input SAMPLE_PROFILE_DOESNT_SUPPORT_CAPABILITY_ERROR
145
+ end
146
+
147
+ Given(/^the provisioning profile doesn't include entitlement$/) do
148
+ add_run_input SAMPLE_PROFILE_DOESNT_INCLUDE_ENTITLEMENT_ERROR
149
+ end
150
+
151
+ Given(/^the target requires code signing$/) do
152
+ add_run_input SAMPLE_CODE_SIGNING_IS_REQUIRED_ERROR
153
+ end
154
+
155
+ Given(/^the matching profile is missing$/) do
156
+ add_run_input SAMPLE_NO_PROFILE_MATCHING_ERROR
157
+ end
158
+
159
+ Then(/^I should see a "(\w+)" completion message$/) do |phase|
160
+ run_output.should start_with("▸ #{phase.capitalize} Succeeded")
161
+ end
162
+
163
+ Then(/^I should see text beginning with "(.*?)"$/) do |text|
164
+ run_output.lines.to_a.detect { |line| line.start_with? text }.should_not be_nil
165
+ end
166
+
167
+ Then(/^I should see text containing "(.*?)" and beginning with "(.*?)"$/) do |inner, start|
168
+ run_output.lines.to_a.detect { |line| line.start_with?(start) && line.include?(inner) }.should_not be_nil
169
+ end
170
+
171
+ Then(/^I should (green|red) text beginning with "(.*?)"$/) do |color, text|
172
+ run_output.should start_with(send(color.to_sym, text))
173
+ end
174
+
175
+ Then(/^I should see a successful tiff validation message$/) do
176
+ run_output.should start_with("▸ Validating")
177
+ end
178
+
179
+ Then(/^I should see a successful touch message$/) do
180
+ run_output.should start_with("▸ Touching")
181
+ end
182
+
183
+ When(/^I pipe to xcpretty with "(.*?)"$/) do |flags|
184
+ run_xcpretty(flags)
185
+ end
186
+
187
+ When(/^I pipe to xcpretty with a custom formatter$/) do
188
+ formatter_path = File.expand_path('../../../spec/fixtures/custom_formatter.rb', __FILE__)
189
+ run_xcpretty("-f #{formatter_path}")
190
+ end
191
+
192
+ Then(/^I should see a custom compilation message$/) do
193
+ run_output.should start_with("😎 Compilation party time")
194
+ end
195
+
196
+ Then(/^I should see a successful compilation message$/) do
197
+ run_output.should start_with("▸ Compiling")
198
+ end
199
+
200
+ Then(/^I should see a successful precompilation message$/) do
201
+ run_output.should start_with("▸ Precompiling")
202
+ end
203
+
204
+ Then(/^I should see an aggregate target message$/) do
205
+ run_output.should start_with("▸ Aggregate")
206
+ end
207
+
208
+ Then(/^I should see a successful analyze message$/) do
209
+ run_output.should start_with("▸ Analyzing")
210
+ end
211
+
212
+ Then(/^I should see a successful code signing message$/) do
213
+ run_output.should start_with("▸ Signing")
214
+ end
215
+
216
+ Then(/^I should see a target will not be code signed warning$/) do
217
+ run_output.should include(yellow("⚠️ FrameworkName will not be code signed because its settings don't specify a development team."))
218
+ end
219
+
220
+ Then(/^I should see a successful preprocessing message$/) do
221
+ run_output.should start_with("▸ Preprocessing")
222
+ end
223
+
224
+ Then(/^I should see a successful copying message$/) do
225
+ run_output.should start_with("▸ Copying")
226
+ end
227
+
228
+ Then(/^I should see a yellow completion icon$/) do
229
+ run_output.should start_with(yellow("▸"))
230
+ end
231
+
232
+ Then(/^I should see a failed test icon$/) do
233
+ run_output.should start_with("F")
234
+ end
235
+
236
+ Then(/^I should see a passing test icon in ASCII$/) do
237
+ run_output.should start_with(".")
238
+ end
239
+
240
+ Then(/^I should see a red failed test icon$/) do
241
+ run_output.should include(red("F"))
242
+ end
243
+
244
+ Then(/^I should see a pending test icon in ASCII$/) do
245
+ run_output.should start_with("P")
246
+ end
247
+
248
+ Then(/^I should see a yellow pending test icon$/) do
249
+ run_output.should start_with(yellow("P"))
250
+ end
251
+
252
+ Then(/^I should see a measuring test icon in ASCII$/) do
253
+ run_output.should start_with('T')
254
+ end
255
+
256
+ Then(/^I should see a yellow measuring test icon$/) do
257
+ run_output.should start_with(yellow('T'))
258
+ end
259
+
260
+ Then(/^the final execution message should be (red|green)$/) do |color|
261
+ last_line = run_output.lines.to_a.last
262
+ last_line.should be_colored(color.to_sym)
263
+ end
264
+
265
+ Then(/^I should see a green passing test icon$/) do
266
+ run_output.should include(green("."))
267
+ end
268
+
269
+ Then(/^I should see the name of a failed test$/) do
270
+ run_output.should =~ FAILING_TEST_NAME_MATCHER
271
+ end
272
+
273
+ Then(/^I should see the path of a failed test$/) do
274
+ run_output.should =~ TEST_PATH_MATCHER
275
+ end
276
+
277
+ Then(/^I should see the name of a passing test$/) do
278
+ run_output.should =~ PASSING_TEST_NAME_MATCHER
279
+ end
280
+
281
+ Then(/^I should not see the path of a passing test$/) do
282
+ run_output.should_not =~ TEST_PATH_MATCHER
283
+ end
284
+
285
+ Then(/^I should see that test suite has started$/) do
286
+ run_output.should =~ TEST_RUN_START_MATCHER
287
+ end
288
+
289
+ Then(/^I should see the name of suite only$/) do
290
+ run_output.should =~ TEST_SUITE_START_MATCHER
291
+ end
292
+
293
+ Then(/^I should see that the test suite finished$/) do
294
+ run_output.strip.should =~ TEST_SUITE_COMPLETION_MATCHER
295
+ end
296
+
297
+ Then(/^I should see a red failed test mark$/) do
298
+ run_output.should include(red("✗"))
299
+ end
300
+
301
+ Then(/^I should see a green passing test mark$/) do
302
+ run_output.should include(green("✓"))
303
+ end
304
+
305
+ Then(/^I should see a non-utf prefixed output$/) do
306
+ run_output.should start_with(" " + green("."))
307
+ end
308
+
309
+ Then(/^I should not see the name of the test group$/) do
310
+ run_output.should_not include("RACTupleSpec")
311
+ end
312
+
313
+ Then(/^I should see a red error message$/) do
314
+ run_output.should include(red("❌ error: ")[0..-5]) # trim \e[0m
315
+ end
316
+
317
+ Then(/^I should see that sandbox is not in sync with Podfile.lock$/) do
318
+ run_output.should include("The sandbox is not in sync with the Podfile.lock")
319
+ end
320
+
321
+ Then(/^I should see which file is missing$/) do
322
+ run_output.should include(SAMPLE_FILE_MISSING_ERROR.split('directory: ')[1].delete("'"))
323
+ end
324
+
325
+ Then(/^I should see a yellow warning message$/) do
326
+ run_output.should include("#{yellow('⚠️ ')}/Users/supermarin/code/oss/ObjectiveSugar/Example/ObjectiveSugar/AppDelegate.m:19:31:")
327
+ run_output.should include(yellow("format specifies type 'id' but the argument has type 'int' [-Wformat]"))
328
+ end
329
+
330
+ Then(/^I should see a red compilation error$/) do
331
+ run_output.should include(red("expected identifier"))
332
+ end
333
+
334
+ Then(/^I should see a failed line$/) do
335
+ run_output.should include("[[thread.lastMessage should] equal:thread.];")
336
+ end
337
+
338
+ Then(/^I should see a cyan cursor$/) do
339
+ run_output.should include(cyan(" ^"))
340
+ end
341
+
342
+ Then(/^I should see the undefined symbold message$/) do
343
+ run_output.should include(red("❌ Undefined symbols for architecture x86_64"))
344
+ end
345
+
346
+ Then(/^I should see the symbol and reference that caused failure$/) do
347
+ run_output.should include("_OBJC_CLASS_$_CABasicAnimation")
348
+ run_output.should include("objc-class-ref in ATZRadialProgressControl.o")
349
+ end
350
+
351
+ Then(/^I should see the name of a pending test$/) do
352
+ run_output.should =~ PENDING_TEST_NAME_MATCHER
353
+ end
354
+
355
+ Then(/^I should see the name of a measuring test$/) do
356
+ run_output.should =~ MEASURING_TEST_NAME_MATCHER
357
+ end
358
+
359
+ Then(/^I should see the test time in yellow$/) do
360
+ run_output.should include("#{yellow("0.026")}")
361
+ end
362
+
363
+ Then(/^I should see the test time in red$/) do
364
+ run_output.should include("#{red("0.101")}")
365
+ end
366
+
367
+ Then(/^I should see text matching "(.*?)"$/) do |text|
368
+ run_output.lines.to_a.last.strip.should == text
369
+ end
370
+
371
+ Then(/^I should see the profile doesn't support capability message$/) do
372
+ run_output.should include("Provisioning profile \"Profile Name\" doesn't support the Push Notifications capability.")
373
+ end
374
+
375
+ Then(/^I should see the profile doesn't include entitlement message$/) do
376
+ run_output.should include("Provisioning profile \"Profile Name\" doesn't include the aps-environment entitlement.")
377
+ end
378
+
379
+ Then(/^I should see the code signing is requried message$/) do
380
+ run_output.should include("Code signing is required for product type 'Application' in SDK 'iOS 10.0'")
381
+ end
382
+
383
+ Then(/^I should see the no profile matching message$/) do
384
+ run_output.should include("No profile matching 'TargetName' found: Xcode couldn't find a profile matching 'TargetName'. Install the profile (by dragging and dropping it onto Xcode's dock item) or select a different one in the General tab of the target editor.")
385
+ end
386
+
@@ -0,0 +1,32 @@
1
+ Then(/^I should see a test suite section in HTML$/) do
2
+ html_test_suites.first.should_not be_nil
3
+ end
4
+
5
+ Then(/^I should see a failed test in HTML$/) do
6
+ html_report_body.get_elements("//*[contains(@class, 'test failing')]/").to_a.size.should_not == 0
7
+ end
8
+
9
+ Then(/^the failure counter should show (\d+) tests?$/) do |fail_count|
10
+ html_report_body.get_elements("//*[@id='fail-count']/").first.elements.to_a.first.text.to_i.should == fail_count.to_i
11
+ end
12
+
13
+ Then(/^I should see a passing test in HTML$/) do
14
+ html_report_body.get_elements("//*[contains(@class, 'test passing')]/").to_a.size.should_not == 0
15
+ end
16
+
17
+ Then(/^I should see (\d+) tests in HTML$/) do |test_count|
18
+ html_report_body.get_elements("//*[contains(@class, 'test ')]/").size.should == test_count.to_i
19
+ end
20
+
21
+ Then(/^I should see (\d+) test suite sections? in HTML$/) do |section_count|
22
+ html_test_suites.size.should == section_count.to_i
23
+ end
24
+
25
+ Then(/^I should see a screenshot in HTML$/) do
26
+ html_report_body.get_elements("//*[contains(@class, 'screenshot')]/").to_a.size.should_not == 0
27
+ end
28
+
29
+ Then(/^I should not see a screenshot in HTML$/) do
30
+ html_report_body.get_elements("//*[contains(@class, 'screenshot')]/").to_a.size.should == 0
31
+ end
32
+
@@ -0,0 +1,45 @@
1
+ Given(/^some big input$/) do
2
+ add_run_input File.open('features/fixtures/xcodebuild.log', 'r').read
3
+ end
4
+
5
+ Then(/^I should have a JSON compilation database in a custom path$/) do
6
+ step("I should have a JSON compilation database at \"#{custom_report_path}\"")
7
+ end
8
+
9
+ Then(/^I should have a JSON compilation database at "(.*?)"$/) do |path|
10
+ json = JSON.parse(File.open(path, 'r').read)
11
+ json.should_not be_nil
12
+ end
13
+
14
+ Then(/^I should have JSON compilation databases in two custom paths$/) do
15
+ step("I should have a JSON compilation database at \"#{custom_report_path}\"")
16
+ step("I should have a JSON compilation database at \"#{other_custom_report_path}\"")
17
+ end
18
+
19
+ Then(/^the JSON compilation database should contain an entry with a command$/) do
20
+ json_db.length.should == 1
21
+ json_db[0]['command'].should start_with('/')
22
+ json_db[0]['command'].should include('clang ')
23
+ json_db[0]['command'].should include(' -c ')
24
+ json_db[0]['command'].should include(' -o ')
25
+ json_db[0]['command'].should end_with('.o')
26
+ end
27
+
28
+ Then(/^the JSON compilation database should contain an entry with a file$/) do
29
+ json_db[0]['file'].should end_with('.m')
30
+ end
31
+
32
+ Then(/^the JSON compilation database should contain an entry with a directory$/) do
33
+ json_db[0]['directory'].should start_with('/')
34
+ end
35
+
36
+ Then(/^the JSON compilation database should be complete$/) do
37
+ entries = json_db.select { |entry| entry['command'] && entry['file'] && entry['directory'] }
38
+ entries.length.should == JSON_DB_FIXTURE_COMMAND_COUNT
39
+ end
40
+
41
+ Then(/^entries with a command shouldn't have malformed "-include" directives$/) do
42
+ entries = json_db.select { |entry| entry['command'].match(/-include\s+-/) }
43
+ entries.length.should == 0
44
+ end
45
+
@@ -0,0 +1,39 @@
1
+ Then(/^I should see a failed test node in my report$/) do
2
+ junit_report_root.elements.to_a.detect do |node|
3
+ element = node.elements.to_a.first
4
+ element && element.name == "failure"
5
+ end.should_not be_nil
6
+ end
7
+
8
+ Then(/^I should see a passing test node in my report$/) do
9
+ junit_report_root.elements.to_a.detect do |node|
10
+ node.attributes["time"] != nil
11
+ end.should_not be_nil
12
+ end
13
+
14
+ Then(/^I should see a pending test node in my report$/) do
15
+ junit_report_root.elements.to_a.detect do |node|
16
+ node.elements.to_a.detect { |child| child.name == 'skipped' }
17
+ end.should_not be_nil
18
+ end
19
+
20
+ Then(/^I should see a test suite node$/) do
21
+ junit_report_root.elements.to_a.first.should_not be_nil
22
+ end
23
+
24
+ Then(/^I should see (\d+) tests in my report$/) do |test_count|
25
+ junit_report_root.attributes["tests"].should == test_count
26
+ junit_report_root.elements.to_a.size.should == test_count.to_i
27
+ end
28
+
29
+ Then(/^I should see (\d+) test suites$/) do |count|
30
+ suites = junit_report.root.elements.to_a
31
+ suites.size.should == count.to_i
32
+ suites.count { |s| s.name == 'testsuite' }.should == count.to_i
33
+ end
34
+
35
+ Then(/^I should have a test report at "(.*?)"$/) do |path|
36
+ doc = REXML::Document.new(File.open(path, 'r').read)
37
+ doc.root.should_not be_nil
38
+ end
39
+
@@ -0,0 +1,27 @@
1
+ Given(/^I have tests in my suite from 2 classes$/) do
2
+ add_run_input SAMPLE_OCUNIT_TEST
3
+ add_run_input SAMPLE_KIWI_TEST
4
+ end
5
+
6
+ When(/^I pipe to xcpretty with "(.*?)" and specify a custom path$/) do |args|
7
+ step("I pipe to xcpretty with \"#{args} --output #{custom_report_path}\"")
8
+ end
9
+
10
+ When(/^I pipe to xcpretty with two custom "(.*?)" report paths$/) do |type|
11
+ step("I pipe to xcpretty with \"--report #{type} --output #{custom_report_path} --report #{type} --output #{other_custom_report_path}\"")
12
+ end
13
+
14
+ Then(/^I should have test reports in two custom paths$/) do
15
+ step("I should have a test report at \"#{custom_report_path}\"")
16
+ step("I should have a test report at \"#{other_custom_report_path}\"")
17
+ end
18
+
19
+ Then(/^I should have a test report in a custom path$/) do
20
+ step("I should have a test report at \"#{custom_report_path}\"")
21
+ end
22
+
23
+ When(/^I pipe to xcpretty with a custom reporter$/) do
24
+ reporter_path = File.expand_path('../../../spec/fixtures/custom_reporter.rb', __FILE__)
25
+ run_xcpretty("-r #{reporter_path}")
26
+ end
27
+
@@ -0,0 +1,31 @@
1
+ When(/^I run xcpretty$/) do
2
+ @output = `bin/xcpretty 2>&1`
3
+ end
4
+
5
+ When(/^I run xcpretty with (.*)$/) do |flags|
6
+ @output = `bin/xcpretty #{flags}`
7
+ end
8
+
9
+ When(/^I run xcpretty over a big file$/) do
10
+ start_time = Time.now
11
+ @output = `cat features/fixtures/xcodebuild.log | bin/xcpretty -c`
12
+ @xcpretty_run_time = Time.now - start_time
13
+ end
14
+
15
+ Then(/^I should see the help banner$/) do
16
+ run_output.should include("Usage: xcodebuild [options] | xcpretty")
17
+ end
18
+
19
+ Then(/^I should see the xcpretty version$/) do
20
+ run_output.should include(XCPretty::VERSION)
21
+ end
22
+
23
+ Then(/^the exit status code should be (\d)$/) do |numbah|
24
+ $?.exitstatus.should == numbah.to_i
25
+ end
26
+
27
+ Then(/^the performance should be way faster than running cat$/) do
28
+ puts "XCPretty run time: #{@xcpretty_run_time}"
29
+ @xcpretty_run_time.should < 2
30
+ end
31
+
@@ -0,0 +1,123 @@
1
+ $LOAD_PATH.unshift File.expand_path('../../..', __FILE__)
2
+
3
+ require 'tempfile'
4
+ require 'spec/fixtures/constants'
5
+ require 'spec/support/matchers/colors'
6
+ require 'lib/xcpretty/ansi'
7
+ require 'lib/xcpretty/version'
8
+ require 'lib/xcpretty/syntax'
9
+ require 'rexml/document'
10
+ require 'lib/xcpretty/formatters/formatter'
11
+ require 'lib/xcpretty/reporters/reporter'
12
+ require 'lib/xcpretty/reporters/junit'
13
+ require 'lib/xcpretty/reporters/html'
14
+ require 'lib/xcpretty/reporters/json_compilation_database'
15
+
16
+ begin
17
+ require 'json'
18
+ rescue LoadError
19
+ require 'vendor/json_pure/parser'
20
+ end
21
+
22
+ include XCPretty::ANSI
23
+
24
+ TEST_RUN_START_MATCHER = /Test Suite .+ started/
25
+ TEST_SUITE_COMPLETION_MATCHER = /Executed \d+ tests, with \d+ failures \(\d+ unexpected\) in \d+\.\d+ \(\d+\.\d+\) seconds/
26
+ TEST_SUITE_START_MATCHER = /[\w]*(Spec|Tests)$/
27
+ TEST_PATH_MATCHER = %r{[\w/\-\s]+:\d+}
28
+ PASSING_TEST_NAME_MATCHER = %r{\w+\s\(\d+\.\d+\sseconds\)}
29
+ PENDING_TEST_NAME_MATCHER = %r{\w+\s\[PENDING\]}
30
+ FAILING_TEST_NAME_MATCHER = %r{\w+, expected:}
31
+ MEASURING_TEST_NAME_MATCHER = %r{\w+\smeasured\s\(\d+\.\d+\sseconds\)}
32
+
33
+ JSON_DB_FIXTURE_COMMAND_COUNT = 557
34
+
35
+ def run_xcpretty(flags)
36
+ input_file = Tempfile.new('xcpretty_input')
37
+ File.open(input_file.path, 'w') do |file|
38
+ file.print run_input
39
+ end
40
+ @output = %x(cat '#{input_file.path}' | bin/xcpretty #{flags})
41
+ input_file.unlink
42
+ end
43
+
44
+ def add_run_input(text)
45
+ run_input << "\n#{text}"
46
+ end
47
+
48
+ def run_input
49
+ @input ||= ''
50
+ end
51
+
52
+ def run_output
53
+ @output ||= ''
54
+ end
55
+
56
+ def html_report
57
+ @html_report ||= REXML::Document.new(File.open(XCPretty::HTML::FILEPATH, 'r').read.sub("<!DOCTYPE html>", ""))
58
+ end
59
+
60
+ def html_report_body
61
+ html_report.root.get_elements('//body').first
62
+ end
63
+
64
+ def html_test_suites
65
+ parent = html_report_body.get_elements("//*[@id='test-suites']/").first
66
+ parent.elements.to_a.select do |e|
67
+ e.attributes['class'] && e.attributes['class'].include?('test-suite')
68
+ end
69
+ end
70
+
71
+ def json_db
72
+ @json ||= JSON.parse(File.open(custom_report_path, 'r').read)
73
+ end
74
+
75
+ def junit_report
76
+ REXML::Document.new(File.open(XCPretty::JUnit::FILEPATH, 'r').read)
77
+ end
78
+
79
+ def junit_report_root
80
+ junit_report.root.elements.to_a.first
81
+ end
82
+
83
+ def custom_report
84
+ @custom_report ||= File.open(XCPretty::Reporter::FILEPATH, 'r').read
85
+ end
86
+
87
+ def custom_report_path
88
+ @custom_report_path ||= begin
89
+ @custom_report_file1 = Tempfile.new('custom_report_path')
90
+ @custom_report_file1.path
91
+ end
92
+ end
93
+
94
+ def other_custom_report_path
95
+ @custom_report_path2 ||= begin
96
+ @custom_report_file2 = Tempfile.new('custom_report_path')
97
+ @custom_report_file2.path
98
+ end
99
+ end
100
+
101
+ def copy_file_to_screenshot_dir(screenshot_file)
102
+ @screenshot_file_path = "#{XCPretty::HTML::SCREENSHOT_DIR}/#{screenshot_file}"
103
+ FileUtils.cp("features/assets/#{screenshot_file}", @screenshot_file_path)
104
+ end
105
+
106
+ Before do
107
+ self.colorize = true
108
+ end
109
+
110
+ After do
111
+ @input = ""
112
+ @output = ""
113
+ @custom_report_file1.unlink if @custom_report_file1
114
+ @custom_report_file2.unlink if @custom_report_file2
115
+ @html_report = nil
116
+ @json = nil
117
+ FileUtils.rm_rf(XCPretty::JUnit::FILEPATH)
118
+ FileUtils.rm_rf(XCPretty::HTML::FILEPATH)
119
+ FileUtils.rm_rf(XCPretty::JSONCompilationDatabase::FILEPATH)
120
+ FileUtils.rm_rf(XCPretty::Reporter::FILEPATH)
121
+ File.delete(@screenshot_file_path) if @screenshot_file_path
122
+ end
123
+