'A task to call the Resource subclass\'s handler methods for action.
Calls the handle_<ACTION>() method for the given action and then calls
the check_<ACTION>_complete() method with the result in a loop until it
returns True. If the methods are not provided, the call is omitted.
Any args provided are passed to the handler.
If a prefix is supplied, the handler method handle_<PREFIX>_<ACTION>()
is called instead.'

def action_handler_task(self, action, args=None, action_prefix=None):

    args = (args or [])
    handler_action = action.lower()
    check = getattr(self, ('check_%s_complete' % handler_action), None)
    if action_prefix:
        handler_action = ('%s_%s' % (action_prefix.lower(), handler_action))
    handler = getattr(self, ('handle_%s' % handler_action), None)
    if callable(handler):
        handler_data = handler(*args)
        (yield)
        if callable(check):
            try:
                while True:
                    try:
                        done = check(handler_data)
                    except PollDelay as delay:
                        (yield delay.period)
                    else:
                        if done:
                            break
                        else:
                            (yield)
            except Exception:
                raise
            except:
                with excutils.save_and_reraise_exception():
                    canceller = getattr(self, ('handle_%s_cancel' % handler_action), None)
                    if callable(canceller):
                        try:
                            canceller(handler_data)
                        except Exception:
                            LOG.exception('Error    cancelling    resource    %s', action)
