Skip to content

Commit 6b253ee

Browse files
authored
make typed_callable idempotent (#14)
Fixes #10
1 parent 09e2d62 commit 6b253ee

File tree

2 files changed

+35
-5
lines changed

2 files changed

+35
-5
lines changed

src/EnforcedTypeSignatureCallables.jl

Lines changed: 25 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -92,6 +92,21 @@ function return_type_enforcer(::Type{Return}) where {Return}
9292
Base.Fix2(typeassert, Return)
9393
end
9494

95+
function typed_callable_no_special_casing(callable::Callable, ::Type{Return}) where {
96+
Return, Callable,
97+
}
98+
ret = return_type_enforcer(Return)
99+
ret callable
100+
end
101+
102+
function typed_callable_no_special_casing(callable::Callable, ::Type{Return}, ::Type{Arguments}) where {
103+
Return, Arguments <: Tuple, Callable,
104+
}
105+
ret = return_type_enforcer(Return)
106+
with_argument_types = CallableWithArgumentTypes{Arguments}(callable)
107+
ret with_argument_types
108+
end
109+
95110
"""
96111
typed_callable(callable, return_type::Type, argument_types::Type{<:Tuple})::CallableWithTypeSignature{return_type, argument_types}
97112
@@ -118,9 +133,11 @@ ERROR: TypeError: in typeassert, expected Tuple{Float32, Float32}, got a value o
118133
function typed_callable(callable::Callable, ::Type{Return}, ::Type{Arguments}) where {
119134
Return, Arguments <: Tuple, Callable,
120135
}
121-
ret = return_type_enforcer(Return)
122-
with_argument_types = CallableWithArgumentTypes{Arguments}(callable)
123-
ret with_argument_types
136+
if callable isa CallableWithTypeSignature{Return, Arguments} # ensure idempotence
137+
callable
138+
else
139+
typed_callable_no_special_casing(callable, Return, Arguments)
140+
end
124141
end
125142

126143
"""
@@ -151,8 +168,11 @@ ERROR: TypeError: in typeassert, expected Float32, got a value of type Float64
151168
function typed_callable(callable::Callable, ::Type{Return}) where {
152169
Return, Callable,
153170
}
154-
ret = return_type_enforcer(Return)
155-
ret callable
171+
if callable isa CallableWithReturnType{Return} # ensure idempotence
172+
callable
173+
else
174+
typed_callable_no_special_casing(callable, Return)
175+
end
156176
end
157177

158178
end

test/runtests.jl

Lines changed: 10 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -24,6 +24,11 @@ using Aqua: Aqua
2424
@test 3 === @inferred f(x_int)
2525
@test_throws TypeError f(x_f64)
2626
end
27+
@testset "`typed_callable` idempotency" begin
28+
@test let t = typed_callable(sin, Float32)
29+
t === @inferred typed_callable(t, Float32)
30+
end
31+
end
2732
end
2833

2934
@testset "`CallableWithTypeSignature`" begin
@@ -69,5 +74,10 @@ using Aqua: Aqua
6974
@test 3 === @inferred f(3.0)
7075
end
7176
end
77+
@testset "`typed_callable` idempotency" begin
78+
@test let t = typed_callable(sin, Float32, Tuple{Float32})
79+
t === @inferred typed_callable(t, Float32, Tuple{Float32})
80+
end
81+
end
7282
end
7383
end

0 commit comments

Comments
 (0)