rspec-sharder 0.0.2 → 0.0.3

Sign up to get free protection for your applications and to get access to all the features.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: defc38fdaa55ddfeb271282a3ca2a992b0391fed1eb4be8d552fcd41caafc551
4
- data.tar.gz: 22fa847d430e3bc20069803710a0e3429eede4a58b4cd56d28eb3f9492c95f2c
3
+ metadata.gz: 7abffffb75542211fc36495edeca3b96f32f59b6975686568b3532d2df6ff9c6
4
+ data.tar.gz: 64bccf923c9897fa23205ade6af164ca10eb60dfc3c89b760b9a73be35d382bb
5
5
  SHA512:
6
- metadata.gz: 507e697bece492b62a5310f761c923e3956e328c014e6aa610fd2106c57c55662a84c23c1e91fca3ee8b3a2028d96832d1a7e790716f21c786d93bdf408c6342
7
- data.tar.gz: 443c1586f14b36142790ea916f3864e797481d8729e16b418e1fb123361d9f7263115cbe9ba7f710c2052d13547b9e1150799c9e80a2198613cb178d0fe1893c
6
+ metadata.gz: 3cbba17bc9116dbe0a8e3f6aef9d7865f57e40c6393d2e3d3243afacfc5dee658d33fe2c729734fb43ad291280a67f124913807f0b5d69eb28f13671d194309f
7
+ data.tar.gz: 809210eec8b32c39a87c6f64dbe6e9f699c1f1242b8edb1c0a9ea8120c7945801461744ad17065913f981a81bdfe1b5e1a031a2ce68a746871db995504e39ff1
data/Gemfile.lock CHANGED
@@ -1,7 +1,7 @@
1
1
  PATH
2
2
  remote: .
3
3
  specs:
4
- rspec-sharder (0.0.1)
4
+ rspec-sharder (0.0.2)
5
5
  rspec-core
6
6
 
7
7
  GEM
data/bin/rspec-sharder CHANGED
@@ -1,75 +1,3 @@
1
1
  #!/usr/bin/env ruby
2
2
 
3
- require 'optparse'
4
- require 'rspec-sharder'
5
-
6
- def fail(message)
7
- warn message
8
- puts
9
- puts @parser.help
10
- exit 1
11
- end
12
-
13
- @total_shards = 1
14
- @shard_num = 1
15
- @persist = false
16
-
17
- @parser = OptionParser.new do |opts|
18
- opts.banner = <<~EOF
19
- Groups specs into shards, ensuring that each shard has a similar size, and runs
20
- the specified shard.
21
-
22
- Shard size is determined by summing the saved durations for each spec file in
23
- the shard. Durations are saved in .spec_durations. If a spec file is not found
24
- in .spec_durations, the duration is estimated based on the number of examples in
25
- the spec file.
26
-
27
- .spec_durations is generate/updated after a successful run when --persist is
28
- specified, but only for the shard which was actually executed. To generate
29
- durations for all shards simultaneously, run with the default options of 1 total
30
- shards and --persist:
31
-
32
- bundle exec rspec-sharder --persist -- [<rspec-args...>]
33
-
34
- Usage: bundle exec rspec-sharder [--total-shards <num> [--shard <num>]] [--persist] -- [<rspec-args...>]
35
-
36
- Options:
37
- EOF
38
-
39
- opts.on('-h', '--help', "Print this message.") do
40
- puts opts
41
- exit
42
- end
43
-
44
- opts.on('-t', '--total-shards <num>', 'The total number of shards. Defaults to 1.') do |total_shards|
45
- begin
46
- @total_shards = Integer(total_shards)
47
- rescue ArgumentError
48
- fail('fatal: invalid value for --total-shards')
49
- end
50
- end
51
-
52
- opts.on('-s', '--shard <num>', 'The shard to run. Defaults to 1.') do |shard|
53
- begin
54
- @shard = Integer(shard)
55
- rescue ArgumentError
56
- fail('fatal: invalid value for --shard')
57
- end
58
- end
59
-
60
- opts.on('-p', '--persist', 'Save durations to .spec_durations.') do
61
- @persist = true
62
- end
63
- end
64
-
65
- begin
66
- @parser.parse!
67
- rescue StandardError => e
68
- fail("fatal: #{e.message}")
69
- end
70
-
71
- fail('fatal: invalid value for --total-shards') unless @total_shards > 0
72
- fail('fatal: invalid value for --shard') unless @shard > 0
73
- fail('fatal: --shard may not be greater than --total-shards') unless @shard <= @total_shards
74
-
75
- RSpec::Sharder.run(total_shards: @total_shards, shard_num: @shard, persist: @persist, rspec_args: ARGV)
3
+ require 'rspec-sharder/command'
@@ -0,0 +1,73 @@
1
+ require 'optparse'
2
+ require 'rspec-sharder'
3
+
4
+ def fail(message)
5
+ warn message
6
+ puts
7
+ puts @parser.help
8
+ exit 1
9
+ end
10
+
11
+ @total_shards = 1
12
+ @shard = 1
13
+ @persist = false
14
+
15
+ @parser = OptionParser.new do |opts|
16
+ opts.banner = <<~EOF
17
+ Groups specs into shards, ensuring that each shard has a similar size, and runs
18
+ the specified shard.
19
+
20
+ Shard size is determined by summing the saved durations for each spec file in
21
+ the shard. Durations are saved in .spec_durations. If a spec file is not found
22
+ in .spec_durations, the duration is estimated based on the number of examples in
23
+ the spec file.
24
+
25
+ .spec_durations is generate/updated after a successful run when --persist is
26
+ specified, but only for the shard which was actually executed. To generate
27
+ durations for all shards simultaneously, run with the default options of 1 total
28
+ shards and --persist:
29
+
30
+ bundle exec rspec-sharder --persist -- [<rspec-args...>]
31
+
32
+ Usage: bundle exec rspec-sharder [--total-shards <num> [--shard <num>]] [--persist] -- [<rspec-args...>]
33
+
34
+ Options:
35
+ EOF
36
+
37
+ opts.on('-h', '--help', "Print this message.") do
38
+ puts opts
39
+ exit
40
+ end
41
+
42
+ opts.on('-t', '--total-shards <num>', 'The total number of shards. Defaults to 1.') do |total_shards|
43
+ begin
44
+ @total_shards = Integer(total_shards)
45
+ rescue ArgumentError
46
+ fail('fatal: invalid value for --total-shards')
47
+ end
48
+ end
49
+
50
+ opts.on('-s', '--shard <num>', 'The shard to run. Defaults to 1.') do |shard|
51
+ begin
52
+ @shard = Integer(shard)
53
+ rescue ArgumentError
54
+ fail('fatal: invalid value for --shard')
55
+ end
56
+ end
57
+
58
+ opts.on('-p', '--persist', 'Save durations to .spec_durations.') do
59
+ @persist = true
60
+ end
61
+ end
62
+
63
+ begin
64
+ @parser.parse!
65
+ rescue StandardError => e
66
+ fail("fatal: #{e.message}")
67
+ end
68
+
69
+ fail('fatal: invalid value for --total-shards') unless @total_shards > 0
70
+ fail('fatal: invalid value for --shard') unless @shard > 0
71
+ fail('fatal: --shard may not be greater than --total-shards') unless @shard <= @total_shards
72
+
73
+ RSpec::Sharder.run(total_shards: @total_shards, shard_num: @shard, persist: @persist, rspec_args: ARGV)
@@ -2,6 +2,6 @@
2
2
 
