1 | use crate::instance::Bound; |
2 | use crate::types::any::PyAnyMethods; |
3 | use crate::types::PyType; |
4 | use crate::{ffi, PyTypeInfo}; |
5 | use crate::{PyAny, PyResult}; |
6 | |
7 | /// Represents a Python `super` object. |
8 | /// |
9 | /// Values of this type are accessed via PyO3's smart pointers, e.g. as |
10 | /// [`Py<PySuper>`][crate::Py] or [`Bound<'py, PySuper>`][Bound]. |
11 | #[repr (transparent)] |
12 | pub struct PySuper(PyAny); |
13 | |
14 | pyobject_native_type_core!( |
15 | PySuper, |
16 | pyobject_native_static_type_object!(ffi::PySuper_Type) |
17 | ); |
18 | |
19 | impl PySuper { |
20 | /// Constructs a new super object. More read about super object: [docs](https://docs.python.org/3/library/functions.html#super) |
21 | /// |
22 | /// # Examples |
23 | /// |
24 | /// ```rust |
25 | /// use pyo3::prelude::*; |
26 | /// |
27 | /// #[pyclass(subclass)] |
28 | /// struct BaseClass { |
29 | /// val1: usize, |
30 | /// } |
31 | /// |
32 | /// #[pymethods] |
33 | /// impl BaseClass { |
34 | /// #[new] |
35 | /// fn new() -> Self { |
36 | /// BaseClass { val1: 10 } |
37 | /// } |
38 | /// |
39 | /// pub fn method(&self) -> usize { |
40 | /// self.val1 |
41 | /// } |
42 | /// } |
43 | /// |
44 | /// #[pyclass(extends=BaseClass)] |
45 | /// struct SubClass {} |
46 | /// |
47 | /// #[pymethods] |
48 | /// impl SubClass { |
49 | /// #[new] |
50 | /// fn new() -> (Self, BaseClass) { |
51 | /// (SubClass {}, BaseClass::new()) |
52 | /// } |
53 | /// |
54 | /// fn method<'py>(self_: &Bound<'py, Self>) -> PyResult<Bound<'py, PyAny>> { |
55 | /// let super_ = self_.py_super()?; |
56 | /// super_.call_method("method" , (), None) |
57 | /// } |
58 | /// } |
59 | /// ``` |
60 | pub fn new<'py>( |
61 | ty: &Bound<'py, PyType>, |
62 | obj: &Bound<'py, PyAny>, |
63 | ) -> PyResult<Bound<'py, PySuper>> { |
64 | PySuper::type_object(ty.py()).call1((ty, obj)).map(|any| { |
65 | // Safety: super() always returns instance of super |
66 | unsafe { any.downcast_into_unchecked() } |
67 | }) |
68 | } |
69 | |
70 | /// Deprecated name for [`PySuper::new`]. |
71 | #[deprecated (since = "0.23.0" , note = "renamed to `PySuper::new`" )] |
72 | #[inline ] |
73 | pub fn new_bound<'py>( |
74 | ty: &Bound<'py, PyType>, |
75 | obj: &Bound<'py, PyAny>, |
76 | ) -> PyResult<Bound<'py, PySuper>> { |
77 | Self::new(ty, obj) |
78 | } |
79 | } |
80 | |