From: Robert Klemme Date: 2008-02-13T01:11:27+09:00 Subject: Re: Ruby equivalent to source command 2008/2/12, Brett Williams : > I am trying to make a "source" command for Ruby (a la sh or tcl), but I > think lexical scoping is tripping me up. I've done a lot of reading > about bindings, and it seems I just can't do what I'm trying to do. > > def source(filename, bind = TOPLEVEL_BINDING) > code = nil > File.open(filename) { |f| code = f.read } > eval(code, bind) > end > > This works as I would like, with the exception of local variables > present in the sourced file. For example, if I had something like this > in the sourced file: > > x = "value set in sourced file" > > then I get an error : undefined local variable or method 'x' Can you show more code? For me it works: 17:05:12 ~ $ echo "x=123; puts x" | ruby -e 'eval(ARGF.read, TOPLEVEL_BINDING)' 123 17:05:18 ~ $ echo "x=123; puts x" | ruby -e 'eval(ARGF.read, binding)' 123 17:05:25 ~ $ Or are you seeing this: 17:05:25 ~ $ echo "x=123" | ruby -e 'eval(ARGF.read, binding); puts x' -e:1: undefined local variable or method `x' for main:Object (NameError) 17:06:31 ~ $ > unless I extend the scope of x by setting it before sourcing the file. Like 17:06:31 ~ $ echo "x=123" | ruby -e 'x=1; eval(ARGF.read, binding); puts x' 123 17:07:32 ~ $ This is because local variables are detected at compile time. That's why Ruby thinks "x" in my bit above is a method because there is no assignment. > Is there any way to accomplish what I want? I could work around this by > sticking to instance variables or *gulp* global variables for this > application, but before I throw in the towel I wanted to throw this out > to people here. A global is probably much more appropriate here. If the code you source somehow generates configuration settings then maybe you can set a global Hash that will receive values. It depends on the larger context of what you want to achieve. > P.S.: Things have changed since I was a pretty regular poster back in > 2002-2003... ;) Does this have to do with your email address? ;-) If yes, congrats and greetings to Becky! Cheers robert -- use.inject do |as, often| as.you_can - without end