[PATCH 1/2] Add function to map functions on items in the main thread

Vratislav Podzimek vpodzime at redhat.com
Wed Nov 13 07:14:20 UTC 2013


On Tue, 2013-11-12 at 08:48 -0800, Brian C. Lane wrote:
> On Sat, Nov 09, 2013 at 03:27:36PM +0100, Vratislav Podzimek wrote:
> > Sometimes we need to map a function on a bunch of items in way that it is called
> > in the main thread. And sometimes we also need to do some transformations on the
> > items before we do the actions that need to take place in the main thread.
> > 
> > This patch adds a versatile function to do those actions in a probably best
> > possible way.
> > 
> > Signed-off-by: Vratislav Podzimek <vpodzime at redhat.com>
> > ---
> >  pyanaconda/constants.py    |  3 ++
> >  pyanaconda/ui/gui/utils.py | 82 +++++++++++++++++++++++++++++++++++++++++++++-
> >  2 files changed, 84 insertions(+), 1 deletion(-)
> > 
> > diff --git a/pyanaconda/constants.py b/pyanaconda/constants.py
> > index 115ef28..48bc142 100644
> > --- a/pyanaconda/constants.py
> > +++ b/pyanaconda/constants.py
> > @@ -143,3 +143,6 @@ PASSWORD_WEAK_CONFIRM = N_("You have provided a weak password. Press Done again
> >  PASSWORD_WEAK_CONFIRM_WITH_ERROR = N_("You have provided a weak password: %s. Press Done again to use anyway.")
> >  
> >  PASSWORD_STRENGTH_DESC = [N_("Empty"), N_("Weak"), N_("Fair"), N_("Good"), N_("Strong")]
> > +
> > +# the number of seconds we consider a noticeable freeze of the UI
> > +NOTICEABLE_FREEZE = 0.25
> 
> I think this should be 0.1 at the most. 250mS is a very noticeable
> delay.
Well, it is. But I was testing it and compared to the other hangs we do
in the main loop it really wasn't noticeable. Have a look at a preview I
did for another patchset [1], I was intentionally going over the
SpokeSelector to show that the cursor changes quite nicely while this
batch processing happens. Maybe the name of the constant should be
changed? :)

[1] http://vpodzime.fedorapeople.org/magical_decorator_with.webm

> 
> > +    def process_one_batch((queue, action, done_queue)):
> > +        tstamp_start = time.time()
> > +        tstamp = time.time()
> > +
> > +        # process as many batches as user cannot notice
> > +        while tstamp - tstamp_start < NOTICEABLE_FREEZE:
> > +            for i in xrange(batch_size):
> 
> I think you can drop the batch size. Just run them until the queue is
> empty or you run out of time. By batching them up you make the delay
> more granular, especially if the items being processed have different
> runtimes.
Well, I wanted to avoid getting, subtracting and comparing time with
every item being processed. That's why I used the batch size and I'd
really like to keep it there. In case there is an action like you
describe, the caller may use batch_size=1 delivering such behaviour and
causing basically no overhead due to the nature of xrange.

> 
> > +                try:
> > +                    action_item = queue.get_nowait()
> > +                    if action_item is TERMINATOR:
> > +                        # all items processed, tell we are finished and return
> > +                        done_queue.put(None)
> > +                        return False
> > +                    else:
> > +                        # run action on the item
> > +                        action(action_item, *args)
> > +                except Queue.Empty:
> > +                    # empty queue, reschedule to run later
> > +                    return True
> > +
> > +            tstamp = time.time()
> > +
> > +        # time out but something left, reschedule to run again later
> > +        return True
> > +
> > +    item_queue = Queue.Queue()
> > +    done_queue = Queue.Queue()
> 
> An Event object may be better for this, it probably amounts to the same
> thing, but you're just using the queue to block until the processing is
> done.
Hey, that's nice! I had no idea there is something like that, thanks!

> 
> It would also be a good idea to add some logging, at least telling when
> it started, maybe the size of the queue, and when it finished.
Good point, it will allow us tweaking the constants.

Doing changes in the version 2 of the patches.

-- 
Vratislav Podzimek

Anaconda Rider | Red Hat, Inc. | Brno - Czech Republic



More information about the anaconda-patches mailing list