Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Add expect_issue and expect_no_issues spec helpers #245

Merged
merged 14 commits into from
Oct 22, 2021
Merged
Show file tree
Hide file tree
Changes from 10 commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
7 changes: 3 additions & 4 deletions spec/ameba/rule/lint/debugger_statement_spec.cr
Original file line number Diff line number Diff line change
Expand Up @@ -5,7 +5,7 @@ module Ameba::Rule::Lint

describe DebuggerStatement do
it "passes if there is no debugger statement" do
s = Source.new %(
expect_no_issues subject, %(
"this is not a debugger statement"
s = "debugger"

Expand All @@ -19,16 +19,15 @@ module Ameba::Rule::Lint
end
A.new.debugger
)
subject.catch(s).should be_valid
end

it "fails if there is a debugger statement" do
s = Source.new %(
expect_issue subject, %(
a = 2
debugger
# ^{} error: Possible forgotten debugger statement detected
a = a + 1
)
subject.catch(s).should_not be_valid
end

it "reports rule, pos and message" do
Expand Down
7 changes: 3 additions & 4 deletions spec/ameba/rule/lint/duplicated_require_spec.cr
Original file line number Diff line number Diff line change
Expand Up @@ -5,21 +5,20 @@ module Ameba::Rule::Lint

describe DuplicatedRequire do
it "passes if there are no duplicated requires" do
source = Source.new %(
expect_no_issues subject, %(
require "math"
require "big"
require "big/big_decimal"
)
subject.catch(source).should be_valid
end

it "reports if there are a duplicated requires" do
source = Source.new %(
expect_issue subject, %(
require "big"
require "math"
require "big"
# ^{} error: Duplicated require of `big`
)
subject.catch(source).should_not be_valid
end

it "reports rule, pos and message" do
Expand Down
67 changes: 21 additions & 46 deletions spec/ameba/rule/lint/shared_var_in_fiber_spec.cr
Original file line number Diff line number Diff line change
Expand Up @@ -5,19 +5,18 @@ module Ameba::Rule::Lint
subject = SharedVarInFiber.new

it "doesn't report if there is only local shared var in fiber" do
s = Source.new %(
expect_no_issues subject, %(
spawn do
i = 1
puts i
end

Fiber.yield
)
subject.catch(s).should be_valid
end

it "doesn't report if there is only block shared var in fiber" do
s = Source.new %(
expect_no_issues subject, %(
10.times do |i|
spawn do
puts i
Expand All @@ -26,11 +25,10 @@ module Ameba::Rule::Lint

Fiber.yield
)
subject.catch(s).should be_valid
end

it "doesn't report if there a spawn macro is used" do
s = Source.new %(
expect_no_issues subject, %(
i = 0
while i < 10
spawn puts(i)
Expand All @@ -39,42 +37,41 @@ module Ameba::Rule::Lint

Fiber.yield
)
subject.catch(s).should be_valid
end

it "reports if there is a shared var in spawn" do
s = Source.new %(
expect_issue subject, %(
i = 0
while i < 10
spawn do
puts(i)
# ^ error: Shared variable `i` is used in fiber
end
i += 1
end

Fiber.yield
)
subject.catch(s).should_not be_valid
end

it "reports reassigned reference to shared var in spawn" do
s = Source.new %(
expect_issue subject, %(
channel = Channel(String).new
n = 0

while n < 10
n = n + 1
spawn do
m = n
# ^ error: Shared variable `n` is used in fiber
channel.send m
end
end
)
subject.catch(s).should_not be_valid
end

it "doesn't report reassigned reference to shared var in block" do
s = Source.new %(
expect_no_issues subject, %(
channel = Channel(String).new
n = 0

Expand All @@ -86,49 +83,37 @@ module Ameba::Rule::Lint
end
end
)
subject.catch(s).should be_valid
end

it "does not report block is called in a spawn" do
s = Source.new %(
expect_no_issues subject, %(
def method(block)
spawn do
block.call(10)
end
end
)
subject.catch(s).should be_valid
end

it "reports multiple shared variables in spawn" do
s = Source.new %(
expect_issue subject, %(
foo, bar, baz = 0, 0, 0
while foo < 10
baz += 1
spawn do
puts foo
# ^^^ error: Shared variable `foo` is used in fiber
puts foo + bar + baz
# ^^^ error: Shared variable `foo` is used in fiber
# ^^^ error: Shared variable `baz` is used in fiber
end
foo += 1
end
)
subject.catch(s).should_not be_valid
s.issues.size.should eq 3
s.issues[0].location.to_s.should eq ":5:10"
s.issues[0].end_location.to_s.should eq ":5:12"
s.issues[0].message.should eq "Shared variable `foo` is used in fiber"

s.issues[1].location.to_s.should eq ":6:10"
s.issues[1].end_location.to_s.should eq ":6:12"
s.issues[1].message.should eq "Shared variable `foo` is used in fiber"

s.issues[2].location.to_s.should eq ":6:22"
s.issues[2].end_location.to_s.should eq ":6:24"
s.issues[2].message.should eq "Shared variable `baz` is used in fiber"
end

it "doesn't report if variable is passed to the proc" do
s = Source.new %(
expect_no_issues subject, %(
i = 0
while i < 10
proc = ->(x : Int32) do
Expand All @@ -140,20 +125,18 @@ module Ameba::Rule::Lint
i += 1
end
)
subject.catch(s).should be_valid
end

it "doesn't report if a channel is declared in outer scope" do
s = Source.new %(
expect_no_issues subject, %(
channel = Channel(Nil).new
spawn { channel.send(nil) }
channel.receive
)
subject.catch(s).should be_valid
end

it "doesn't report if there is a loop in spawn" do
s = Source.new %(
expect_no_issues subject, %(
channel = Channel(String).new

spawn do
Expand All @@ -164,54 +147,46 @@ module Ameba::Rule::Lint
end
end
)
subject.catch(s).should be_valid
end

it "doesn't report if a var is mutated in spawn and referenced outside" do
s = Source.new %(
expect_no_issues subject, %(
def method
foo = 1
spawn { foo = 2 }
foo
end
)
subject.catch(s).should be_valid
end

it "doesn't report if variable is changed without iterations" do
s = Source.new %(
expect_no_issues subject, %(
def foo
i = 0
i += 1
spawn { i }
end
), "source.cr"

subject.catch(s).should be_valid
)
end

it "doesn't report if variable is in a loop inside spawn" do
s = Source.new %(
expect_no_issues subject, %(
i = 0
spawn do
while i < 10
i += 1
end
end
)

subject.catch(s).should be_valid
end

it "doesn't report if variable declared inside loop" do
s = Source.new %(
expect_no_issues subject, %(
while true
i = 0
spawn { i += 1 }
end
)

subject.catch(s).should be_valid
end

it "reports rule, location and message" do
Expand Down
40 changes: 15 additions & 25 deletions spec/ameba/rule/performance/any_after_filter_spec.cr
Original file line number Diff line number Diff line change
Expand Up @@ -5,76 +5,66 @@ module Ameba::Rule::Performance

describe AnyAfterFilter do
it "passes if there is no potential performance improvements" do
source = Source.new %(
expect_no_issues subject, %(
[1, 2, 3].select { |e| e > 1 }.any?(&.zero?)
[1, 2, 3].reject { |e| e > 1 }.any?(&.zero?)
[1, 2, 3].select { |e| e > 1 }
[1, 2, 3].reject { |e| e > 1 }
[1, 2, 3].any? { |e| e > 1 }
)
subject.catch(source).should be_valid
end

it "reports if there is select followed by any? without a block" do
source = Source.new %(
expect_issue subject, %(
[1, 2, 3].select { |e| e > 2 }.any?
# ^^^^^^^^^^^^^^^^^^^^^^^^^^ error: Use `any? {...}` instead of `select {...}.any?`
)
subject.catch(source).should_not be_valid
end

it "does not report if source is a spec" do
source = Source.new %(
expect_no_issues subject, %(
[1, 2, 3].select { |e| e > 2 }.any?
), "source_spec.cr"
subject.catch(source).should be_valid
end

it "reports if there is reject followed by any? without a block" do
source = Source.new %(
expect_issue subject, %(
[1, 2, 3].reject { |e| e > 2 }.any?
# ^^^^^^^^^^^^^^^^^^^^^^^^^^ error: Use `any? {...}` instead of `reject {...}.any?`
)
subject.catch(source).should_not be_valid
end

it "does not report if any? calls contains a block" do
source = Source.new %(
expect_no_issues subject, %(
[1, 2, 3].select { |e| e > 2 }.any?(&.zero?)
[1, 2, 3].reject { |e| e > 2 }.any?(&.zero?)
)
subject.catch(source).should be_valid
end

context "properties" do
it "allows to configure object_call_names" do
source = Source.new %(
[1, 2, 3].reject { |e| e > 2 }.any?
)
rule = Rule::Performance::AnyAfterFilter.new
rule.filter_names = %w(select)
rule.catch(source).should be_valid
expect_no_issues rule, %(
[1, 2, 3].reject { |e| e > 2 }.any?
)
end
end

context "macro" do
it "reports in macro scope" do
source = Source.new %(
expect_issue subject, %(
{{ [1, 2, 3].reject { |e| e > 2 }.any? }}
# ^^^^^^^^^^^^^^^^^^^^^^^^^^^ error: Use `any? {...}` instead of `reject {...}.any?`
)
subject.catch(source).should_not be_valid
end
end

it "reports rule, pos and message" do
s = Source.new %(
expect_issue subject, %(
[1, 2, 3].reject { |e| e > 2 }.any?
), "source.cr"
subject.catch(s).should_not be_valid
issue = s.issues.first

issue.rule.should_not be_nil
issue.location.to_s.should eq "source.cr:1:11"
issue.end_location.to_s.should eq "source.cr:1:36"
issue.message.should eq "Use `any? {...}` instead of `reject {...}.any?`"
# ^^^^^^^^^^^^^^^^^^^^^^^^^^ error: Use `any? {...}` instead of `reject {...}.any?`
)
end
end
end
Loading