1 | //! Various types defined by the Python interpreter such as `int`, `str` and `tuple`. |
2 | |
3 | pub use self::any::{PyAny, PyAnyMethods}; |
4 | pub use self::boolobject::{PyBool, PyBoolMethods}; |
5 | pub use self::bytearray::{PyByteArray, PyByteArrayMethods}; |
6 | pub use self::bytes::{PyBytes, PyBytesMethods}; |
7 | pub use self::capsule::{PyCapsule, PyCapsuleMethods}; |
8 | #[cfg (all(not(Py_LIMITED_API), not(PyPy), not(GraalPy)))] |
9 | pub use self::code::PyCode; |
10 | pub use self::complex::{PyComplex, PyComplexMethods}; |
11 | #[cfg (not(Py_LIMITED_API))] |
12 | #[allow (deprecated)] |
13 | pub use self::datetime::{ |
14 | timezone_utc, timezone_utc_bound, PyDate, PyDateAccess, PyDateTime, PyDelta, PyDeltaAccess, |
15 | PyTime, PyTimeAccess, PyTzInfo, PyTzInfoAccess, |
16 | }; |
17 | pub use self::dict::{IntoPyDict, PyDict, PyDictMethods}; |
18 | #[cfg (not(any(PyPy, GraalPy)))] |
19 | pub use self::dict::{PyDictItems, PyDictKeys, PyDictValues}; |
20 | pub use self::ellipsis::PyEllipsis; |
21 | pub use self::float::{PyFloat, PyFloatMethods}; |
22 | #[cfg (all(not(Py_LIMITED_API), not(PyPy), not(GraalPy)))] |
23 | pub use self::frame::PyFrame; |
24 | pub use self::frozenset::{PyFrozenSet, PyFrozenSetBuilder, PyFrozenSetMethods}; |
25 | pub use self::function::PyCFunction; |
26 | #[cfg (all(not(Py_LIMITED_API), not(all(PyPy, not(Py_3_8)))))] |
27 | pub use self::function::PyFunction; |
28 | #[cfg (Py_3_9)] |
29 | pub use self::genericalias::PyGenericAlias; |
30 | pub use self::iterator::PyIterator; |
31 | pub use self::list::{PyList, PyListMethods}; |
32 | pub use self::mapping::{PyMapping, PyMappingMethods}; |
33 | pub use self::mappingproxy::PyMappingProxy; |
34 | pub use self::memoryview::PyMemoryView; |
35 | pub use self::module::{PyModule, PyModuleMethods}; |
36 | pub use self::none::PyNone; |
37 | pub use self::notimplemented::PyNotImplemented; |
38 | #[allow (deprecated)] |
39 | pub use self::num::{PyInt, PyLong}; |
40 | #[cfg (not(any(PyPy, GraalPy)))] |
41 | pub use self::pysuper::PySuper; |
42 | pub use self::sequence::{PySequence, PySequenceMethods}; |
43 | pub use self::set::{PySet, PySetMethods}; |
44 | pub use self::slice::{PySlice, PySliceIndices, PySliceMethods}; |
45 | #[cfg (not(Py_LIMITED_API))] |
46 | pub use self::string::PyStringData; |
47 | #[allow (deprecated)] |
48 | pub use self::string::{PyString, PyStringMethods, PyUnicode}; |
49 | pub use self::traceback::{PyTraceback, PyTracebackMethods}; |
50 | pub use self::tuple::{PyTuple, PyTupleMethods}; |
51 | pub use self::typeobject::{PyType, PyTypeMethods}; |
52 | pub use self::weakref::{PyWeakref, PyWeakrefMethods, PyWeakrefProxy, PyWeakrefReference}; |
53 | |
54 | /// Iteration over Python collections. |
55 | /// |
56 | /// When working with a Python collection, one approach is to convert it to a Rust collection such |
57 | /// as `Vec` or `HashMap`. However this is a relatively expensive operation. If you just want to |
58 | /// visit all their items, consider iterating over the collections directly: |
59 | /// |
60 | /// # Examples |
61 | /// |
62 | /// ```rust |
63 | /// use pyo3::prelude::*; |
64 | /// use pyo3::types::PyDict; |
65 | /// use pyo3::ffi::c_str; |
66 | /// |
67 | /// # pub fn main() -> PyResult<()> { |
68 | /// Python::with_gil(|py| { |
69 | /// let dict = py.eval(c_str!("{'a':'b', 'c':'d'}" ), None, None)?.downcast_into::<PyDict>()?; |
70 | /// |
71 | /// for (key, value) in &dict { |
72 | /// println!("key: {}, value: {}" , key, value); |
73 | /// } |
74 | /// |
75 | /// Ok(()) |
76 | /// }) |
77 | /// # } |
78 | /// ``` |
79 | /// |
80 | /// If PyO3 detects that the collection is mutated during iteration, it will panic. |
81 | /// |
82 | /// These iterators use Python's C-API directly. However in certain cases, like when compiling for |
83 | /// the Limited API and PyPy, the underlying structures are opaque and that may not be possible. |
84 | /// In these cases the iterators are implemented by forwarding to [`PyIterator`]. |
85 | pub mod iter { |
86 | pub use super::dict::BoundDictIterator; |
87 | pub use super::frozenset::BoundFrozenSetIterator; |
88 | pub use super::list::BoundListIterator; |
89 | pub use super::set::BoundSetIterator; |
90 | pub use super::tuple::{BorrowedTupleIterator, BoundTupleIterator}; |
91 | } |
92 | |
93 | /// Python objects that have a base type. |
94 | /// |
95 | /// This marks types that can be upcast into a [`PyAny`] and used in its place. |
96 | /// This essentially includes every Python object except [`PyAny`] itself. |
97 | /// |
98 | /// This is used to provide the [`Deref<Target = Bound<'_, PyAny>>`](std::ops::Deref) |
99 | /// implementations for [`Bound<'_, T>`](crate::Bound). |
100 | /// |
101 | /// Users should not need to implement this trait directly. It's implementation |
102 | /// is provided by the [`#[pyclass]`](macro@crate::pyclass) attribute. |
103 | /// |
104 | /// ## Note |
105 | /// This is needed because the compiler currently tries to figure out all the |
106 | /// types in a deref-chain before starting to look for applicable method calls. |
107 | /// So we need to prevent [`Bound<'_, PyAny`](crate::Bound) dereferencing to |
108 | /// itself in order to avoid running into the recursion limit. This trait is |
109 | /// used to exclude this from our blanket implementation. See [this Rust |
110 | /// issue][1] for more details. If the compiler limitation gets resolved, this |
111 | /// trait will be removed. |
112 | /// |
113 | /// [1]: https://github.com/rust-lang/rust/issues/19509 |
114 | pub trait DerefToPyAny { |
115 | // Empty. |
116 | } |
117 | |
118 | // Implementations core to all native types except for PyAny (because they don't |
119 | // make sense on PyAny / have different implementations). |
120 | #[doc (hidden)] |
121 | #[macro_export ] |
122 | macro_rules! pyobject_native_type_named ( |
123 | ($name:ty $(;$generics:ident)*) => { |
124 | impl $crate::types::DerefToPyAny for $name {} |
125 | }; |
126 | ); |
127 | |
128 | #[doc (hidden)] |
129 | #[macro_export ] |
130 | macro_rules! pyobject_native_static_type_object( |
131 | ($typeobject:expr) => { |
132 | |_py| { |
133 | #[allow(unused_unsafe)] // https://github.com/rust-lang/rust/pull/125834 |
134 | unsafe { ::std::ptr::addr_of_mut!($typeobject) } |
135 | } |
136 | }; |
137 | ); |
138 | |
139 | #[doc (hidden)] |
140 | #[macro_export ] |
141 | macro_rules! pyobject_native_type_info( |
142 | ($name:ty, $typeobject:expr, $module:expr $(, #checkfunction=$checkfunction:path)? $(;$generics:ident)*) => { |
143 | unsafe impl<$($generics,)*> $crate::type_object::PyTypeInfo for $name { |
144 | const NAME: &'static str = stringify!($name); |
145 | const MODULE: ::std::option::Option<&'static str> = $module; |
146 | |
147 | #[inline] |
148 | #[allow(clippy::redundant_closure_call)] |
149 | fn type_object_raw(py: $crate::Python<'_>) -> *mut $crate::ffi::PyTypeObject { |
150 | $typeobject(py) |
151 | } |
152 | |
153 | $( |
154 | #[inline] |
155 | fn is_type_of(obj: &$crate::Bound<'_, $crate::PyAny>) -> bool { |
156 | #[allow(unused_unsafe)] |
157 | unsafe { $checkfunction(obj.as_ptr()) > 0 } |
158 | } |
159 | )? |
160 | } |
161 | |
162 | impl $name { |
163 | #[doc(hidden)] |
164 | pub const _PYO3_DEF: $crate::impl_::pymodule::AddTypeToModule<Self> = $crate::impl_::pymodule::AddTypeToModule::new(); |
165 | } |
166 | }; |
167 | ); |
168 | |
169 | /// Declares all of the boilerplate for Python types. |
170 | #[doc (hidden)] |
171 | #[macro_export ] |
172 | macro_rules! pyobject_native_type_core { |
173 | ($name:ty, $typeobject:expr, #module=$module:expr $(, #checkfunction=$checkfunction:path)? $(;$generics:ident)*) => { |
174 | $crate::pyobject_native_type_named!($name $(;$generics)*); |
175 | $crate::pyobject_native_type_info!($name, $typeobject, $module $(, #checkfunction=$checkfunction)? $(;$generics)*); |
176 | }; |
177 | ($name:ty, $typeobject:expr $(, #checkfunction=$checkfunction:path)? $(;$generics:ident)*) => { |
178 | $crate::pyobject_native_type_core!($name, $typeobject, #module=::std::option::Option::Some("builtins" ) $(, #checkfunction=$checkfunction)? $(;$generics)*); |
179 | }; |
180 | } |
181 | |
182 | #[doc (hidden)] |
183 | #[macro_export ] |
184 | macro_rules! pyobject_subclassable_native_type { |
185 | ($name:ty, $layout:path $(;$generics:ident)*) => { |
186 | #[cfg(not(Py_LIMITED_API))] |
187 | impl<$($generics,)*> $crate::impl_::pyclass::PyClassBaseType for $name { |
188 | type LayoutAsBase = $crate::impl_::pycell::PyClassObjectBase<$layout>; |
189 | type BaseNativeType = $name; |
190 | type Initializer = $crate::impl_::pyclass_init::PyNativeTypeInitializer<Self>; |
191 | type PyClassMutability = $crate::pycell::impl_::ImmutableClass; |
192 | } |
193 | } |
194 | } |
195 | |
196 | #[doc (hidden)] |
197 | #[macro_export ] |
198 | macro_rules! pyobject_native_type_sized { |
199 | ($name:ty, $layout:path $(;$generics:ident)*) => { |
200 | unsafe impl $crate::type_object::PyLayout<$name> for $layout {} |
201 | impl $crate::type_object::PySizedLayout<$name> for $layout {} |
202 | }; |
203 | } |
204 | |
205 | /// Declares all of the boilerplate for Python types which can be inherited from (because the exact |
206 | /// Python layout is known). |
207 | #[doc (hidden)] |
208 | #[macro_export ] |
209 | macro_rules! pyobject_native_type { |
210 | ($name:ty, $layout:path, $typeobject:expr $(, #module=$module:expr)? $(, #checkfunction=$checkfunction:path)? $(;$generics:ident)*) => { |
211 | $crate::pyobject_native_type_core!($name, $typeobject $(, #module=$module)? $(, #checkfunction=$checkfunction)? $(;$generics)*); |
212 | // To prevent inheriting native types with ABI3 |
213 | #[cfg(not(Py_LIMITED_API))] |
214 | $crate::pyobject_native_type_sized!($name, $layout $(;$generics)*); |
215 | }; |
216 | } |
217 | |
218 | pub(crate) mod any; |
219 | pub(crate) mod boolobject; |
220 | pub(crate) mod bytearray; |
221 | pub(crate) mod bytes; |
222 | pub(crate) mod capsule; |
223 | #[cfg (all(not(Py_LIMITED_API), not(PyPy), not(GraalPy)))] |
224 | mod code; |
225 | pub(crate) mod complex; |
226 | #[cfg (not(Py_LIMITED_API))] |
227 | pub(crate) mod datetime; |
228 | #[cfg (all(Py_LIMITED_API, any(feature = "chrono" , feature = "jiff-02" )))] |
229 | pub(crate) mod datetime_abi3; |
230 | pub(crate) mod dict; |
231 | mod ellipsis; |
232 | pub(crate) mod float; |
233 | #[cfg (all(not(Py_LIMITED_API), not(PyPy), not(GraalPy)))] |
234 | mod frame; |
235 | pub(crate) mod frozenset; |
236 | mod function; |
237 | #[cfg (Py_3_9)] |
238 | pub(crate) mod genericalias; |
239 | pub(crate) mod iterator; |
240 | pub(crate) mod list; |
241 | pub(crate) mod mapping; |
242 | pub(crate) mod mappingproxy; |
243 | mod memoryview; |
244 | pub(crate) mod module; |
245 | mod none; |
246 | mod notimplemented; |
247 | mod num; |
248 | #[cfg (not(any(PyPy, GraalPy)))] |
249 | mod pysuper; |
250 | pub(crate) mod sequence; |
251 | pub(crate) mod set; |
252 | pub(crate) mod slice; |
253 | pub(crate) mod string; |
254 | pub(crate) mod traceback; |
255 | pub(crate) mod tuple; |
256 | pub(crate) mod typeobject; |
257 | pub(crate) mod weakref; |
258 | |