8#pragma warning(disable : 4250)
15#pragma warning(default : 4250)
21#include <boost/python/bases.hpp>
22#include <boost/python/class.hpp>
23#include <boost/python/dict.hpp>
24#include <boost/python/exception_translator.hpp>
25#include <boost/python/overloads.hpp>
32#pragma warning(disable : 4267)
34#include <boost/python/raw_function.hpp>
38#include <boost/python/register_ptr_to_python.hpp>
39#include <boost/python/scope.hpp>
40#include <boost/variant.hpp>
41#include <boost/variant/static_visitor.hpp>
62using declarePropertyType2 = void (*)(boost::python::object &,
const std::string &,
const boost::python::object &,
63 const boost::python::object &,
const std::string &,
const int);
65using declarePropertyType3 = void (*)(boost::python::object &,
const std::string &,
const boost::python::object &,
66 const std::string &,
const int);
68using declarePropertyType4 = void (*)(boost::python::object &,
const std::string &,
const boost::python::object &,
77BOOST_PYTHON_FUNCTION_OVERLOADS(declarePropertyType1_Overload, PythonAlgorithm::declarePyAlgProperty, 2, 3)
78BOOST_PYTHON_FUNCTION_OVERLOADS(declarePropertyType2_Overload, PythonAlgorithm::declarePyAlgProperty, 3, 6)
79BOOST_PYTHON_FUNCTION_OVERLOADS(declarePropertyType3_Overload, PythonAlgorithm::declarePyAlgProperty, 4, 5)
90void translateCancel(const
Algorithm::CancelException &exc) {
92 PyErr_SetString(PyExc_KeyboardInterrupt,
"");
100void translateH5Exception(
const H5::Exception &exc) {
101 auto handleFrame = [](
unsigned int n,
const H5E_error_t *err,
void *ss_arg) ->
herr_t {
102 std::stringstream &ss_ = *((std::stringstream *)ss_arg);
104 ss_ <<
" #" <<
n <<
": " << err->desc <<
"\n";
109 std::stringstream ss;
110 exc.walkErrorStack(H5E_WALK_DOWNWARD, handleFrame, &ss);
112 PyErr_SetString(PyExc_RuntimeError, ss.str().c_str());
115template <
typename T> std::optional<T> extractArg(ssize_t
index,
const tuple &args) {
116 if (
index < len(args)) {
117 return std::optional<T>(extract<T>(args[
index]));
122template <
typename T>
void extractKwargs(
const dict &kwargs,
const std::string &keyName, std::optional<T> &out) {
123 if (!kwargs.has_key(keyName)) {
126 if (out != std::nullopt) {
127 throw std::invalid_argument(
"Parameter called '" + keyName +
128 "' was specified twice."
129 " This must be either positional or a kwarg, but not both.");
131 out = std::optional<T>(extract<T>(kwargs.get(keyName)));
137 :
m_alg(alg), m_propName(propName) {}
150 using Mantid::PythonInterface::IPyTypeVisitor::operator();
153 template <
typename T>
void setProp(
const T &val)
const {
m_alg->
setProperty(m_propName, val); }
156 std::string
const &m_propName;
160object createChildWithProps(tuple args, dict kwargs) {
162 auto name = extractArg<std::string>(1, args);
163 auto startProgress = extractArg<double>(2, args);
164 auto endProgress = extractArg<double>(3, args);
165 auto enableLogging = extractArg<bool>(4, args);
166 auto version = extractArg<int>(5, args);
168 const std::array<std::string, 6> reservedNames = {
"name",
"startProgress",
"endProgress",
169 "enableLogging",
"version",
"StoreInADS"};
171 extractKwargs<std::string>(kwargs, reservedNames[0],
name);
172 extractKwargs<double>(kwargs, reservedNames[1], startProgress);
173 extractKwargs<double>(kwargs, reservedNames[2], endProgress);
174 extractKwargs<bool>(kwargs, reservedNames[3], enableLogging);
175 extractKwargs<int>(kwargs, reservedNames[4], version);
177 if (!
name.has_value()) {
178 throw std::invalid_argument(
"Please specify the algorithm name");
180 auto childAlg = parentAlg->createChildAlgorithm(
name.value(), startProgress.value_or(-1), endProgress.value_or(-1),
181 enableLogging.value_or(
true), version.value_or(-1));
183 if (kwargs.has_key(reservedNames[5])) {
185 std::optional<bool> storeADS = std::nullopt;
186 extractKwargs<bool>(kwargs, reservedNames[5], storeADS);
187 childAlg->setAlwaysStoreInADS(storeADS.value_or(
false));
190 const list keys = kwargs.keys();
191 for (
int i = 0; i < len(keys); ++i) {
192 const std::string propName = extract<std::string>(keys[i]);
194 if (std::find(reservedNames.cbegin(), reservedNames.cend(), propName) != reservedNames.cend())
197 object curArg = kwargs[keys[i]];
198 if (curArg.is_none())
202 auto nativeObj = PyNativeTypeExtractor::convert(curArg);
204 boost::apply_visitor(SetPropertyVisitor(childAlg, propName), nativeObj);
206 return object(childAlg);
213 register_ptr_to_python<std::shared_ptr<Algorithm>>();
214 register_exception_translator<Algorithm::CancelException>(&translateCancel);
215 register_exception_translator<H5::Exception>(&translateH5Exception);
221 class_<Algorithm, bases<Mantid::API::IAlgorithm>, std::shared_ptr<PythonAlgorithm>, boost::noncopyable>(
222 "Algorithm",
"Base class for all algorithms")
224 .staticmethod(
"fromString")
225 .def(
"createChildAlgorithm", raw_function(&createChildWithProps, std::size_t(1)),
226 "Creates and intializes a named child algorithm. Output workspaces "
227 "are given a dummy name.")
228 .def(
"declareProperty", (declarePropertyType1)&PythonAlgorithm::declarePyAlgProperty,
229 declarePropertyType1_Overload((arg(
"self"), arg(
"prop"), arg(
"doc") =
"")))
231 "Turns history recording on or off for an algorithm.")
232 .def(
"declareProperty", (declarePropertyType2)&PythonAlgorithm::declarePyAlgProperty,
233 declarePropertyType2_Overload((arg(
"self"), arg(
"name"), arg(
"defaultValue"), arg(
"validator") =
object(),
235 "Declares a named property where the type is taken from "
236 "the type of the defaultValue and mapped to an appropriate C++ "
238 .def(
"declareProperty", (declarePropertyType3)&PythonAlgorithm::declarePyAlgProperty,
239 declarePropertyType3_Overload(
240 (arg(
"self"), arg(
"name"), arg(
"defaultValue"), arg(
"doc") =
"", arg(
"direction") =
Direction::Input),
241 "Declares a named property where the type is taken from the "
243 "of the defaultValue and mapped to an appropriate C++ type"))
244 .def(
"declareProperty", (declarePropertyType4)&PythonAlgorithm::declarePyAlgProperty,
245 (arg(
"self"), arg(
"name"), arg(
"defaultValue"), arg(
"direction") =
Direction::Input),
246 "Declares a named property where the type is taken from the type "
247 "of the defaultValue and mapped to an appropriate C++ type")
248 .def(
"declareOrReplaceProperty", &PythonAlgorithm::declareOrReplacePyAlgProperty,
249 (arg(
"self"), arg(
"name"), arg(
"defaultValue"), arg(
"validator") = object(), arg(
"doc") =
"",
251 "Declares or replaces a named property where the type is taken from "
252 "the type of the defaultValue and mapped to an appropriate C++ "
254 .def(
"getLogger", &PythonAlgorithm::getLogger, arg(
"self"), return_value_policy<reference_existing_object>(),
255 "Returns a reference to this algorithm's logger")
256 .def(
"log", &PythonAlgorithm::getLogger, arg(
"self"), return_value_policy<reference_existing_object>(),
257 "Returns a reference to this algorithm's logger")
260 .def(
"setWikiSummary", &PythonAlgorithm::setWikiSummary, (arg(
"self"), arg(
"summary")),
261 "(Deprecated.) Set summary for the help.");
270 scope().attr(
"PythonAlgorithm") = scope().attr(
"Algorithm");
double value
The value of the point.
#define GET_POINTER_SPECIALIZATION(TYPE)
std::map< DeltaEMode::Type, std::string > index
void export_leaf_classes()
#define UNUSED_ARG(x)
Function arguments are sometimes unused in certain implmentations but are required for documentation ...
#define GNU_DIAG_OFF(x)
This is a collection of macros for turning compiler warnings off in a controlled manner.
Base class from which all concrete algorithm classes should be derived.
static IAlgorithm_sptr fromString(const std::string &input)
De-serialize an object from a string.
void setPropertyValue(const std::string &name, const std::string &value) override
Set the value of a property by string N.B.
void enableHistoryRecordingForChild(const bool on) override
Change the state of the history recording flag.
IPropertyManager * setProperty(const std::string &name, const T &value)
Templated method to set the value of a PropertyWithValue.
Base class for properties.
Provides a layer class for boost::python to allow C++ virtual functions to be overridden in a Python ...
virtual void operator()(bool value) const =0
std::shared_ptr< Workspace > Workspace_sptr
shared pointer to Mantid::API::Workspace
std::shared_ptr< Algorithm > Algorithm_sptr
Typedef for a shared pointer to an Algorithm.
Describes the direction (within an algorithm) of a Property.
@ Input
An input workspace.