KivyUnitTest icon indicating copy to clipboard operation
KivyUnitTest copied to clipboard

Confused by the workflow of KivyUnitTest

Open pakal opened this issue 6 years ago • 1 comments

Hello,

Thanks for this module (I'm having troubles finding nice ways to test Kiby, now that InteractiveLauncher is deprecated). But I don't understand the principles of KivyUnitTest.

From my understanding, in a GUI engine like Kivy, everything runs synchronously in a single main thread.

So in your readme example excerpt below, run_test(), having been schedule on the Clock, should run entirely as a scheduled callback, before any other event can be processed by the main loop.

Thus, if it ends with app.stop() , the application will stop immediately, before any other scheduled event (like pause()) has a chance to be executed. So it shouldn't be possible to test, with this system, long operations with frame refreshes and user interactions.

What am I missing ? There is no "preemptive interrupts" or "greenlets" in Kivy here, is there ? Interrupting the python function runtest() right in the middle to play other events would be fragile, wouldn't it?

class Test(unittest.TestCase):
    def pause(*args):
        time.sleep(0.000001)

    def run_test(self, app, *args):
        Clock.schedule_interval(self.pause, 0.000001)
        # Do stuffs
        app.stop()

def test_example(self):
        app = My()
        p = partial(self.run_test, app)
        Clock.schedule_once(p, 0.000001)
        app.run()

pakal avatar Oct 11 '19 13:10 pakal

Just in case - I'm investigating a different approach using Gevent; with such microthreads all running in main thread, tests and app can run concurrently. One probably still needs 1 process per test though, to avoid conflicts between Kivy contexts.

import gevent
from gevent import monkey; monkey.patch_all()


def test_example(self):
        ...
        gevent.spawn(app.run)
        self.run_test(app)

pakal avatar Oct 11 '19 17:10 pakal