Whoops, forgot to Reply All. ---------- Forwarded message ---------- From: Paul Baumgart <[email protected]> Date: Sat, Mar 21, 2009 at 1:57 PM Subject: Re: [Fab-user] More Complex Objects in Fabric Variables To: Jeff Forcier <[email protected]>
comments inline On Sat, Mar 21, 2009 at 12:11 PM, Jeff Forcier <[email protected]> wrote: > On Sat, Mar 21, 2009 at 2:53 PM, Paul Baumgart <[email protected]> wrote: >> Hi Jeff, >> >> I understand it's possible to /assign/ non-strings to Fabric >> variables, but how do you get them back out as anything other than >> strings? > > Reference config.myvar! This is why I'm confused, you're focusing on > let(), which may still be around as a vestigal method, but is not how > you're intended to interface with the ENV as of 0.1.0 -- it's from the > old let()/set() setup which was in 0.0.9 and earlier. Ah, ok, I didn't know let() was deprecated. That clears things up, thanks. > > Instead, you should probably be doing config.myvar = foo, and then > e.g. print config.myvar[0] -- and that ought to be 100% Pythonic and > not do any sort of casting to string (unless you're using the lazy > string eval, which is only one way of gettng data out of the ENV.) > > Let me update your example: > > > def data1(): > config.data=[1,2,3] > > def data2(): > config.data=[4,5,6] > > def show_first_datum(): > #local('echo $(data[0])') <-- This is not possible right now, but > might be a legitimate feature request :) > config.first_datum=data[0] > local('echo $(first_datum)') > > > The result: > > > Fabric v. 0.1.0. > Running data1... > Running show_first_datum... > [localhost] run: echo 1 > 1 > Done. > > > As noted in the example, a potential side-issue here, interpreting > Python statements such as indexing within the lazily-interpreted > string, is not currently supported. I personally am not sure it's > worth using eval() to have that added, either (it's easy enough to use > normal string interpolation there and do the indexing outside the > string), but I'll let Christian weigh in before I make any sort of > judgement :) Yeah, fair enough. This is plenty functional without eval(); it just be syntactic sugar, and furthermore I think the error messages would be fairly cryptic in the case of incorrect syntax within a lazily-interpreted string, which would probably make it less user-friendly all-in-all. > > >> (PS: I am using the latest code from the repository, specifically a >> fork I made on GitHub to play with 2 days ago.) > > Yup, but I'm not sure you've read the most recent docs -- they outline > how to use the 'config' object :) > > > I hope this clears things up some, let me know if I'm still missing something No, I'm satisfied; thanks for your help. :-) > > -Jeff > >> >> Paul >> >> On Sat, Mar 21, 2009 at 6:06 AM, Jeff Forcier <[email protected]> wrote: >>> 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 <[email protected]> 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 >>>> [email protected] >>>> http://lists.nongnu.org/mailman/listinfo/fab-user >>>> >>> >> > _______________________________________________ Fab-user mailing list [email protected] http://lists.nongnu.org/mailman/listinfo/fab-user
