Skip to content

Commit 6f56285

Browse files
Use new test-parallel command to trigger parallelism
1 parent 840156e commit 6f56285

File tree

6 files changed

+38
-30
lines changed

6 files changed

+38
-30
lines changed

spec/integration_spec.cr

Lines changed: 22 additions & 20 deletions
Original file line numberDiff line numberDiff line change
@@ -2,21 +2,22 @@ require "./spec_helper"
22

33
{% unless flag?("skip-integration") %}
44
describe Crytic do
5-
describe "the test command" do
6-
describe "--help/-h" do
7-
it "prints usage info" do
8-
result = run_crytic("--help")
9-
result.output.should contain("Usage: crytic [arguments]")
10-
result.exit_code.should eq 0
11-
result = run_crytic("-h")
12-
result.output.should contain("Usage: crytic [arguments]")
13-
result.exit_code.should eq 0
14-
end
5+
describe "--help/-h" do
6+
it "prints usage info" do
7+
result = run_crytic("--help")
8+
result.output.should contain("Usage: crytic [arguments]")
9+
result.exit_code.should eq 0
10+
result = run_crytic("-h")
11+
result.output.should contain("Usage: crytic [arguments]")
12+
result.exit_code.should eq 0
1513
end
14+
end
1615

16+
{% for command in ["test", "test-parallel"] %}
17+
describe "the {{ command.id }} command" do
1718
describe "--preamble/-p" do
1819
it "injects the given custom preamble, failing the neutral mutant" do
19-
result = run_crytic("test -s ./fixtures/conditionals/fully_covered.cr ./fixtures/conditionals/uncovered_spec.cr -p 'exit 1'")
20+
result = run_crytic("{{ command.id }} -s ./fixtures/conditionals/fully_covered.cr ./fixtures/conditionals/uncovered_spec.cr -p 'exit 1'")
2021
result.output.should contain("unmodified subject")
2122
result.output.should_not contain("ConditionFlip")
2223
result.exit_code.should eq 1
@@ -25,7 +26,7 @@ require "./spec_helper"
2526

2627
describe "with a fully covered subject" do
2728
it "passes the mutation specs" do
28-
result = run_crytic("-s ./fixtures/conditionals/fully_covered.cr ./fixtures/conditionals/fully_covered_spec.cr")
29+
result = run_crytic("{{ command.id }} -s ./fixtures/conditionals/fully_covered.cr ./fixtures/conditionals/fully_covered_spec.cr")
2930
result.output.should contain("✅ ConditionFlip")
3031
result.output.should contain("✅ BoolLiteralFlip")
3132
result.output.should contain("3 covered")
@@ -35,22 +36,22 @@ require "./spec_helper"
3536

3637
describe "with an insufficiently covered subject" do
3738
it "fails the mutation specs" do
38-
result = run_crytic("-s ./fixtures/conditionals/fully_covered.cr ./fixtures/conditionals/uncovered_spec.cr")
39+
result = run_crytic("{{ command.id }} -s ./fixtures/conditionals/fully_covered.cr ./fixtures/conditionals/uncovered_spec.cr")
3940
result.output.should contain("❌ ConditionFlip")
4041
result.output.should contain("❌ BoolLiteralFlip")
4142
result.output.should contain("3 uncovered")
4243
result.exit_code.should be > 0
4344
end
4445

4546
it "exits successfully when the msi threshold is set sufficiently" do
46-
result = run_crytic("--min-msi=0.0 -s ./fixtures/conditionals/fully_covered.cr ./fixtures/conditionals/uncovered_spec.cr")
47+
result = run_crytic("{{ command.id }} --min-msi=0.0 -s ./fixtures/conditionals/fully_covered.cr ./fixtures/conditionals/uncovered_spec.cr")
4748
result.exit_code.should eq 0
4849
end
4950
end
5051

5152
describe "without passing a subject or tests" do
5253
it "mutates all sources and runs all tests" do
53-
result = run_crytic_in_dir("./fixtures/autofind")
54+
result = run_crytic_in_dir("./fixtures/autofind", {{ command }})
5455
result.output.should contain("✅ ConditionFlip")
5556
result.output.should contain("✅ BoolLiteralFlip")
5657
result.output.should contain("✅ NumberLiteralSignFlip")
@@ -64,7 +65,7 @@ require "./spec_helper"
6465

6566
describe "subject without any coverage" do
6667
it "fails all mutants" do
67-
result = run_crytic("-s ./fixtures/uncovered/without.cr ./fixtures/uncovered/without_spec.cr")
68+
result = run_crytic("{{ command.id }} -s ./fixtures/uncovered/without.cr ./fixtures/uncovered/without_spec.cr")
6869
result.output.should contain("❌ BoolLiteralFlip")
6970
result.output.should contain("❌ ConditionFlip")
7071
result.output.should contain("❌ NumberLiteralSignFlip")
@@ -76,7 +77,7 @@ require "./spec_helper"
7677

