Skip to content

Commit

Permalink
Revert "Enhance test_ambiguities (JuliaTesting#144)"
Browse files Browse the repository at this point in the history
This reverts commit f4c3352.
  • Loading branch information
lgoettgens authored Jun 26, 2023
1 parent f4c3352 commit 295c0ce
Show file tree
Hide file tree
Showing 4 changed files with 33 additions and 96 deletions.
2 changes: 1 addition & 1 deletion Project.toml
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
name = "Aqua"
uuid = "4c88cf16-eb10-579e-8560-4a9242c79595"
authors = ["Takafumi Arakaki <[email protected]> and contributors"]
version = "0.7.0-DEV"
version = "0.6.4"

[deps]
Compat = "34da2185-b29b-5c13-b0c7-acf172513d20"
Expand Down
21 changes: 10 additions & 11 deletions src/ambiguities.jl
Original file line number Diff line number Diff line change
Expand Up @@ -15,9 +15,10 @@ false-positive.
- `exclude::AbstractVector = []`: A vector of functions or types to be
excluded from ambiguity testing. A function means to exclude _all_
its methods. A type means to exclude _all_ its methods of the
callable (sometimes also called "functor") and the constructor.
That is to say, `MyModule.MyType` means to ignore ambiguities between
`(::MyType)(x, y::Int)` and `(::MyType)(x::Int, y)`.
callable (sometimes also called "functor"). That is to say,
`MyModule.MyType` means to ignore ambiguities between `(::MyType)(x,
y::Int)` and `(::MyType)(x::Int, y)`. Note that there is no way to
exclude the constructor of a specific type at the moment.
- `recursive::Bool = true`: Passed to `Test.detect_ambiguities`.
Note that the default here (`true`) is different from
`detect_ambiguities`. This is for testing ambiguities in methods
Expand Down Expand Up @@ -164,6 +165,7 @@ end

struct _NoValue end

