fab-user
[Top][All Lists]
Advanced

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

Re: [Fab-user] Task.run() and task decorators


From: Rich Andrews
Subject: Re: [Fab-user] Task.run() and task decorators
Date: Mon, 16 Dec 2013 13:28:50 -0500

Michael, thanks for responding to my question about,  "What is the best way to implement Task subclass task-oriented logic: In Task.run() or in the wrapped function?"

I believe that the fab task function decorators must be declared in order, @task() first, with the remainder following.  Should @runs_once precede @task() as follows, the following exception will occur:

@runs_once
@task(task_class=CustomTask, myarg='value', alias='ata')
def wrapped_custom_taska(instance):
    print("wrapped_custom_taska()")

  File "xxxxxx/local/lib/python2.7/site-packages/fabric/decorators.py", line 136, in runs_once
    @wraps(func)
  File "/usr/lib/python2.7/functools.py", line 33, in update_wrapper
    setattr(wrapper, attr, getattr(wrapped, attr))
AttributeError: 'CustomTask' object has no attribute '__name__'

I believe this is expected behavior.

What is notable, is that if @task() does not have a task_class specified, WrappedCallableTask is used.  When given the two fab task functions:

@task(task_class=CustomTask, myarg='value', alias='ata')
@runs_once
def wrapped_custom_taska(instance):
    print("wrapped_custom_taska()")

# WrappedCallableTask
@task()
@runs_once
def wrapped_custom_taskc():
    print("wrapped_custom_task()")

The following runs occur:

$ fab -f fab_busybox1.py -H a,b,c,d wrapped_custom_taskc
[a] Executing task 'wrapped_custom_taskc'
WrappedCallableTask run()
wrapped_custom_task()
WrappedCallableTask run()
WrappedCallableTask run()
WrappedCallableTask run()
Done.

$ fab -f fab_busybox1.py -H a,b,c,d wrapped_custom_taska
[a] Executing task 'wrapped_custom_taska'
<fab_busybox1.CustomTask object at 0x15cd2d0> run()
wrapped_custom_taska()
[b] Executing task 'wrapped_custom_taska'
<fab_busybox1.CustomTask object at 0x15cd2d0> run()
[c] Executing task 'wrapped_custom_taska'
<fab_busybox1.CustomTask object at 0x15cd2d0> run()
[d] Executing task 'wrapped_custom_taska'
<fab_busybox1.CustomTask object at 0x15cd2d0> run()
Done.

We might be closer to answering question with this example. It appears both WrappedCallableTask and the Task subclass are run() for each host present in the fab role being treated, though the @runs_once decorator is present.

So then a more articulate question may be, "How does a Task subclass know the intentions of the decorators following its @task(task_class=) declaration?"


On Mon, Dec 16, 2013 at 8:01 AM, Michael Gliwinski <address@hidden> wrote:
On Sunday 15 Dec 2013 14:55:32 Rich Andrews wrote:
...
> The desire is that a decorator such as @runs_once could then be stacked.
>  But what happens in this case is that the customtask.run() is invoked for
> each host specified in the role, and the wrapped function is what runs once.

Off top of my head, this may have something to do with the order of
decorators.  Have you tried ordering them differently?

reply via email to

[Prev in Thread] Current Thread [Next in Thread]