7778
describe "a failing initial test suite" do
7879
it "reports initial failure" do
79-
result = run_crytic("-s ./fixtures/uncovered/without.cr ./fixtures/failing/failing_spec.cr")
80+
result = run_crytic("{{ command.id }} -s ./fixtures/uncovered/without.cr ./fixtures/failing/failing_spec.cr")
8081
result.output.should contain "❌ Original test suite failed.\n"
8182
result.output.should contain "no overload matches"
8283
result.exit_code.should be > 0
@@ -85,13 +86,14 @@ require "./spec_helper"
8586

8687
describe "a subject that is mutated into an endless loop" do
8788
it "finishes and reports a timed out spec" do
88-
result = run_crytic("-s ./fixtures/timeout/timeout.cr ./fixtures/timeout/timeout_spec.cr")
89+
result = run_crytic("{{ command.id }} -s ./fixtures/timeout/timeout.cr ./fixtures/timeout/timeout_spec.cr")
8990
result.output.should contain "✅ Original test suite passed.\n"
9091
result.output.should contain "1 timeout"
9192
result.exit_code.should be > 0
9293
end
9394
end
9495
end
96+
{% end %}
9597

9698
describe "the noop command" do
9799
it "outputs the noop'ed code to stdout" do
@@ -103,9 +105,9 @@ require "./spec_helper"
103105
end
104106
{% end %}
105107

106-
def run_crytic_in_dir(dir : String)
108+
def run_crytic_in_dir(dir : String, args : String)
107109
io = IO::Memory.new
108-
result = Process.run("cd #{dir} && crystal run ../../src/crytic.cr",
110+
result = Process.run("cd #{dir} && crystal run ../../src/crytic.cr -- #{args}",
109111
output: io,
110112
error: io,
111113
shell: true,

src/crytic/cli.cr

Lines changed: 6 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,6 @@
11
require "./command/*"
2+
require "./runner/parallel"
3+
require "./runner/sequential"
24
require "./side_effects"
35

46
module Crytic
@@ -10,13 +12,15 @@ module Crytic
1012
def run(args)
1113
case args.first?
1214
when "test"
13-
Command::Test.new(@side_effects).execute(args.tap(&.shift))
15+
Command::Test.new(Runner::Sequential.new, @side_effects).execute(args.tap(&.shift))
16+
when "test-parallel"
17+
Command::Test.new(Runner::Parallel.new, @side_effects).execute(args.tap(&.shift))
1418
when "noop"
1519
Command::Noop
1620
.new(@side_effects, Command::Noop::DEFAULT_SPEC_FILES_GLOB)
1721
.execute(args.tap(&.shift))
1822
else
19-
Command::Test.new(@side_effects).execute(args)
23+
Command::Test.new(Runner::Sequential.new, @side_effects).execute(args)
2024
end
2125
end
2226
end

src/crytic/cli_options.cr

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -14,6 +14,7 @@ module Crytic
1414
@preamble = Generator::Generator::DEFAULT_PREAMBLE
1515
@spec_files = [] of String
1616
@subject = [] of String
17+
getter multi_threaded : Bool = false
1718

1819
def initialize(@side_effects : SideEffects, @spec_files_glob : String)
1920
@reporters << Reporter::IoReporter.new(@side_effects.std_out)

src/crytic/command/test.cr

Lines changed: 3 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -2,13 +2,13 @@ require "../cli_options"
22
require "../generator/in_memory_generator"
33
require "../generator/isolated_mutation_factory"
44
require "../mutation/no_mutation"
5-
require "../runner/parallel"
65
require "../runner/run"
6+
require "../runner/runner"
77
require "../side_effects"
88
require "../subject"
99

1010
class Crytic::Command::Test
11-
def initialize(@side_effects : SideEffects)
11+
def initialize(@runner : Runner::Runner, @side_effects : SideEffects)
1212
end
1313

1414
def execute(args)
@@ -18,9 +18,7 @@ class Crytic::Command::Test
1818
Mutation::NoMutation.with(specs)
1919
}
2020

21-
Crytic::Runner::Parallel
22-
.new
23-
.run(Crytic::Runner::Run.from_options(options, generator, factory), @side_effects)
21+
@runner.run(Crytic::Runner::Run.from_options(options, generator, factory), @side_effects)
2422
end
2523

2624
private def parse_options(args)

src/crytic/runner/parallel.cr

Lines changed: 4 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,8 @@
1+
require "./runner"
2+
13
module Crytic::Runner
2-
class Parallel
3-
def run(run, side_effects)
4+
class Parallel < Runner
5+
def run(run, side_effects) : Bool
46
original_result = run.execute_original_test_suite(side_effects)
57

68
return false unless original_result.successful?

src/crytic/runner/sequential.cr

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,9 +1,10 @@
11
require "../mutation/result"
22
require "../mutation/result_set"
33
require "./run"
4+
require "./runner"
45

56
module Crytic::Runner
6-
class Sequential
7+
class Sequential < Runner
78
def run(run, side_effects) : Bool
89
original_result = run.execute_original_test_suite(side_effects)
910

0 commit comments

Comments
 (0)