# FIXME: This does not support non-singleton callables.
function getobj(m::Method)
ty = try
fieldtype(m.sig, 1)
Expand All @@ -177,17 +179,13 @@ function getobj(m::Method)
return _NoValue()
end
ty = Base.unwrap_unionall(ty)
if ty <: Function
try
return ty.instance # this should work for functions
catch
end
try
return ty.instance # this should work for singletons (e.g., functions)
catch
end
try
if ty.name.wrapper === Type
return ty.parameters[1]
else
return ty.name.wrapper
end
catch err
@error(
Expand All @@ -210,7 +208,8 @@ function test_ambiguities_impl(
if !isempty(exspecs)
exclude_objs = getobj.(exspecs)
ambiguities = filter(ambiguities) do (m1, m2)
getobj(m1) exclude_objs && getobj(m2) exclude_objs
# `getobj(m1) == getobj(m2)` so no need to check `m2`
getobj(m1) exclude_objs
end
end

Expand Down
35 changes: 4 additions & 31 deletions test/pkgs/PkgWithAmbiguities.jl
Original file line number Diff line number Diff line change
@@ -1,40 +1,13 @@
module PkgWithAmbiguities

# 1 ambiguity
f(::Any, ::Int) = 1
f(::Int, ::Any) = 2

abstract type AbstractType end
struct SingletonType <: AbstractType end

struct ConcreteType <: AbstractType
x::Int
end

# 2 ambiguities
SingletonType(::Any, ::Any, ::Int) = 1
SingletonType(::Any, ::Int, ::Int) = 2
SingletonType(::Int, ::Any, ::Any) = 3

# 1 ambiguity
(::SingletonType)(::Any, ::Float64) = 1
(::SingletonType)(::Float64, ::Any) = 2

# 3 ambiguities
ConcreteType(::Any, ::Any, ::Int) = 1
ConcreteType(::Any, ::Int, ::Any) = 2
ConcreteType(::Int, ::Any, ::Any) = 3

# 1 ambiguity
(::ConcreteType)(::Any, ::Float64) = 1
(::ConcreteType)(::Float64, ::Any) = 2


@static if VERSION >= v"1.3-"
abstract type AbstractParameterizedType{T} end
struct ConcreteParameterizedType{T} <: AbstractParameterizedType{T} end
(::AbstractParameterizedType{T})(::Tuple{Tuple{Int}}) where {T} = 1
(::ConcreteParameterizedType)(::Tuple) = 2
abstract type AbstractType{T} end
struct ConcreteType{T} <: AbstractType{T} end
(::AbstractType{T})(::Tuple{Tuple{Int}}) where {T} = 1
(::ConcreteType)(::Tuple) = 2
end

end # module
71 changes: 18 additions & 53 deletions test/test_ambiguities.jl
Original file line number Diff line number Diff line change
Expand Up @@ -5,66 +5,31 @@ include("preamble.jl")
using PkgWithAmbiguities

@testset begin
function check_testcase(exclude, num_ambiguities::Int; broken::Bool = false)
pkgids = Aqua.aspkgids([PkgWithAmbiguities, Core]) # include Core to find constructor ambiguities
num_ambiguities_, strout, strerr = Aqua._find_ambiguities(pkgids; exclude = exclude)
if broken
@test_broken num_ambiguities_ == num_ambiguities
else
@test num_ambiguities_ == num_ambiguities
end
@test isempty(strerr)
end

@static if VERSION >= v"1.3-"
total = 9
else
total = 8
end

check_testcase([], total)

# exclude just anything irrelevant, see #49
check_testcase([convert], total)

# exclude function
check_testcase([PkgWithAmbiguities.f], total - 1)

# exclude callables and constructors
check_testcase([PkgWithAmbiguities.SingletonType], total - 2 - 1)
check_testcase([PkgWithAmbiguities.ConcreteType], total - 3 - 1)

# exclude abstract supertype without callables and constructors
check_testcase([PkgWithAmbiguities.AbstractType], total)
num_ambiguities, strout, strerr =
Aqua._find_ambiguities(Aqua.aspkgids(PkgWithAmbiguities))
@test num_ambiguities == 2
@test isempty(strerr)

@static if VERSION >= v"1.3-"
# for ambiguities between abstract and concrete type callables, only one needs to be excluded
check_testcase([PkgWithAmbiguities.AbstractParameterizedType], total - 1)
check_testcase([PkgWithAmbiguities.ConcreteParameterizedType], total - 1)
# exclude just anything irrelevant, see #49
num_ambiguities, strout, strerr =
Aqua._find_ambiguities(Aqua.aspkgids(PkgWithAmbiguities); exclude = [convert])
@test num_ambiguities == 2
@test isempty(strerr)

# exclude everything
check_testcase(
[
PkgWithAmbiguities.f,
PkgWithAmbiguities.SingletonType,
PkgWithAmbiguities.ConcreteType,
PkgWithAmbiguities.ConcreteParameterizedType,
],
0,
num_ambiguities, strout, strerr = Aqua._find_ambiguities(
Aqua.aspkgids(PkgWithAmbiguities);
exclude = [PkgWithAmbiguities.f, PkgWithAmbiguities.AbstractType],
)
@test_broken num_ambiguities == 0
@test isempty(strerr)
else
# exclude everything
check_testcase(
[
PkgWithAmbiguities.f,
PkgWithAmbiguities.SingletonType,
PkgWithAmbiguities.ConcreteType,
],
0,
)
num_ambiguities, strout, strerr =
Aqua._find_ambiguities(Aqua.aspkgids(PkgWithAmbiguities))
@test num_ambiguities == 1
@test isempty(strerr)
end


# It works with other tests:
Aqua.test_unbound_args(PkgWithAmbiguities)
Aqua.test_undefined_exports(PkgWithAmbiguities)
Expand Down

0 comments on commit 295c0ce

Please sign in to comment.