24 #ifndef LSST_UTILS_PYTHON_H 25 #define LSST_UTILS_PYTHON_H 27 #include "pybind11/pybind11.h" 62 template<
typename T,
typename PyClass>
66 pybind11::is_operator());
69 pybind11::is_operator());
86 template <
class PyClass>
103 template <
class PyClass>
106 cls.def(
"__hash__", [](Class
const &
self) {
125 auto const i_orig = i;
130 if (i < 0 || i >= size) {
132 os <<
"Index " << i_orig <<
" not in range [" << -size <<
", " << size - 1 <<
"]";
133 throw pybind11::index_error(os.
str());
156 os <<
"Index (" << i <<
", " << j <<
") not in range [" 157 << -size_i <<
", " << size_i - 1 <<
"], [" 158 << -size_j <<
", " << size_j - 1 <<
"]";
159 throw pybind11::index_error(os.
str());
284 PyErr_SetString(PyExc_ImportError,
285 "WrapperCollection::finish() not called; module definition incomplete.");
286 PyErr_WriteUnraisable(
module.ptr());
330 _dependencies.splice(_dependencies.end(), submodule._dependencies);
331 _definitions.splice(_definitions.end(), submodule._definitions);
344 pybind11::module::import(name.
c_str());
358 _dependencies.push_back(name);
390 template <
typename PyType,
typename ClassWrapperCallback>
391 PyType
wrapType(PyType
cls, ClassWrapperCallback
function,
bool setModuleName=
true) {
393 cls.attr(
"__module__") = _package;
420 template <
typename CxxException,
typename CxxBase>
422 auto cls = pex::exceptions::python::declareException<CxxException, CxxBase>(
module, pyName, pyBase);
424 cls.attr(
"__module__") = _package;
436 for (
auto dep = _dependencies.begin(); dep != _dependencies.end(); dep = _dependencies.erase(dep)) {
437 pybind11::module::import(dep->c_str());
439 for (
auto def = _definitions.begin(); def != _definitions.end(); def = _definitions.erase(def)) {
440 (def->second)(def->first);
WrapperCollection(pybind11::module module_, std::string const &package)
Construct a new WrapperCollection.
void addOutputOp(PyClass &cls, std::string const &method)
Add __str__ or __repr__ method implemented by operator<<.
WrapperCollection makeSubmodule(std::string const &name)
Create a WrapperCollection for a submodule defined in the same binary.
~WrapperCollection() noexcept
std::size_t cppIndex(std::ptrdiff_t size, std::ptrdiff_t i)
Compute a C++ index from a Python index (negative values count from the end) and range-check.
void addInheritanceDependency(std::string const &name)
Indicate an external module that provides a base class for a subsequent addType call.
void finish()
Invoke all deferred wrapper-declaring callables.
#define LSST_PRIVATE
Make a symbol hidden even if default visiblity is public.
void wrap(WrapperCallback function)
Add a set of wrappers without defining a class.
pybind11::module module
The module object passed to the PYBIND11_MODULE block that contains this WrapperCollection.
void addSignatureDependency(std::string const &name)
Indicate an external module that provides a type used in function/method signatures.
A base class for image defects.
T uncaught_exception(T... args)
void addHash(PyClass &cls)
Add __hash__ method implemented by std::hash.
Reports attempts to access elements outside a valid range of indices.
void addSharedPtrEquality(PyClass &cls)
Add __eq__ and __ne__ methods based on two std::shared_ptr<T> pointing to the same address...
ItemVariant const * other
void collectSubmodule(WrapperCollection &&submodule)
Merge deferred definitions in the given submodule into the parent WrapperCollection.
A helper class for subdividing pybind11 module across multiple translation units (i.e.
WrapperCollection(WrapperCollection &&other) noexcept
auto wrapException(std::string const &pyName, std::string const &pyBase, bool setModuleName=true)
Wrap a C++ exception as a Python exception.
PyType wrapType(PyType cls, ClassWrapperCallback function, bool setModuleName=true)
Add a type (class or enum) wrapper, deferring method and other attribute definitions until finish() i...