faaxm / spix Goto Github PK
View Code? Open in Web Editor NEWUI test automation library for QtQuick/QML Apps
License: MIT License
UI test automation library for QtQuick/QML Apps
License: MIT License
I stumbled upon the use-case where I need to check the correct behavior of the app under test when using mouse hover over an element (i.e. tooltips).
Is this planned and/or something of interest if I would implement it for my team?
Hi dear @faaxm
Thanks for creation of this useful and beautiful thing. β€οΈ π πΉ
How to find items by a unique object name.
It is really hard to access to an item by its full path. ("mainWidnow/mainView/rightSide/setting
")
I have some items that are creating by another ones in runtime Unpredictably and they don't have any predefined area.
I don't now to handle some situations like this.
But if there is a way to access qml items by unique object name i think this problem will be solved easily.
Code will not compile on Ubuntu 18.04 due to missing #include <atomic>
in AnyRpcServer.cpp. Adding the include solves this
More a theoretical problem than anything else, but if you would send a 'quit' to the application and then enqueue some additional commands, before the quit is processed, what would happen?
I guess it is undefined behavior, crash or deadlock or something, no?
Can we have an additional lock or something to prevent any additional commands after a 'quit' was committed?
Hi,
I have the use-case where the application under test shall be fed by the external test script using the AnyRPC with some initial backend state.
So I quickly cooked up a generic callback implementation where one can send arbitrary data to the application under test.
So basically, the application under test would define a callback like so:
server.setGenericCommandHandler([](std::string command, std::string payload) {
// do whatever needs to be done
});
and the script would feed in my case the initial state to the application before doing the usual stuff:
s = xmlrpc.client.ServerProxy('http://localhost:9000')
s.command('loadBackendState', 'BackendData')
Would this generally be a feature of interest?
Hi,
Thanks for your very good library. The last commits (cmake-cleanup) did break something.
On an Ubuntu 18.04, ti works well with commit 071eeba, but not with the last one (00cf734 )
I got this message during "cmake ..":
CMake Error at CMakeLists.txt:39 (install):
install TARGETS given target "Spix" which does not exist in this directory.
-- Configuring incomplete, errors occurred!
Thanks for your nice job :-)
Hello, I want to ask why I put the instance code into the QT project. The cpp file is missing the "spix_export. h" header file, and cannot recognize many class names and function names, such as TestServer, override, wait, getStringProperty, QtQmlBot, etc.
Hi,
I would like to be able to use mouse right click on an item.
It seems to me, that this is currently not possible, yes?
I could do the implementation if you can give me pointers if you would rather have it as a separate command or somehow amalgamated into the existing mouseClick.
Thanks.
In QML if I have a combobox e.g.:
ComboBox {
objectName: "fruitCombo"
anchors.bottom: parent.bottom
width: 200
model: [ "Banana", "Apple", "Coconut" ]
}
I can click the list using mouseClick("fruitCombo")
but how can I click individual items in the list? e.g. the 3rd item or the item with text 'Coconut'. Would such functionality be easy to implement in spix?
I've have installed AnyRPC and Spix, and have added the lines specified in the readme into my .pro file;
...
# Spix
QT += quick
INCLUDEPATH += /usr/local/include
LIBS += -lSpix -lanyrpc
Building and running this by itself works fine, and doesn't produce any errors.
When I create a spix::AnyRpcServer
instance with the default port, it also still works fine;
int main(int argc, char *argv[])
{
...
QQmlApplicationEngine *engine = new QQmlApplicationEngine;
engine->addImportPath("qrc:/");
// Set up Spix server
spix::AnyRpcServer server;
// auto bot = new spix::QtQmlBot();
// bot->runTestServer(server);
...
}
but as soon as I uncomment the auto bot = new spix::QtQmlBot();
line, I get the following errors in Qt Creator:
π error: /usr/local/lib/libSpix.a(QtItemTools.cpp.o): in function QByteArray::compare(char const*, Qt::CaseSensitivity) const': QtItemTools.cpp:-1: error: undefined reference to
qstrnicmp(char const*, long long, char const*, long long)'
π error: collect2: error: ld returned 1 exit status
π error: [Makefile:82: mainapp] Error 1
And the following in the compile output
/usr/bin/ld: /usr/local/lib/libSpix.a(QtItemTools.cpp.o): in function `QByteArray::compare(char const*, Qt::CaseSensitivity) const':
QtItemTools.cpp:(.text._ZNK10QByteArray7compareEPKcN2Qt15CaseSensitivityE[_ZNK10QByteArray7compareEPKcN2Qt15CaseSensitivityE]+0x63): undefined reference to `qstrnicmp(char const*, long long, char const*, long long)'
collect2: error: ld returned 1 exit status
make[2]: *** [Makefile:82: mainapp] Error 1
make[2]: Leaving directory '/home/ruuds/Programming/djd/build-mea-Desktop_Qt_5_11_3_GCC_64bit-Debug/mainapp/mainapp'
make[1]: *** [Makefile:46: sub-mainapp-make_first] Error 2
make[1]: Leaving directory '/home/ruuds/Programming/djd/build-mea-Desktop_Qt_5_11_3_GCC_64bit-Debug/mainapp'
make: *** [Makefile:51: sub-mainapp-make_first] Error 2
15:59:58: The process "/usr/bin/make" exited with code 2.
Error while building/deploying project mea (kit: Desktop Qt 5.11.3 GCC 64bit)
When executing step "Make"
Any help would be appreciated!
I don't understand how invokeMethod is used. Can you add some relevant examples in the example?
Error (from VCPKG CI):
D:\buildtrees\spix\src\v0.5-97159dbd3f.clean\lib\src\Scene\Qt\QtItemTools.cpp(98): error C2440: 'return': cannot convert from 'QMetaMethodReturnArgument' to 'QGenericReturnArgument'
D:\buildtrees\spix\src\v0.5-97159dbd3f.clean\lib\src\Scene\Qt\QtItemTools.cpp(98): note: No user-defined-conversion operator available that can perform this conversion, or the operator cannot be called
D:\buildtrees\spix\src\v0.5-97159dbd3f.clean\lib\src\Scene\Qt\QtItemTools.cpp(101): error C2440: 'return': cannot convert from 'QMetaMethodReturnArgument' to 'QGenericReturnArgument'
D:\buildtrees\spix\src\v0.5-97159dbd3f.clean\lib\src\Scene\Qt\QtItemTools.cpp(101): note: No user-defined-conversion operator available that can perform this conversion, or the operator cannot be called
D:\buildtrees\spix\src\v0.5-97159dbd3f.clean\lib\src\Scene\Qt\QtItemTools.cpp(104): error C2440: 'return': cannot convert from 'QMetaMethodReturnArgument' to 'QGenericReturnArgument'
D:\buildtrees\spix\src\v0.5-97159dbd3f.clean\lib\src\Scene\Qt\QtItemTools.cpp(104): note: No user-defined-conversion operator available that can perform this conversion, or the operator cannot be called
D:\buildtrees\spix\src\v0.5-97159dbd3f.clean\lib\src\Scene\Qt\QtItemTools.cpp(107): error C2440: 'return': cannot convert from 'QMetaMethodReturnArgument' to 'QGenericReturnArgument'
D:\buildtrees\spix\src\v0.5-97159dbd3f.clean\lib\src\Scene\Qt\QtItemTools.cpp(107): note: No user-defined-conversion operator available that can perform this conversion, or the operator cannot be called
D:\buildtrees\spix\src\v0.5-97159dbd3f.clean\lib\src\Scene\Qt\QtItemTools.cpp(110): error C2440: 'return': cannot convert from 'QMetaMethodReturnArgument' to 'QGenericReturnArgument'
D:\buildtrees\spix\src\v0.5-97159dbd3f.clean\lib\src\Scene\Qt\QtItemTools.cpp(110): note: No user-defined-conversion operator available that can perform this conversion, or the operator cannot be called
D:\buildtrees\spix\src\v0.5-97159dbd3f.clean\lib\src\Scene\Qt\QtItemTools.cpp(113): error C2440: 'return': cannot convert from 'QMetaMethodReturnArgument' to 'QGenericReturnArgument'
D:\buildtrees\spix\src\v0.5-97159dbd3f.clean\lib\src\Scene\Qt\QtItemTools.cpp(113): note: No user-defined-conversion operator available that can perform this conversion, or the operator cannot be called
D:\buildtrees\spix\src\v0.5-97159dbd3f.clean\lib\src\Scene\Qt\QtItemTools.cpp(116): error C2440: 'return': cannot convert from 'QMetaMethodReturnArgument' to 'QGenericReturnArgument'
D:\buildtrees\spix\src\v0.5-97159dbd3f.clean\lib\src\Scene\Qt\QtItemTools.cpp(116): note: No user-defined-conversion operator available that can perform this conversion, or the operator cannot be called
D:\buildtrees\spix\src\v0.5-97159dbd3f.clean\lib\src\Scene\Qt\QtItemTools.cpp(201): warning C4996: 'QVariant::canConvert': was declared deprecated
D:\buildtrees\spix\src\v0.5-97159dbd3f.clean\lib\src\Scene\Qt\QtItemTools.cpp(211): warning C4996: 'QVariant::canConvert': was declared deprecated
D:\buildtrees\spix\src\v0.5-97159dbd3f.clean\lib\src\Scene\Qt\QtItemTools.cpp(221): warning C4996: 'QVariant::canConvert': was declared deprecated
D:\buildtrees\spix\src\v0.5-97159dbd3f.clean\lib\src\Scene\Qt\QtItemTools.cpp(259): warning C4267: 'argument': conversion from 'size_t' to 'int', possible loss of data
D:\buildtrees\spix\src\v0.5-97159dbd3f.clean\lib\src\Scene\Qt\QtItemTools.cpp(260): warning C4996: 'QVariant::canConvert': was declared deprecated
D:\buildtrees\spix\src\v0.5-97159dbd3f.clean\lib\src\Scene\Qt\QtItemTools.cpp(271): warning C4267: 'argument': conversion from 'size_t' to 'int', possible loss of data
D:\buildtrees\spix\src\v0.5-97159dbd3f.clean\lib\src\Scene\Qt\QtItemTools.cpp(286): warning C4267: 'argument': conversion from 'size_t' to 'int', possible loss of data
D:\buildtrees\spix\src\v0.5-97159dbd3f.clean\lib\src\Scene\Qt\QtItemTools.cpp(291): error C2665: 'std::vector<QGenericArgument,std::allocator<QGenericArgument>>::push_back': no overloaded function could convert all the argument types
C:\Program Files\Microsoft Visual Studio\2022\Enterprise\VC\Tools\MSVC\14.35.32215\include\vector(939): note: could be 'void std::vector<QGenericArgument,std::allocator<QGenericArgument>>::push_back(_Ty &&)'
with
[
_Ty=QGenericArgument
]
D:\buildtrees\spix\src\v0.5-97159dbd3f.clean\lib\src\Scene\Qt\QtItemTools.cpp(291): note: 'void std::vector<QGenericArgument,std::allocator<QGenericArgument>>::push_back(_Ty &&)': cannot convert argument 1 from 'QMetaMethodArgument' to '_Ty &&'
with
[
_Ty=QGenericArgument
]
D:\buildtrees\spix\src\v0.5-97159dbd3f.clean\lib\src\Scene\Qt\QtItemTools.cpp(291): note: Reason: cannot convert from 'QMetaMethodArgument' to '_Ty'
with
[
_Ty=QGenericArgument
]
D:\buildtrees\spix\src\v0.5-97159dbd3f.clean\lib\src\Scene\Qt\QtItemTools.cpp(291): note: No user-defined-conversion operator available that can perform this conversion, or the operator cannot be called
C:\Program Files\Microsoft Visual Studio\2022\Enterprise\VC\Tools\MSVC\14.35.32215\include\vector(935): note: or 'void std::vector<QGenericArgument,std::allocator<QGenericArgument>>::push_back(const _Ty &)'
with
[
_Ty=QGenericArgument
]
D:\buildtrees\spix\src\v0.5-97159dbd3f.clean\lib\src\Scene\Qt\QtItemTools.cpp(291): note: 'void std::vector<QGenericArgument,std::allocator<QGenericArgument>>::push_back(const _Ty &)': cannot convert argument 1 from 'QMetaMethodArgument' to 'const _Ty &'
with
[
_Ty=QGenericArgument
]
D:\buildtrees\spix\src\v0.5-97159dbd3f.clean\lib\src\Scene\Qt\QtItemTools.cpp(291): note: Reason: cannot convert from 'QMetaMethodArgument' to 'const _Ty'
with
[
_Ty=QGenericArgument
]
D:\buildtrees\spix\src\v0.5-97159dbd3f.clean\lib\src\Scene\Qt\QtItemTools.cpp(291): note: No user-defined-conversion operator available that can perform this conversion, or the operator cannot be called
D:\buildtrees\spix\src\v0.5-97159dbd3f.clean\lib\src\Scene\Qt\QtItemTools.cpp(291): note: while trying to match the argument list '(QMetaMethodArgument)'
D:\buildtrees\spix\src\v0.5-97159dbd3f.clean\lib\src\Scene\Qt\QtItemTools.cpp(288): warning C4996: 'QVariant::convert': was declared deprecated
With the existing implementation of TestServer.cpp, would it be possible to search for a path that contains a '/' without treating the '/' as a directory seperator? e.g. 'mainWindow/1/2' where '1/2' is the object to find
If not, what modifications could be done to the existsAndVisible
function?
Hi, first of all, great library ! I was wondering if it was possible to do a double click on a QML component ? I tried doing two successive mouseclick but it does not register as a doubleClick. I also tried with a wait between the two but it also doesn't register.
what should be the approach to mouseClick an item from a ListView QML item that uses a model and a delegate?
Hello,
This is for now more a question as and issue.
We are using spix v0.3 and I also tried v0.5 and am getting the same problem.
We integrated spxi into the qt app as described in the readme and are using python for testing ([XMLRPC client built into python]).
Our UI application has backend written in C++ and forehand in QML and we are using approaches like:
header file:
`Q_PROPERTY( int testStep READ testStep NOTIFY testStepChanged )`
qml file:
...
property int guideStep: TestSetupCtrl.testStep
...
onGuideStepChanged: handleGuideControll()
...
function handleGuideControll()
{
// console.log("simple logging ")
switch (guideStep)
{
case TestSetupCtrl.QC_SWAP_GUIDE_STEP_PRECAUTIONS:
guideControll.guideHeaderLabelText = qsTr("PRECAUTIONS")
guideControll.guideLabelText = qsTr("Wear gloves when running a QC test")
break
...
We then added python test cases using spix commands wait_screen, mouseclick, etc. And if we execute mouseclick() which simulates ui button click that changes testStep property then with the above code our test case fails, UI crash. But if I uncomment the above line "console.log" then test executes ok. Is there some timing problem here or did I miss something else? And did you encounter this issue on your side? Let me know if you need more information.
Thanks for the answer, Frenk
Is it possible to build and use Spix in MacOS??
I have a strange bug that I'm trying to wrap my head around. When using spix (modified to print the mouse events) with a minimal QML application on Qt6 everything works as expected:
ApplicationWindow {
id: window
visible: true
Button {
id: clickMe
onClicked: console.log("clicked");
text: "A Special Button"
}
}
s = xmlrpc.client.ServerProxy('http://localhost:9000')
s.mouseClick("window/clickMe")
print(s.getErrors())
# Qt
Starting minimalDrawerBug...
QML debugging is enabled. Only use this in a safe environment.
QMouseEvent(MouseButtonPress LeftButton pos=60.1016,12.5 scn=60.1016,12.5 gbl=2470,944 dev=QPointingDevice("core pointer" Mouse id=1))
QMouseEvent(MouseButtonRelease LeftButton pos=60.1016,12.5 scn=60.1016,12.5 gbl=2470,944 dev=QPointingDevice("core pointer" Mouse id=1))
qml: clicked
# python
[]
When I update the QML application to include a Drawer
element, however, spix is unable to click on the element:
ApplicationWindow {
id: window
visible: true
Button {
id: clickMe
onClicked: console.log("clicked");
text: "A Special Button"
}
// I tested placing drawer both before and after button
Drawer {
id: drawer
}
}
# Qt
Starting minimalDrawerBug...
QML debugging is enabled. Only use this in a safe environment.
QMouseEvent(MouseButtonPress LeftButton pos=60.1016,12.5 scn=60.1016,12.5 gbl=2470,944 dev=QPointingDevice("core pointer" Mouse id=1))
QMouseEvent(MouseButtonRelease LeftButton pos=60.1016,12.5 scn=60.1016,12.5 gbl=2470,944 dev=QPointingDevice("core pointer" Mouse id=1))
# python
[]
I am still able to click the button with normal mouse interaction, but spix seems unable to replicate the same behavior using synthetic events. As far as I can tell spix is generating the same MouseEvent in both cases, so maybe it has something to do with how Drawer interacts with mouse events?
I'm on Ubuntu 20.04, Qt 6.2.3 and the latest spix from master
(modified slightly to print mouse events). I'd be happy to post the full project that I test with if that's helpful.
Do you guys consider adding support for qml running in widgets? We use QMainWindow
with QQuickWidget
as a central widget for a couple of reasons and so far Spix cannot automate such applications.
After some digging I ended up with a working version with just a few lines of code, so maybe you can add that? You will need to add Qt5::Widgets
and Qt5::QuickWidgets
to the project, then add a widget-searching function:
QQuickItem* getQuickWidgetItemAtPath(const spix::ItemPath& path)
{
QList<QQuickItem *> list;
auto windows = qApp->topLevelWidgets();
for (const auto& window : windows) {
auto qwidgets = window->findChildren<QQuickWidget *>();
for (auto qw : qwidgets) {
list << qobject_cast<QQuickWidget *>(qw)->rootObject();
}
}
for (auto qi : list) {
auto res = getQQuickItemWithRoot(path, qi);
if (res) return res;
}
return nullptr;
}
that you call in QQuickItem* getQQuickItemAtPath(const spix::ItemPath& path)
in its "nothing found" branch:
if (!itemWindow) {
return getQuickWidgetItemAtPath(path);
}
finally, it needs two includes at the top:
#include <QQuickWidget>
#include <QApplication>
as you would probably make widget support optional, I am not sure if I can submit a proper pull request that takes this into account, but you are very welcome to add the code above to the project, so I can use the original version.
Thank you :)
I created a conan recipe for spix (see conan-io/conan-center-index#13953).
It would be great to create a 0.5 release containing the invokeMethod feature so that we can benefit from this feature using conan.
Thanks for your work !
On the large project, it's hard to maintain a consistent object name path. There are a lot of dynamic elements, and there is also potential for a lot of refactoring to be done on the Items hierarchy.
For this reason, it would be helpful to have a recursive approach. For example, we could add a parameter or create a separate method like "getStringPropertyRecursive" to work with QML items and their unique object names recursively.
Thank you for this very nice library, I am just testing it for https://github.com/opengisch/QField/
One place where I could see some potential for improvement is by allowing to use id
's instead of objectName
's, plenty of the code already defines ids, but almost nowhere objectNames, so the overhead for writing tests could be lowered.
What I think would need to be done:
Happy to hear back any feedback on this.
It would be great to have a possibility to send DoubleClick event.
Is there any work around for that?
It would be great to be able to add some custom rpc methods in AnyRpcServer.
However I did not find a solution without exposing anyrpc in the header of AnyRpcServer like this void addMethod(anyrpc::Method* method);
But by looking at the name of this class, does it really matter to hide anyrcp from AnyRpcServer ?
It would be nice to have some automated tests that check if Spix is working as expected with different Qt versions and when the code is changed. As it is hard to cover the interaction between Spix and Qt with unit tests one way would be to have a suite of UI tests running and verifying that they deliver consistent results.
This could be just having a github workflow run the examples that come with Spix and evaluating their results, or something more compact / customized.
Spix's item lookup fails to find and QML Item of Popup type or children of it (even when it is visible/open).
e.g.
Popup {
id: mypopup
Rectangle {
id: myrect
}
}
Spix isn't able to find mypopup or myrect.
We uses Popups for various kinds of dialog questions with buttons in our app and Spix isn't able to click on any of the dialog buttons or even find the Popup itself to determine visibility (when the popups are open), so we can't even add helper functions to click the buttons etc.
The Qt docs talk about some kind of dynamic re-parenting and there are properties contentItem
, contentChildren
and contentData
(but no children
as it inherits from QtObject
not Item
, which does have an objectName
).
Any ideas where to look troubleshooting or seeing how to add support for that?
Given the following element:
Text { text: "Hello World!" objectName: "test" font.family: "Helvetica" font.pointSize: 24 }
How would one proceed to query the font family with getStringProperty(...)?
I tried the following approaches and none seems to return anything:
getStringProperty("test", "font.family")
getStringProperty("test/font", "family")
Am I doing something wrong or is there an issue?
Hello,
I've got several questions during my work with spix:
I'm sorry for bombarding you with questions, you've done a great job and I really appreciate it!
Hello,
I have currently #87 which has been fix by this merge #91.
I need to get spix from conan which don't have this fix,
Is there a possibility to tag the main branch with a new version like 0.6 or 0.51 ?
Next, I'm in contact with @fdgStilla to add the new spix receipe in conan-center
Thanks for your work and your help
I have successfully built and installed in MacOS. But when I tried to make an instance the following error occurs
Undefined symbols for architecture x86_64:
"anyrpc::Connection::Connection(int, anyrpc::MethodManager*)", referenced from:
anyrpc::HttpConnection::HttpConnection(int, anyrpc::MethodManager*, std::__1::vector<anyrpc::RpcContentHandler, std::__1::allocator<anyrpc::RpcContentHandler> >&) in libSpix.a(AnyRpcServer.cpp.o)
"anyrpc::Connection::~Connection()", referenced from:
anyrpc::HttpConnection::HttpConnection(int, anyrpc::MethodManager*, std::__1::vector<anyrpc::RpcContentHandler, std::__1::allocator<anyrpc::RpcContentHandler> >&) in libSpix.a(AnyRpcServer.cpp.o)
"anyrpc::MethodManager::AddMethod(anyrpc::Method*)", referenced from:
void spix::utils::AddFunctionToAnyRpc<void (int)>(anyrpc::MethodManager*, std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> > const&, std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> > const&, std::__1::function<void (int)>) in libSpix.a(AnyRpcServer.cpp.o)
void spix::utils::AddFunctionToAnyRpc<void (std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> >)>(anyrpc::MethodManager*, std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> > const&, std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> > const&, std::__1::function<void (std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> >)>) in libSpix.a(AnyRpcServer.cpp.o)
void spix::utils::AddFunctionToAnyRpc<void (std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> >, std::__1::vector<std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> >, std::__1::allocator<std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> > > >)>(anyrpc::MethodManager*, std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> > const&, std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> > const&, std::__1::function<void (std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> >, std::__1::vector<std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> >, std::__1::allocator<std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> > > >)>) in libSpix.a(AnyRpcServer.cpp.o)
void spix::utils::AddFunctionToAnyRpc<void (std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> >, std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> >)>(anyrpc::MethodManager*, std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> > const&, std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> > const&, std::__1::function<void (std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> >, std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> >)>) in libSpix.a(AnyRpcServer.cpp.o)
void spix::utils::AddFunctionToAnyRpc<void (std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> >, int, unsigned int)>(anyrpc::MethodManager*, std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> > const&, std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> > const&, std::__1::function<void (std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> >, int, unsigned int)>) in libSpix.a(AnyRpcServer.cpp.o)
void spix::utils::AddFunctionToAnyRpc<std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> > (std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> >, std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> >)>(anyrpc::MethodManager*, std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> > const&, std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> > const&, std::__1::function<std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> > (std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> >, std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> >)>) in libSpix.a(AnyRpcServer.cpp.o)
void spix::utils::AddFunctionToAnyRpc<void (std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> >, std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> >, std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> >)>(anyrpc::MethodManager*, std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> > const&, std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> > const&, std::__1::function<void (std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> >, std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> >, std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> >)>) in libSpix.a(AnyRpcServer.cpp.o)
...
"anyrpc::MethodManager::~MethodManager()", referenced from:
anyrpc::Server::~Server() in libSpix.a(AnyRpcServer.cpp.o)
"anyrpc::XmlRpcHandler(anyrpc::MethodManager*, char*, unsigned long, anyrpc::Stream&)", referenced from:
anyrpc::XmlHttpServer::XmlHttpServer() in libSpix.a(AnyRpcServer.cpp.o)
"anyrpc::Value::PushBack(anyrpc::Value&)", referenced from:
void spix::utils::callAndAssignAnyRpcResult<std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> > >(std::__1::function<std::__1::vector<std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> >, std::__1::allocator<std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> > > > ()>, anyrpc::Value&) in libSpix.a(AnyRpcServer.cpp.o)
"anyrpc::Value::SetArray()", referenced from:
void spix::utils::callAndAssignAnyRpcResult<std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> > >(std::__1::function<std::__1::vector<std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> >, std::__1::allocator<std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> > > > ()>, anyrpc::Value&) in libSpix.a(AnyRpcServer.cpp.o)
"anyrpc::Value::Value(std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> > const&)", referenced from:
void spix::utils::callAndAssignAnyRpcResult<std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> > >(std::__1::function<std::__1::vector<std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> >, std::__1::allocator<std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> > > > ()>, anyrpc::Value&) in libSpix.a(AnyRpcServer.cpp.o)
"anyrpc::Value::~Value()", referenced from:
void spix::utils::callAndAssignAnyRpcResult<std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> > >(std::__1::function<std::__1::vector<std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> >, std::__1::allocator<std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> > > > ()>, anyrpc::Value&) in libSpix.a(AnyRpcServer.cpp.o)
"anyrpc::Value::operator=(std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> > const&)", referenced from:
void spix::utils::callAndAssignAnyRpcResult<std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> >, void, std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> >, std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> > >(std::__1::function<std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> > (std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> >, std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> >)>, anyrpc::Value&, std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> >, std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> >) in libSpix.a(AnyRpcServer.cpp.o)
"anyrpc::Value::operator=(bool)", referenced from:
void spix::utils::callAndAssignAnyRpcResult<bool, void, std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> > >(std::__1::function<bool (std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> >)>, anyrpc::Value&, std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> >) in libSpix.a(AnyRpcServer.cpp.o)
"anyrpc::Value::operator[](unsigned long)", referenced from:
std::__1::vector<std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> >, std::__1::allocator<std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> > > > spix::utils::unpackAnyRpcParam<std::__1::vector<std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> >, std::__1::allocator<std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> > > > >(anyrpc::Value&) in libSpix.a(AnyRpcServer.cpp.o)
void spix::utils::callAndAssignAnyRpcResult<int, 0ul, std::__1::function<void (int)> >(std::__1::function<void (int)>, anyrpc::Value&, std::__1::integer_sequence<unsigned long, 0ul>, anyrpc::Value&) in libSpix.a(AnyRpcServer.cpp.o)
void spix::utils::callAndAssignAnyRpcResult<std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> >, 0ul, std::__1::function<void (std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> >)> >(std::__1::function<void (std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> >)>, anyrpc::Value&, std::__1::integer_sequence<unsigned long, 0ul>, anyrpc::Value&) in libSpix.a(AnyRpcServer.cpp.o)
void spix::utils::callAndAssignAnyRpcResult<std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> >, std::__1::vector<std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> >, std::__1::allocator<std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> > > >, 0ul, 1ul, std::__1::function<void (std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> >, std::__1::vector<std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> >, std::__1::allocator<std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> > > >)> >(std::__1::function<void (std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> >, std::__1::vector<std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> >, std::__1::allocator<std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> > > >)>, anyrpc::Value&, std::__1::integer_sequence<unsigned long, 0ul, 1ul>, anyrpc::Value&) in libSpix.a(AnyRpcServer.cpp.o)
void spix::utils::callAndAssignAnyRpcResult<std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> >, std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> >, 0ul, 1ul, std::__1::function<void (std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> >, std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> >)> >(std::__1::function<void (std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> >, std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> >)>, anyrpc::Value&, std::__1::integer_sequence<unsigned long, 0ul, 1ul>, anyrpc::Value&) in libSpix.a(AnyRpcServer.cpp.o)
void spix::utils::callAndAssignAnyRpcResult<std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> >, int, unsigned int, 0ul, 1ul, 2ul, std::__1::function<void (std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> >, int, unsigned int)> >(std::__1::function<void (std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> >, int, unsigned int)>, anyrpc::Value&, std::__1::integer_sequence<unsigned long, 0ul, 1ul, 2ul>, anyrpc::Value&) in libSpix.a(AnyRpcServer.cpp.o)
void spix::utils::callAndAssignAnyRpcResult<std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> >, std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> >, 0ul, 1ul, std::__1::function<std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> > (std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> >, std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> >)> >(std::__1::function<std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> > (std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> >, std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> >)>, anyrpc::Value&, std::__1::integer_sequence<unsigned long, 0ul, 1ul>, anyrpc::Value&) in libSpix.a(AnyRpcServer.cpp.o)
...
"anyrpc::Server::AddHandler(bool (*)(anyrpc::MethodManager*, char*, unsigned long, anyrpc::Stream&), std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> >, std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> >)", referenced from:
anyrpc::XmlHttpServer::XmlHttpServer() in libSpix.a(AnyRpcServer.cpp.o)
"anyrpc::Server::StartThread()", referenced from:
vtable for anyrpc::XmlHttpServer in libSpix.a(AnyRpcServer.cpp.o)
"anyrpc::Server::BindAndListen(int, int)", referenced from:
vtable for anyrpc::XmlHttpServer in libSpix.a(AnyRpcServer.cpp.o)
"anyrpc::Server::AddAllHandlers()", referenced from:
vtable for anyrpc::XmlHttpServer in libSpix.a(AnyRpcServer.cpp.o)
"anyrpc::Server::Exit()", referenced from:
vtable for anyrpc::XmlHttpServer in libSpix.a(AnyRpcServer.cpp.o)
"anyrpc::Server::Server()", referenced from:
anyrpc::ServerST::ServerST() in libSpix.a(AnyRpcServer.cpp.o)
"anyrpc::Socket::~Socket()", referenced from:
anyrpc::TcpSocket::~TcpSocket() in libSpix.a(AnyRpcServer.cpp.o)
"anyrpc::ServerST::Work(int)", referenced from:
vtable for anyrpc::XmlHttpServer in libSpix.a(AnyRpcServer.cpp.o)
"anyrpc::ServerST::Shutdown()", referenced from:
vtable for anyrpc::XmlHttpServer in libSpix.a(AnyRpcServer.cpp.o)
"anyrpc::internal::HttpHeader::HttpHeader()", referenced from:
anyrpc::internal::HttpRequest::HttpRequest() in libSpix.a(AnyRpcServer.cpp.o)
"anyrpc::Value::GetString() const", referenced from:
std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> > spix::utils::unpackAnyRpcParam<std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> > >(anyrpc::Value&) in libSpix.a(AnyRpcServer.cpp.o)
std::__1::vector<std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> >, std::__1::allocator<std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> > > > spix::utils::unpackAnyRpcParam<std::__1::vector<std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> >, std::__1::allocator<std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> > > > >(anyrpc::Value&) in libSpix.a(AnyRpcServer.cpp.o)
"anyrpc::Server::GetConnectionsPeerInfo(std::__1::list<std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> >, std::__1::allocator<std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> > > >&, std::__1::list<unsigned int, std::__1::allocator<unsigned int> >&) const", referenced from:
vtable for anyrpc::XmlHttpServer in libSpix.a(AnyRpcServer.cpp.o)
"anyrpc::Server::GetConnectionsSockInfo(std::__1::list<std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> >, std::__1::allocator<std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> > > >&, std::__1::list<unsigned int, std::__1::allocator<unsigned int> >&) const", referenced from:
vtable for anyrpc::XmlHttpServer in libSpix.a(AnyRpcServer.cpp.o)
"anyrpc::Socket::GetSockInfo(std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> >&, unsigned int&) const", referenced from:
anyrpc::Server::GetMainSockInfo(std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> >&, unsigned int&) const in libSpix.a(AnyRpcServer.cpp.o)
"typeinfo for anyrpc::ServerST", referenced from:
typeinfo for anyrpc::XmlHttpServer in libSpix.a(AnyRpcServer.cpp.o)
"vtable for anyrpc::HttpConnection", referenced from:
anyrpc::HttpConnection::HttpConnection(int, anyrpc::MethodManager*, std::__1::vector<anyrpc::RpcContentHandler, std::__1::allocator<anyrpc::RpcContentHandler> >&) in libSpix.a(AnyRpcServer.cpp.o)
NOTE: a missing vtable usually means the first non-inline virtual member function has no definition.
"vtable for anyrpc::Server", referenced from:
anyrpc::Server::~Server() in libSpix.a(AnyRpcServer.cpp.o)
NOTE: a missing vtable usually means the first non-inline virtual member function has no definition.
"vtable for anyrpc::ServerST", referenced from:
anyrpc::ServerST::ServerST() in libSpix.a(AnyRpcServer.cpp.o)
NOTE: a missing vtable usually means the first non-inline virtual member function has no definition.
"vtable for anyrpc::internal::HttpRequest", referenced from:
anyrpc::internal::HttpRequest::HttpRequest() in libSpix.a(AnyRpcServer.cpp.o)
NOTE: a missing vtable usually means the first non-inline virtual member function has no definition.
ld: symbol(s) not found for architecture x86_64
clang: error: linker command failed with exit code 1 (use -v to see invocation)
make: *** [TestApp.app/Contents/MacOS/TestApp] Error 1
Application .pro file
macx: LIBS += -L$$PWD/../../../usr/local/lib/ -lSpix
INCLUDEPATH += $$PWD/../../../usr/local/include
DEPENDPATH += $$PWD/../../../usr/local/include
macx: PRE_TARGETDEPS += $$PWD/../../../usr/local/lib/libSpix.a
Hello,
I'm trying to integrate spix into my tests, but for some reason neither mouseBeginDrag nor mouseEndDrag move my mouse. Both functions activate drag mode, but if the mouse doesn't move on its own, it won't reach the target and therefore it doesn't actually accomplish anything.
It's weird because lib/src/Commands/DragBegin.cpp and lib/src/Commands/DragEnd.cpp already contain the following line:
env.scene().events().mouseMove(item.get(), midPoint);
OS: Arch Linux
Confirmed on X11 and Wayland
(QCursor::setPos doesn't work on Wayland anyway, therefore it can probably be ignored)
Edit: Maybe it's relevant that the objectNames I'm targetting are inside delegates. For the application, I'm using QGuiApplication and QQmlApplicationEngine, too. Simple clicking seems to work just fine (double click doesn't though, but I suspect that this would have to be implemented separately).
π error: /usr/local/lib/x86_64-linux-gnu/libSpix.a(AnyRpcServer.cpp.o): in function
std::__cxx11::basic_string<char, >std::char_traits<char>, std::allocator<char> > spix::utils::unpackAnyRpcParam<std::__cxx11::basic_string<char, >std::char_traits<char>, std::allocator<char> > >(anyrpc::Value&)': AnyRpcServer.cpp:-1: error: undefined reference to
anyrpc::Value::GetString() const'
...
...
and many other errors like that says cannot find xxx.cpp in some other qt modules
I have installed both QT and AnyRpc,but it looks like I didn't confirm them well.
Is there a more more detailed description for the installation such as how to set the parameters,which ubuntu/qt/cmake version should I use?
And,as you can see, i'm a noob both in coding and English
I hope my question doesn't offend you
I need to do test automation on Windows OS. Does the framework support Windows 10?
Hi @faaxm
In my Qt app I currently have buttons in a rowLayout, I use Spix in remote control with AnyRPC to control them and it works amazingly !
However, if one of these buttons turns invisible (button01
), with its Qt-QML property visible: false
, the layout automatically rearrange the other buttons (button00
and button02
) putting them over the invisible button (button01
). Then if I use another s.mouseClick("mainWindow/button01")
Spix find well my button because it still exists, gets its bounding box and clicks there. Problem is it's invisible and button02
has overdisplay it, so button02
is triggered because there is no checks on the visible
property before the click.
Of course it's easy to patch on the client side by checking with s.existsAndVisible("mainWindow/button01")
but would it be convenient to add an anyRPC method in order to do that, for example a mouseClickWithCheck
, or simply to have a ClickOnItem: [WARNING] item clicked but invisible
like the Item not found
report error in ClickOnItem::execute
I could propose such an implementation if you're interested in.
Thanks a lot π
A declarative, efficient, and flexible JavaScript library for building user interfaces.
π Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.
TypeScript is a superset of JavaScript that compiles to clean JavaScript output.
An Open Source Machine Learning Framework for Everyone
The Web framework for perfectionists with deadlines.
A PHP framework for web artisans
Bring data to life with SVG, Canvas and HTML. πππ
JavaScript (JS) is a lightweight interpreted programming language with first-class functions.
Some thing interesting about web. New door for the world.
A server is a program made to process requests and deliver data to clients.
Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.
Some thing interesting about visualization, use data art
Some thing interesting about game, make everyone happy.
We are working to build community through open source technology. NB: members must have two-factor auth.
Open source projects and samples from Microsoft.
Google β€οΈ Open Source for everyone.
Alibaba Open Source for everyone
Data-Driven Documents codes.
China tencent open source team.