fab-user
[Top][All Lists]
Advanced

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

Re: [Fab-user] More Complex Objects in Fabric Variables


From: Jeff Forcier
Subject: Re: [Fab-user] More Complex Objects in Fabric Variables
Date: Sat, 21 Mar 2009 09:06:29 -0400

Hi Paul,

I'm not sure where you got the impression that Fabric's let/set
functionality only works with strings! It should have always worked
with any Python variable whatsoever. The backend of let/set (which is,
in 0.1.0, just setting/getting attributes of a 'config' object -- may
want to upgrade if you can :)) is just a Python dict, nothing special.

If you can clarify how that first let() statement you posted "doesn't
work", perhaps we can figure out what went wrong.

Best,
Jeff

On Sat, Mar 21, 2009 at 5:29 AM, Paul Baumgart <address@hidden> wrote:
> Hi,
>
> I just recently came across Fabric, and I think it's a really useful
> tool. I was wondering, though, what the best way is to store, for
> example, a list in a Fabric variable.
>
> My use case is as follows:
> I'm creating an Apache virtual host file, and I want to store a list
> of ServerAliases, and then create the file containing these
> ServerAliases dynamically. There are anywhere from 0-5 ServerAliases
> depending on the site, so I want to avoid creating separate variables
> for each "slot". The problem with using a list though, is that, as I
> understand it, it's not possible to do anything with a Fabric variable
> besides cast it to a string, so, for example,
> let(directives="'ServerAlias ' + '\\\\nServerAlias '.join(aliases) +
> '\\\\n'") doesn't work.
>
> As a work-around I added the following functionality:
> http://github.com/paulbaumgart/fabric/blob/e36611d6be5a45b2dbd0771f6698c3c74d81f711/fabric.py#L844
> . Here's the docstring I wrote for it:
> """
> Optionally, you can pass eval=True, and all string values will be interpreted
> as lines of Python code, evaluated over all Fabric variables that have been
> previously set. String interpolation will not be performed if eval=True.
> Be sure to escape backslashes.
>
> Important note: do not reference variables set in the same let command. There
> is no guarantee the variables will be evaluated in the order given.
>
> Given the following fabfile:
> def print_y():
> require('y')
> local('echo "$(y)"');
>
> You can do this:
> $ fab let:x='1',eval=True let:y='x+1',eval=True print_y
> Fabric v. 0.1.1.
> Running let...
> Running let...
> Running print_y...
> [localhost] run: echo "2"
> 2
> Done.
>
> But /not/ this:
> $ fab let:x='1',y='x+1',eval=True print_y > /dev/null
> NameError: name 'x' is not defined
> Make sure the variable exists and that you are not referencing a
> variable defined elsewhere in the same let command.
>
> As you can see, it tries to warn you, but there would have been no error
> message if x had been set previously; it would just have the unexpected
> behavior of using the previous value of x.
> """
>
> But this feels a bit kludgy, especially because the evaluation order
> is not guaranteed for multiple expressions in one let statement.
>
> Can anyone suggest a better way to do this? Did I overlook existing
> functionality that accomplishes the same thing?
>
> Best,
> Paul
>
>
> _______________________________________________
> Fab-user mailing list
> address@hidden
> http://lists.nongnu.org/mailman/listinfo/fab-user
>




reply via email to

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