Сначала я должен сказать, что, как программист на Python, я мог бы видеть эту проблему с неправильной точки зрения, прошло много лет с тех пор, как я написал свой последний код C++ еще в колледж.Как правильно запускать события браузера из python с помощью boost и Firebreath
У меня возникла небольшая проблема, пытаясь создать гибридный плагин python/C++ с использованием firebreath. Я до сих пор был успешным, интегрируя все части с помощью boost/python.h, но проблема возникла, когда я попытался запустить событие изнутри python. Я наткнулся на проблему необходимости связывать функцию python с функцией C++ (используя BOOST_PYTHON_MODULE). Сначала я попытался связать непосредственно python с моим JSAPI-производным классом fbtestconpythonAPI, проблема с этим подходом, похоже, связана с отсутствием ссылки на объект JSAPI, созданный браузером, что дает мне разные проблемы с несоответствием сигнатур между функцией python и эквивалентом C++ при время исполнения.
Единственное, что мне пришло, чтобы исправить это (я согласен, это уродливое грязное решение), заключается в использовании глобального указателя, который я инициализирую вручную с помощью set_pluginPointer. До сих пор это очень хорошо работает, но я знаю, что это не правильный способ сделать это. Я читал, что я не должен использовать «необработанный» указатель с объектом JSAPI, но я не уверен, как заменить его на shared_ptr для этой конкретной реализации. Другой проблемой является глобальная переменная, которая разделяется по всем экземплярам, что приводит, например, к тому, что все события запускаются в последней открытой вкладке/окне. Один из способов решения последнего - создать какой-то массив с индексом, являющимся текущим идентификатором окна/потока, с которым я должен иметь доступ как от моего объекта JSAPI, так и от функции python/C++.
Конечно, я открыт и буду очень ценить любые предложения относительно того, как улучшить/исправить либо это обходное решение, либо, лучше, правильный способ связи boost :: python и firebreath без взлома.
Ниже приводится соответствующая часть кода плагина
// Global pointer to plugin instance
fbtestconpythonAPI *fbtestPtr;
void fbtestconpythonAPI::set_pluginPointer(const std::string& val){
m_testString = val;
fbtestPtr = this; //Global pointer initialization
}
void echo(std::string x){
// Firing the echo event on the plugin instance using the global raw pointer
fbtestPtr->fire_echo(x, 1);
}
BOOST_PYTHON_MODULE(Pointless) {
def("echo", echo);
}
FB::variant fbtestconpythonAPI::echo(const FB::variant& msg){
int result_value;
Py_Initialize();
try {
initPointless(); // initialize Pointless
PyRun_SimpleString("import Pointless");
PyRun_SimpleString("Pointless.echo('hello world')");
object module(handle<>(borrowed(PyImport_AddModule("__main__"))));
object dictionary = module.attr("__dict__");
} catch (error_already_set) {
PyErr_Print();
}
Py_Finalize();
return 0;
}
Я еще не работал с Boost.Python, но, похоже, вам следует изучить, как получить объекты Python, связанные с экземплярами плагина FireBreath, вместо того, чтобы пытаться использовать обходной путь (свободные функции + глобальные). Я рекомендую задать вопрос об этой первоначальной проблеме. –
Спасибо за комментарий. Возможно, я был не очень ясен, пожалуйста, простите меня, потому что английский не мой первый язык, я имел в виду, что любое предложение о том, как это сделать (connect boost: python with firebreath), будет высоко оценено. Я просто хотел поделиться решением, которое я придумал, чтобы это исходило из ответов – skalanux
Я вижу, тогда я просто неправильно вас понял. –