Skip to content

Commit a317ef1

Browse files
committed
Use Probe
1 parent 6a0fa41 commit a317ef1

File tree

3 files changed

+13
-58
lines changed

3 files changed

+13
-58
lines changed

pyo3-macros-backend/src/type_hint.rs

Lines changed: 3 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -148,11 +148,10 @@ impl PythonTypeHint {
148148
}
149149
}
150150
PythonTypeHintVariant::ReturnType(t) => {
151-
// Use https://github.com/GoldsteinE/gh-blog/blob/master/const_deref_specialization/src/lib.md to detect empty tuple
152151
quote! {{
153-
const TYPE: #pyo3_crate_path::inspect::TypeHint = if #pyo3_crate_path::impl_::introspection::is_empty_tuple_from_closure(&|| {
154-
#pyo3_crate_path::impl_::introspection::IsEmptyTupleChecker::<#t>::new().check()
155-
}) {
152+
#[allow(unused_imports)]
153+
use #pyo3_crate_path::impl_::pyclass::Probe as _;
154+
const TYPE: #pyo3_crate_path::inspect::TypeHint = if #pyo3_crate_path::impl_::pyclass::IsReturningEmptyTuple::<#t>::VALUE {
156155
#pyo3_crate_path::inspect::TypeHint::builtin("None")
157156
} else {
158157
<#t as #pyo3_crate_path::impl_::introspection::PyReturnType>::OUTPUT_TYPE

src/impl_/introspection.rs

Lines changed: 0 additions & 54 deletions
Original file line numberDiff line numberDiff line change
@@ -1,8 +1,5 @@
11
use crate::conversion::IntoPyObject;
22
use crate::inspect::TypeHint;
3-
use crate::pyclass::boolean_struct::{private::Boolean, False, True};
4-
use std::marker::PhantomData;
5-
use std::ops::Deref;
63

74
/// Trait to guess a function Python return type
85
///
@@ -20,57 +17,6 @@ impl<T: PyReturnType, E> PyReturnType for Result<T, E> {
2017
const OUTPUT_TYPE: TypeHint = T::OUTPUT_TYPE;
2118
}
2219

23-
/// Hack to guess if the output type is the empty tuple
24-
///
25-
/// Inspiration: <https://github.com/GoldsteinE/gh-blog/blob/master/const_deref_specialization/src/lib.md>
26-
/// TL;DR: with closure we can get the compiler to return us the output type of the usual deref-based specialization
27-
pub const fn is_empty_tuple_from_closure<B: Boolean>(
28-
_closure_returning_bool: &impl FnOnce() -> B,
29-
) -> bool {
30-
B::VALUE
31-
}
32-
33-
pub struct IsEmptyTupleChecker<T> {
34-
_marker: PhantomData<T>,
35-
}
36-
37-
impl<T> IsEmptyTupleChecker<T> {
38-
#[allow(clippy::new_without_default)]
39-
pub const fn new() -> Self {
40-
Self {
41-
_marker: PhantomData,
42-
}
43-
}
44-
}
45-
46-
impl IsEmptyTupleChecker<()> {
47-
pub fn check(&self) -> True {
48-
True
49-
}
50-
}
51-
52-
impl<E> IsEmptyTupleChecker<Result<(), E>> {
53-
pub fn check(&self) -> True {
54-
True
55-
}
56-
}
57-
58-
impl<T> Deref for IsEmptyTupleChecker<T> {
59-
type Target = IsEmptyTupleCheckerFalse;
60-
61-
fn deref(&self) -> &IsEmptyTupleCheckerFalse {
62-
&IsEmptyTupleCheckerFalse
63-
}
64-
}
65-
66-
pub struct IsEmptyTupleCheckerFalse;
67-
68-
impl IsEmptyTupleCheckerFalse {
69-
pub fn check(&self) -> False {
70-
False
71-
}
72-
}
73-
7420
#[repr(C)]
7521
pub struct SerializedIntrospectionFragment<const LEN: usize> {
7622
pub length: u32,

src/impl_/pyclass/probes.rs

Lines changed: 10 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -79,6 +79,16 @@ impl<T: Clone> IsClone<T> {
7979
pub const VALUE: bool = true;
8080
}
8181

82+
probe!(IsReturningEmptyTuple);
83+
84+
impl IsReturningEmptyTuple<()> {
85+
pub const VALUE: bool = true;
86+
}
87+
88+
impl<E> IsReturningEmptyTuple<Result<(), E>> {
89+
pub const VALUE: bool = true;
90+
}
91+
8292
#[cfg(test)]
8393
macro_rules! value_of {
8494
($probe:ident, $ty:ty) => {{

0 commit comments

Comments
 (0)