3
3
  module RSpec
4
4
  module Sharder
5
- VERSION = "0.0.2"
5
+ VERSION = "0.0.3"
6
6
  end
7
7
  end
data/lib/rspec-sharder.rb CHANGED
@@ -50,12 +50,9 @@ module RSpec
50
50
  end
51
51
 
52
52
  group_results = example_groups.map do |example_group|
53
- start_time = current_time_millis
54
- result = example_group.run(reporter)
55
- end_time = current_time_millis
53
+ result, duration = run_example_group(example_group, reporter)
56
54
 
57
55
  file_path = example_group.metadata[:file_path]
58
- duration = (end_time - start_time).to_i
59
56
  actual_total_duration += duration
60
57
  new_durations[file_path] ||= 0
61
58
  new_durations[file_path] += duration
@@ -88,10 +85,7 @@ module RSpec
88
85
  else
89
86
  if exit_code == 0
90
87
  # Print recorded durations and summary.
91
- ::RSpec.configuration.output_stream.puts <<~EOF
92
-
93
- Durations:
94
- EOF
88
+ ::RSpec.configuration.output_stream.puts 'Durations'
95
89
 
96
90
  new_durations.sort_by { |file_path, duration| file_path }.each do |file_path, duration|
97
91
  ::RSpec.configuration.output_stream.puts "#{file_path},#{duration}"
@@ -177,7 +171,7 @@ module RSpec
177
171
  if durations[file_path]
178
172
  files[file_path] = durations[file_path]
179
173
  else
180
- ::RSpec.configuration.error_stream.puts "warning: recorded duration not found for #{file_path}"
174
+ ::RSpec.configuration.output_stream.puts "warning: recorded duration not found for #{file_path}"
181
175
 
182
176
  # Assume 1000 milliseconds per example.
183
177
  files[file_path] += ::RSpec.world.example_count([example_group]) * 1000
@@ -209,7 +203,7 @@ module RSpec
209
203
  end
210
204
  ::RSpec::Core::ExampleStatusPersister.persist(examples, path)
211
205
  rescue SystemCallError => e
212
- ::RSpec.configuration.error_stream.puts "warning: failed to write results to #{path}"
206
+ ::RSpec.configuration.output_stream.puts "warning: failed to write results to #{path}"
213
207
  end
214
208
 
215
209
  def self.pretty_duration(duration_millis)
@@ -236,7 +230,7 @@ module RSpec
236
230
  shard[:file_paths].each do |file_path|
237
231
  ::RSpec.configuration.output_stream.puts file_path
238
232
  end
239
- ::RSpec.configuration.output_stream.puts
233
+ ::RSpec.configuration.output_stream.puts unless i == shards.size - 1
240
234
  end
241
235
  end
242
236
 
@@ -255,5 +249,11 @@ module RSpec
255
249
  def self.current_time_millis
256
250
  (Process.clock_gettime(Process::CLOCK_MONOTONIC) * 1000).to_i
257
251
  end
252
+
253
+ def self.run_example_group(example_group, reporter)
254
+ start_time = current_time_millis
255
+ result = example_group.run(reporter)
256
+ [result, (current_time_millis - start_time).to_i]
257
+ end
258
258
  end
259
259
  end
metadata CHANGED
@@ -1,7 +1,7 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: rspec-sharder
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.0.2
4
+ version: 0.0.3
5
5
  platform: ruby
6
6
  authors:
7
7
  - Nick Dower
@@ -39,6 +39,7 @@ files:
39
39
  - README.md
40
40
  - bin/rspec-sharder
41
41
  - lib/rspec-sharder.rb
42
+ - lib/rspec-sharder/command.rb
42
43
  - lib/rspec-sharder/version.rb
43
44
  - rspec-sharder.gemspec
44
45
  - scripts/release.sh