mirror of
https://gitea.invidious.io/iv-org/shard-ameba.git
synced 2024-08-15 00:53:29 +00:00
1086 lines
27 KiB
Crystal
1086 lines
27 KiB
Crystal
require "../../../spec_helper"
|
|
|
|
module Ameba::Rule::Lint
|
|
describe UselessAssign do
|
|
subject = UselessAssign.new
|
|
.tap(&.exclude_type_declarations = false)
|
|
|
|
it "does not report used assignments" do
|
|
expect_no_issues subject, <<-CRYSTAL
|
|
def method
|
|
a = 2
|
|
a
|
|
end
|
|
CRYSTAL
|
|
end
|
|
|
|
it "reports a useless assignment in a method" do
|
|
expect_issue subject, <<-CRYSTAL
|
|
def method
|
|
a = 2
|
|
# ^ error: Useless assignment to variable `a`
|
|
end
|
|
CRYSTAL
|
|
end
|
|
|
|
it "reports a useless assignment in a proc" do
|
|
expect_issue subject, <<-CRYSTAL
|
|
->() {
|
|
a = 2
|
|
# ^ error: Useless assignment to variable `a`
|
|
}
|
|
CRYSTAL
|
|
end
|
|
|
|
it "reports a useless assignment in a block" do
|
|
expect_issue subject, <<-CRYSTAL
|
|
def method
|
|
3.times do
|
|
a = 1
|
|
# ^ error: Useless assignment to variable `a`
|
|
end
|
|
end
|
|
CRYSTAL
|
|
end
|
|
|
|
it "reports a useless assignment in a proc inside def" do
|
|
expect_issue subject, <<-CRYSTAL
|
|
def method
|
|
->() {
|
|
a = 2
|
|
# ^ error: Useless assignment to variable `a`
|
|
}
|
|
end
|
|
CRYSTAL
|
|
end
|
|
|
|
it "does not report ignored assignments" do
|
|
expect_no_issues subject, <<-CRYSTAL
|
|
payload, _header = decode
|
|
puts payload
|
|
CRYSTAL
|
|
end
|
|
|
|
it "reports a useless assignment in a proc inside a block" do
|
|
expect_issue subject, <<-CRYSTAL
|
|
def method
|
|
3.times do
|
|
->() {
|
|
a = 2
|
|
# ^ error: Useless assignment to variable `a`
|
|
}
|
|
end
|
|
end
|
|
CRYSTAL
|
|
end
|
|
|
|
it "does not report useless assignment of instance var" do
|
|
expect_no_issues subject, <<-CRYSTAL
|
|
class Cls
|
|
def initialize(@name)
|
|
end
|
|
end
|
|
CRYSTAL
|
|
end
|
|
|
|
it "does not report if assignment used in the inner block scope" do
|
|
expect_no_issues subject, <<-CRYSTAL
|
|
def method
|
|
var = true
|
|
3.times { var = false }
|
|
end
|
|
CRYSTAL
|
|
end
|
|
|
|
it "reports if assigned is not referenced in the inner block scope" do
|
|
expect_issue subject, <<-CRYSTAL
|
|
def method
|
|
var = true
|
|
# ^^^ error: Useless assignment to variable `var`
|
|
3.times {}
|
|
end
|
|
CRYSTAL
|
|
end
|
|
|
|
it "doesn't report if assignment in referenced in inner block" do
|
|
expect_no_issues subject, <<-CRYSTAL
|
|
def method
|
|
two = true
|
|
|
|
3.times do
|
|
mutex.synchronize do
|
|
two = 2
|
|
end
|
|
end
|
|
|
|
two.should be_true
|
|
end
|
|
CRYSTAL
|
|
end
|
|
|
|
it "reports if first assignment is useless" do
|
|
expect_issue subject, <<-CRYSTAL
|
|
def method
|
|
var = true
|
|
# ^^^ error: Useless assignment to variable `var`
|
|
var = false
|
|
var
|
|
end
|
|
CRYSTAL
|
|
end
|
|
|
|
it "reports if variable reassigned and not used" do
|
|
expect_issue subject, <<-CRYSTAL
|
|
def method
|
|
var = true
|
|
# ^^^ error: Useless assignment to variable `var`
|
|
var = false
|
|
# ^^^ error: Useless assignment to variable `var`
|
|
end
|
|
CRYSTAL
|
|
end
|
|
|
|
it "does not report if variable used in a condition" do
|
|
expect_no_issues subject, <<-CRYSTAL
|
|
def method
|
|
a = 1
|
|
if a
|
|
nil
|
|
end
|
|
end
|
|
CRYSTAL
|
|
end
|
|
|
|
it "reports second assignment as useless" do
|
|
expect_issue subject, <<-CRYSTAL
|
|
def method
|
|
a = 1
|
|
a = a + 1
|
|
# ^ error: Useless assignment to variable `a`
|
|
end
|
|
CRYSTAL
|
|
end
|
|
|
|
it "does not report if variable is referenced in other assignment" do
|
|
expect_no_issues subject, <<-CRYSTAL
|
|
def method
|
|
if f = get_something
|
|
@f = f
|
|
end
|
|
end
|
|
CRYSTAL
|
|
end
|
|
|
|
it "does not report if variable is referenced in a setter" do
|
|
expect_no_issues subject, <<-CRYSTAL
|
|
def method
|
|
foo = 2
|
|
table[foo] ||= "bar"
|
|
end
|
|
CRYSTAL
|
|
end
|
|
|
|
it "does not report if variable is reassigned but not referenced" do
|
|
expect_issue subject, <<-CRYSTAL
|
|
def method
|
|
foo = 1
|
|
puts foo
|
|
foo = 2
|
|
# ^^^ error: Useless assignment to variable `foo`
|
|
end
|
|
CRYSTAL
|
|
end
|
|
|
|
it "does not report if variable is referenced in a call" do
|
|
expect_no_issues subject, <<-CRYSTAL
|
|
def method
|
|
if f = FORMATTER
|
|
@formatter = f.new
|
|
end
|
|
end
|
|
CRYSTAL
|
|
end
|
|
|
|
it "does not report if a setter is invoked with operator assignment" do
|
|
expect_no_issues subject, <<-CRYSTAL
|
|
def method
|
|
obj = {} of Symbol => Int32
|
|
obj[:name] = 3
|
|
end
|
|
CRYSTAL
|
|
end
|
|
|
|
context "block unpacking" do
|
|
it "does not report if the first arg is transformed and not used" do
|
|
expect_no_issues subject, <<-CRYSTAL
|
|
collection.each do |(a, b)|
|
|
puts b
|
|
end
|
|
CRYSTAL
|
|
end
|
|
|
|
it "does not report if the second arg is transformed and not used" do
|
|
expect_no_issues subject, <<-CRYSTAL
|
|
collection.each do |(a, b)|
|
|
puts a
|
|
end
|
|
CRYSTAL
|
|
end
|
|
|
|
it "does not report if all transformed args are not used in a block" do
|
|
expect_no_issues subject, <<-CRYSTAL
|
|
collection.each do |(foo, bar), (baz, _qux), index, object|
|
|
end
|
|
CRYSTAL
|
|
end
|
|
end
|
|
|
|
it "does not report if assignment is referenced in a proc" do
|
|
expect_no_issues subject, <<-CRYSTAL
|
|
def method
|
|
called = false
|
|
->() { called = true }
|
|
called
|
|
end
|
|
CRYSTAL
|
|
end
|
|
|
|
it "reports if variable is shadowed in inner scope" do
|
|
expect_issue subject, <<-CRYSTAL
|
|
def method
|
|
i = 1
|
|
# ^ error: Useless assignment to variable `i`
|
|
3.times do |i|
|
|
i + 1
|
|
end
|
|
end
|
|
CRYSTAL
|
|
end
|
|
|
|
it "does not report if parameter is referenced after the branch" do
|
|
expect_no_issues subject, <<-CRYSTAL
|
|
def method(param)
|
|
3.times do
|
|
param = 3
|
|
end
|
|
param
|
|
end
|
|
CRYSTAL
|
|
end
|
|
|
|
context "op assigns" do
|
|
it "does not report if variable is referenced below the op assign" do
|
|
expect_no_issues subject, <<-CRYSTAL
|
|
def method
|
|
a = 1
|
|
a += 1
|
|
a
|
|
end
|
|
CRYSTAL
|
|
end
|
|
|
|
it "does not report if variable is referenced in op assign few times" do
|
|
expect_no_issues subject, <<-CRYSTAL
|
|
def method
|
|
a = 1
|
|
a += 1
|
|
a += 1
|
|
a = a + 1
|
|
a
|
|
end
|
|
CRYSTAL
|
|
end
|
|
|
|
it "reports if variable is not referenced below the op assign" do
|
|
expect_issue subject, <<-CRYSTAL
|
|
def method
|
|
a = 1
|
|
a += 1
|
|
# ^ error: Useless assignment to variable `a`
|
|
end
|
|
CRYSTAL
|
|
end
|
|
end
|
|
|
|
context "multi assigns" do
|
|
it "does not report if all assigns are referenced" do
|
|
expect_no_issues subject, <<-CRYSTAL
|
|
def method
|
|
a, b = {1, 2}
|
|
a + b
|
|
end
|
|
CRYSTAL
|
|
end
|
|
|
|
it "reports if one assign is not referenced" do
|
|
expect_issue subject, <<-CRYSTAL
|
|
def method
|
|
a, b = {1, 2}
|
|
# ^ error: Useless assignment to variable `b`
|
|
a
|
|
end
|
|
CRYSTAL
|
|
end
|
|
|
|
it "reports if both assigns are reassigned and useless" do
|
|
expect_issue subject, <<-CRYSTAL
|
|
def method
|
|
a, b = {1, 2}
|
|
# ^ error: Useless assignment to variable `a`
|
|
# ^ error: Useless assignment to variable `b`
|
|
a, b = {3, 4}
|
|
# ^ error: Useless assignment to variable `a`
|
|
# ^ error: Useless assignment to variable `b`
|
|
end
|
|
CRYSTAL
|
|
end
|
|
|
|
it "reports if both assigns are not referenced" do
|
|
expect_issue subject, <<-CRYSTAL
|
|
def method
|
|
a, b = {1, 2}
|
|
# ^ error: Useless assignment to variable `a`
|
|
# ^ error: Useless assignment to variable `b`
|
|
end
|
|
CRYSTAL
|
|
end
|
|
end
|
|
|
|
context "top level" do
|
|
it "reports if assignment is not referenced" do
|
|
expect_issue subject, <<-CRYSTAL
|
|
a = 1
|
|
# ^{} error: Useless assignment to variable `a`
|
|
a = 2
|
|
# ^{} error: Useless assignment to variable `a`
|
|
CRYSTAL
|
|
end
|
|
|
|
it "doesn't report if assignments are referenced" do
|
|
expect_no_issues subject, <<-CRYSTAL
|
|
a = 1
|
|
a += 1
|
|
a
|
|
|
|
b, c = {1, 2}
|
|
b
|
|
c
|
|
CRYSTAL
|
|
end
|
|
|
|
it "doesn't report if assignment is captured by block" do
|
|
expect_no_issues subject, <<-CRYSTAL
|
|
a = 1
|
|
|
|
3.times do
|
|
a = 2
|
|
end
|
|
CRYSTAL
|
|
end
|
|
|
|
it "doesn't report if assignment initialized and captured by block" do
|
|
expect_no_issues subject, <<-CRYSTAL
|
|
a : String? = nil
|
|
|
|
1.times do
|
|
a = "Fotis"
|
|
end
|
|
CRYSTAL
|
|
end
|
|
|
|
it "doesn't report record declaration" do
|
|
expect_no_issues subject, <<-CRYSTAL
|
|
record Foo, foo : String
|
|
record Foo, foo = "foo"
|
|
CRYSTAL
|
|
end
|
|
|
|
it "doesn't report record declarations (generics)" do
|
|
expect_no_issues subject, <<-CRYSTAL
|
|
record Foo(T), foo : T
|
|
record Foo(T), foo = T.new
|
|
CRYSTAL
|
|
end
|
|
|
|
pending "doesn't report type declaration as a call argument" do
|
|
expect_no_issues subject, <<-CRYSTAL
|
|
foo Foo(T), foo : T
|
|
foo Foo, foo : Nil
|
|
foo foo : String
|
|
foo foo : String, bar : Int32?, baz : Bool
|
|
CRYSTAL
|
|
end
|
|
|
|
it "doesn't report accessor declarations" do
|
|
accessor_macros = %w[setter class_setter]
|
|
%w[getter class_getter property class_property].each do |name|
|
|
accessor_macros << name
|
|
accessor_macros << "#{name}?"
|
|
accessor_macros << "#{name}!"
|
|
end
|
|
accessor_macros.each do |accessor|
|
|
expect_no_issues subject, <<-CRYSTAL
|
|
class Foo
|
|
#{accessor} foo : String?
|
|
#{accessor} bar = "bar"
|
|
end
|
|
CRYSTAL
|
|
end
|
|
end
|
|
|
|
it "does not report if assignment is referenced after the record declaration" do
|
|
expect_no_issues subject, <<-CRYSTAL
|
|
foo = 2
|
|
record Bar, foo = 3 # foo = 3 is not parsed as assignment
|
|
puts foo
|
|
CRYSTAL
|
|
end
|
|
|
|
it "reports if assignment is not referenced after the record declaration" do
|
|
expect_issue subject, <<-CRYSTAL
|
|
foo = 2
|
|
# ^ error: Useless assignment to variable `foo`
|
|
record Bar, foo = 3
|
|
CRYSTAL
|
|
end
|
|
|
|
it "doesn't report if type declaration assigned inside module and referenced" do
|
|
expect_no_issues subject, <<-CRYSTAL
|
|
module A
|
|
foo : String? = "foo"
|
|
|
|
bar do
|
|
foo = "bar"
|
|
end
|
|
|
|
p foo
|
|
end
|
|
CRYSTAL
|
|
end
|
|
|
|
it "reports if type declaration assigned inside class" do
|
|
expect_issue subject, <<-CRYSTAL
|
|
class A
|
|
foo : String? = "foo"
|
|
# ^^^ error: Useless assignment to variable `foo`
|
|
|
|
def method
|
|
foo = "bar"
|
|
# ^^^ error: Useless assignment to variable `foo`
|
|
end
|
|
end
|
|
CRYSTAL
|
|
end
|
|
end
|
|
|
|
context "branching" do
|
|
context "if-then-else" do
|
|
it "doesn't report if assignment is consumed by branches" do
|
|
expect_no_issues subject, <<-CRYSTAL
|
|
def method
|
|
a = 0
|
|
if something
|
|
a = 1
|
|
else
|
|
a = 2
|
|
end
|
|
a
|
|
end
|
|
CRYSTAL
|
|
end
|
|
|
|
it "doesn't report if assignment is in one branch" do
|
|
expect_no_issues subject, <<-CRYSTAL
|
|
def method
|
|
a = 0
|
|
if something
|
|
a = 1
|
|
else
|
|
nil
|
|
end
|
|
a
|
|
end
|
|
CRYSTAL
|
|
end
|
|
|
|
it "doesn't report if assignment is in one line branch" do
|
|
expect_no_issues subject, <<-CRYSTAL
|
|
def method
|
|
a = 0
|
|
a = 1 if something
|
|
a
|
|
end
|
|
CRYSTAL
|
|
end
|
|
|
|
it "reports if assignment is useless in the branch" do
|
|
expect_issue subject, <<-CRYSTAL
|
|
def method(a)
|
|
if a
|
|
a = 2
|
|
# ^ error: Useless assignment to variable `a`
|
|
end
|
|
end
|
|
CRYSTAL
|
|
end
|
|
|
|
it "reports if only last assignment is referenced in a branch" do
|
|
expect_issue subject, <<-CRYSTAL
|
|
def method(a)
|
|
a = 1
|
|
if a
|
|
a = 2
|
|
# ^ error: Useless assignment to variable `a`
|
|
a = 3
|
|
end
|
|
a
|
|
end
|
|
CRYSTAL
|
|
end
|
|
|
|
it "does not report of assignments are referenced in all branches" do
|
|
expect_no_issues subject, <<-CRYSTAL
|
|
def method
|
|
if matches
|
|
matches = owner.lookup_matches signature
|
|
else
|
|
matches = owner.lookup_matches signature
|
|
end
|
|
matches
|
|
end
|
|
CRYSTAL
|
|
end
|
|
|
|
it "does not report referenced assignments in inner branches" do
|
|
expect_no_issues subject, <<-CRYSTAL
|
|
def method
|
|
has_newline = false
|
|
|
|
if something
|
|
do_something unless false
|
|
has_newline = false
|
|
else
|
|
do_something if true
|
|
has_newline = true
|
|
end
|
|
|
|
has_newline
|
|
end
|
|
CRYSTAL
|
|
end
|
|
end
|
|
|
|
context "unless-then-else" do
|
|
it "doesn't report if assignment is consumed by branches" do
|
|
expect_no_issues subject, <<-CRYSTAL
|
|
def method
|
|
a = 0
|
|
unless something
|
|
a = 1
|
|
else
|
|
a = 2
|
|
end
|
|
a
|
|
end
|
|
CRYSTAL
|
|
end
|
|
|
|
it "reports if there is a useless assignment in a branch" do
|
|
expect_issue subject, <<-CRYSTAL
|
|
def method
|
|
a = 0
|
|
unless something
|
|
a = 1
|
|
# ^ error: Useless assignment to variable `a`
|
|
a = 2
|
|
else
|
|
a = 2
|
|
end
|
|
a
|
|
end
|
|
CRYSTAL
|
|
end
|
|
end
|
|
|
|
context "case" do
|
|
it "does not report if assignment is referenced" do
|
|
expect_no_issues subject, <<-CRYSTAL
|
|
def method(a)
|
|
case a
|
|
when /foo/
|
|
a = 1
|
|
when /bar/
|
|
a = 2
|
|
end
|
|
puts a
|
|
end
|
|
CRYSTAL
|
|
end
|
|
|
|
it "reports if assignment is useless" do
|
|
expect_issue subject, <<-CRYSTAL
|
|
def method(a)
|
|
case a
|
|
when /foo/
|
|
a = 1
|
|
# ^ error: Useless assignment to variable `a`
|
|
when /bar/
|
|
a = 2
|
|
# ^ error: Useless assignment to variable `a`
|
|
end
|
|
end
|
|
CRYSTAL
|
|
end
|
|
|
|
it "doesn't report if assignment is referenced in cond" do
|
|
expect_no_issues subject, <<-CRYSTAL
|
|
def method
|
|
a = 2
|
|
case a
|
|
when /foo/
|
|
end
|
|
end
|
|
CRYSTAL
|
|
end
|
|
end
|
|
|
|
context "binary operator" do
|
|
it "does not report if assignment is referenced" do
|
|
expect_no_issues subject, <<-CRYSTAL
|
|
def method(a)
|
|
(a = 1) && (b = 1)
|
|
a + b
|
|
end
|
|
CRYSTAL
|
|
end
|
|
|
|
it "reports if assignment is useless" do
|
|
expect_issue subject, <<-CRYSTAL
|
|
def method(a)
|
|
(a = 1) || (b = 1)
|
|
# ^ error: Useless assignment to variable `b`
|
|
a
|
|
end
|
|
CRYSTAL
|
|
end
|
|
end
|
|
|
|
context "while" do
|
|
it "does not report if assignment is referenced" do
|
|
expect_no_issues subject, <<-CRYSTAL
|
|
def method(a)
|
|
while a < 10
|
|
a = a + 1
|
|
end
|
|
a
|
|
end
|
|
CRYSTAL
|
|
end
|
|
|
|
it "reports if assignment is useless" do
|
|
expect_issue subject, <<-CRYSTAL
|
|
def method(a)
|
|
while a < 10
|
|
b = a
|
|
# ^ error: Useless assignment to variable `b`
|
|
end
|
|
end
|
|
CRYSTAL
|
|
end
|
|
|
|
it "does not report if assignment is referenced in a loop" do
|
|
expect_no_issues subject, <<-CRYSTAL
|
|
def method
|
|
a = 3
|
|
result = 0
|
|
|
|
while result < 10
|
|
result += a
|
|
a = a + 1
|
|
end
|
|
result
|
|
end
|
|
CRYSTAL
|
|
end
|
|
|
|
it "does not report if assignment is referenced as param in a loop" do
|
|
expect_no_issues subject, <<-CRYSTAL
|
|
def method(a)
|
|
result = 0
|
|
|
|
while result < 10
|
|
result += a
|
|
a = a + 1
|
|
end
|
|
result
|
|
end
|
|
CRYSTAL
|
|
end
|
|
|
|
it "does not report if assignment is referenced in loop and inner branch" do
|
|
expect_no_issues subject, <<-CRYSTAL
|
|
def method(a)
|
|
result = 0
|
|
|
|
while result < 10
|
|
result += a
|
|
if result > 0
|
|
a = a + 1
|
|
else
|
|
a = 3
|
|
end
|
|
end
|
|
result
|
|
end
|
|
CRYSTAL
|
|
end
|
|
|
|
it "works properly if there is branch with blank node" do
|
|
expect_no_issues subject, <<-CRYSTAL
|
|
def visit
|
|
count = 0
|
|
while true
|
|
break if count == 1
|
|
case something
|
|
when :any
|
|
else
|
|
:anything_else
|
|
end
|
|
count += 1
|
|
end
|
|
end
|
|
CRYSTAL
|
|
end
|
|
end
|
|
|
|
context "until" do
|
|
it "does not report if assignment is referenced" do
|
|
expect_no_issues subject, <<-CRYSTAL
|
|
def method(a)
|
|
until a > 10
|
|
a = a + 1
|
|
end
|
|
a
|
|
end
|
|
CRYSTAL
|
|
end
|
|
|
|
it "reports if assignment is useless" do
|
|
expect_issue subject, <<-CRYSTAL
|
|
def method(a)
|
|
until a > 10
|
|
b = a + 1
|
|
# ^ error: Useless assignment to variable `b`
|
|
end
|
|
end
|
|
CRYSTAL
|
|
end
|
|
end
|
|
|
|
context "exception handler" do
|
|
it "does not report if assignment is referenced in body" do
|
|
expect_no_issues subject, <<-CRYSTAL
|
|
def method(a)
|
|
a = 2
|
|
rescue
|
|
a
|
|
end
|
|
CRYSTAL
|
|
end
|
|
|
|
it "doesn't report if assignment is referenced in ensure" do
|
|
expect_no_issues subject, <<-CRYSTAL
|
|
def method(a)
|
|
a = 2
|
|
ensure
|
|
a
|
|
end
|
|
CRYSTAL
|
|
end
|
|
|
|
it "doesn't report if assignment is referenced in else" do
|
|
expect_no_issues subject, <<-CRYSTAL
|
|
def method(a)
|
|
a = 2
|
|
rescue
|
|
else
|
|
a
|
|
end
|
|
CRYSTAL
|
|
end
|
|
|
|
it "reports if assignment is useless" do
|
|
expect_issue subject, <<-CRYSTAL
|
|
def method(a)
|
|
rescue
|
|
a = 2
|
|
# ^ error: Useless assignment to variable `a`
|
|
end
|
|
CRYSTAL
|
|
end
|
|
end
|
|
end
|
|
|
|
context "typeof" do
|
|
it "reports useless assignments in typeof" do
|
|
expect_issue subject, <<-CRYSTAL
|
|
typeof(begin
|
|
foo = 1
|
|
# ^^^ error: Useless assignment to variable `foo`
|
|
bar = 2
|
|
# ^^^ error: Useless assignment to variable `bar`
|
|
end)
|
|
CRYSTAL
|
|
end
|
|
end
|
|
|
|
context "macro" do
|
|
it "doesn't report if assignment is referenced in macro" do
|
|
expect_no_issues subject, <<-CRYSTAL
|
|
def method
|
|
a = 2
|
|
{% if flag?(:bits64) %}
|
|
a.to_s
|
|
{% else %}
|
|
a
|
|
{% end %}
|
|
end
|
|
CRYSTAL
|
|
end
|
|
|
|
it "doesn't report referenced assignments in macro literal" do
|
|
expect_no_issues subject, <<-CRYSTAL
|
|
def method
|
|
a = 2
|
|
{% if flag?(:bits64) %}
|
|
a = 3
|
|
{% else %}
|
|
a = 4
|
|
{% end %}
|
|
puts a
|
|
end
|
|
CRYSTAL
|
|
end
|
|
|
|
it "doesn't report if assignment is referenced in macro def" do
|
|
expect_no_issues subject, <<-CRYSTAL
|
|
macro macro_call
|
|
puts x
|
|
end
|
|
|
|
def foo
|
|
x = 1
|
|
macro_call
|
|
end
|
|
CRYSTAL
|
|
end
|
|
|
|
it "doesn't report if assignment is referenced in a macro below" do
|
|
expect_no_issues subject, <<-CRYSTAL
|
|
class Foo
|
|
def foo
|
|
a = 1
|
|
macro_call
|
|
end
|
|
|
|
macro macro_call
|
|
puts a
|
|
end
|
|
end
|
|
CRYSTAL
|
|
end
|
|
|
|
it "doesn't report if assignment is referenced in a macro expression as string" do
|
|
expect_no_issues subject, <<-CRYSTAL
|
|
foo = 1
|
|
puts {{ "foo".id }}
|
|
CRYSTAL
|
|
end
|
|
|
|
it "doesn't report if assignment is referenced in for macro in exp" do
|
|
expect_no_issues subject, <<-CRYSTAL
|
|
foo = 22
|
|
|
|
{% for x in %w[foo] %}
|
|
add({{ x.id }})
|
|
{% end %}
|
|
CRYSTAL
|
|
end
|
|
|
|
it "doesn't report if assignment is referenced in for macro in body" do
|
|
expect_no_issues subject, <<-CRYSTAL
|
|
foo = 22
|
|
|
|
{% for x in %w[bar] %}
|
|
puts {{ "foo".id }}
|
|
{% end %}
|
|
CRYSTAL
|
|
end
|
|
|
|
it "doesn't report if assignment is referenced in if macro in cond" do
|
|
expect_no_issues subject, <<-CRYSTAL
|
|
foo = 22
|
|
|
|
{% if "foo".id %}
|
|
{% end %}
|
|
CRYSTAL
|
|
end
|
|
|
|
it "doesn't report if assignment is referenced in if macro in then" do
|
|
expect_no_issues subject, <<-CRYSTAL
|
|
foo = 22
|
|
|
|
{% if true %}
|
|
puts {{ "foo".id }}
|
|
{% end %}
|
|
CRYSTAL
|
|
end
|
|
|
|
it "doesn't report if assignment is referenced in if macro in else" do
|
|
expect_no_issues subject, <<-CRYSTAL
|
|
foo = 22
|
|
|
|
{% if true %}
|
|
{% else %}
|
|
puts {{ "foo".id }}
|
|
{% end %}
|
|
CRYSTAL
|
|
end
|
|
end
|
|
|
|
it "does not report if variable is referenced and there is a deep level scope" do
|
|
expect_no_issues subject, <<-CRYSTAL
|
|
response = JSON.build do |json|
|
|
json.object do
|
|
json.object do
|
|
json.object do
|
|
json.object do
|
|
json.object do
|
|
json.object do
|
|
json.object do
|
|
json.object do
|
|
json.object do
|
|
json.object do
|
|
json.object do
|
|
json.object do
|
|
json.object do
|
|
json.object do
|
|
json.object do
|
|
anything
|
|
end
|
|
end
|
|
end
|
|
end
|
|
end
|
|
end
|
|
end
|
|
end
|
|
end
|
|
end
|
|
end
|
|
end
|
|
end
|
|
end
|
|
end
|
|
end
|
|
|
|
response = JSON.parse(response)
|
|
response
|
|
CRYSTAL
|
|
end
|
|
|
|
context "type declaration" do
|
|
it "reports if it's not referenced at a top level" do
|
|
expect_issue subject, <<-CRYSTAL
|
|
a : String?
|
|
# ^{} error: Useless assignment to variable `a`
|
|
CRYSTAL
|
|
end
|
|
|
|
it "reports if it's not referenced in a method" do
|
|
expect_issue subject, <<-CRYSTAL
|
|
def foo
|
|
a : String?
|
|
# ^ error: Useless assignment to variable `a`
|
|
end
|
|
CRYSTAL
|
|
end
|
|
|
|
it "reports if it's not referenced in a class" do
|
|
expect_issue subject, <<-CRYSTAL
|
|
class Foo
|
|
a : String?
|
|
# ^ error: Useless assignment to variable `a`
|
|
end
|
|
CRYSTAL
|
|
end
|
|
|
|
it "doesn't report if it's referenced in a lib" do
|
|
expect_no_issues subject, <<-CRYSTAL
|
|
lib LibFoo
|
|
struct Foo
|
|
a : Int32
|
|
end
|
|
end
|
|
CRYSTAL
|
|
end
|
|
|
|
it "doesn't report if it's referenced" do
|
|
expect_no_issues subject, <<-CRYSTAL
|
|
def foo
|
|
a : String?
|
|
a
|
|
end
|
|
CRYSTAL
|
|
end
|
|
end
|
|
|
|
context "#properties" do
|
|
context "#exclude_type_declarations" do
|
|
it "doesn't report type declarations if enabled" do
|
|
rule = UselessAssign.new
|
|
rule.exclude_type_declarations = true
|
|
|
|
expect_no_issues rule, <<-CRYSTAL
|
|
a : String?
|
|
|
|
class Foo
|
|
b : String?
|
|
end
|
|
|
|
def foo
|
|
c : String?
|
|
end
|
|
CRYSTAL
|
|
end
|
|
end
|
|
end
|
|
|
|
context "uninitialized" do
|
|
it "reports if uninitialized assignment is not referenced at a top level" do
|
|
expect_issue subject, <<-CRYSTAL
|
|
a = uninitialized U
|
|
# ^{} error: Useless assignment to variable `a`
|
|
CRYSTAL
|
|
end
|
|
|
|
it "reports if uninitialized assignment is not referenced in a method" do
|
|
expect_issue subject, <<-CRYSTAL
|
|
def foo
|
|
a = uninitialized U
|
|
# ^ error: Useless assignment to variable `a`
|
|
end
|
|
CRYSTAL
|
|
end
|
|
|
|
it "doesn't report if uninitialized assignment is referenced" do
|
|
expect_no_issues subject, <<-CRYSTAL
|
|
def foo
|
|
a = uninitialized U
|
|
a
|
|
end
|
|
CRYSTAL
|
|
end
|
|
end
|
|
end
|
|
end
|