Re: Redirecting standard out in a single namespace
On 23 Jan 2006 04:00:40 -0800, Fuzzyman [EMAIL PROTECTED] wrote: Bengt Richter wrote: [...] It wouldn't be shadowing, but I suppose you could replace sys.stdout with a custom object whose methods check where they were called from. Then you could give the object initialization parameters as to which namespace you want to have the effect in, and/or methods to control the action or turn it on or off etc. BTW, how about stderr? Redirecting stderr is identical in concept to redirecting stdout. Yeah, just reminding, in case you need to do that too ;-) The following in the write method of the custom out object works : sys._getframe(1).f_globals['__name__'] sys.stdout.write is *always* called from at least one frame deep in the stack - so it works. Yes, that's about what I had in mind, not being able to think of an alternative (other than the obvious one of using something other than print in the module where you want to redirect, either by hand or by effective source rewrite one way or another to translate print statments into e.g. myprint('the', 'print', 'args') or such. You could do source preprocessing or translating at the AST level, or you could do byte code munging. Nothing too nice. However the Python docs say of sys._getframe : This function should be used for internal and specialized purposes only. Might this approach be brittle ? In what sense? I guess it ought to work for the version it's defined for, but the advice is there. Maybe we can get something more specific from the author of the above doc snippet ;-) Regards, Bengt Richter -- http://mail.python.org/mailman/listinfo/python-list
Re: Redirecting standard out in a single namespace
Bengt Richter wrote: [snip..] The following in the write method of the custom out object works : sys._getframe(1).f_globals['__name__'] sys.stdout.write is *always* called from at least one frame deep in the stack - so it works. Yes, that's about what I had in mind, not being able to think of an alternative (other than the obvious one of using something other than print in the module where you want to redirect, either by hand or by effective source rewrite one way or another to translate print statments into e.g. myprint('the', 'print', 'args') or such. You could do source preprocessing or translating at the AST level, or you could do byte code munging. Nothing too nice. However the Python docs say of sys._getframe : This function should be used for internal and specialized purposes only. Might this approach be brittle ? In what sense? I guess it ought to work for the version it's defined for, but the advice is there. Maybe we can get something more specific from the author of the above doc snippet ;-) ``inspect.currentframe`` has no such warning. The equivalent would then be : inspect.currentframe().f_back.f_globals['__name__'] I guess unless the implementation of Python changes that will continue to work. :-) Thanks Fuzzyman http://www.voidspace.org.uk/python/index.shtml Regards, Bengt Richter -- http://mail.python.org/mailman/listinfo/python-list
Re: Redirecting standard out in a single namespace
On 20 Jan 2006 07:37:15 -0800, Fuzzyman [EMAIL PROTECTED] wrote: Hello, I'm trying to redirect standard out in a single namespace. I can replace sys.stdout with a custom object - but that affects all namespaces. There will be code running simultaneously that could import sys afterwards - so I don't want to make the change in the sys module. I have an idea to redefine __import__ for the relevant namespace - so that an attempt to import sys will return a different module with a custom object for stdout. As sys is a builtin module this might not work for the print statement, which is what I want to redirect. I'm not in a position to test my idea until later : __import = __import__ def __import__(name): if name == 'sys': return __import('newsys') else: return __import(name) import sys Is there another way to shadow the sys module from a single namespace ? It wouldn't be shadowing, but I suppose you could replace sys.stdout with a custom object whose methods check where they were called from. Then you could give the object initialization parameters as to which namespace you want to have the effect in, and/or methods to control the action or turn it on or off etc. BTW, how about stderr? Regards, Bengt Richter -- http://mail.python.org/mailman/listinfo/python-list
Re: Redirecting standard out in a single namespace
Maybe you can use __name__ to determine which module the print statement is in:class out: def write(s,a): if __name__ ==myModule: mylog.write(a) else: sys.__stdout__.write(a)sys.stdout = out() -- http://mail.python.org/mailman/listinfo/python-list
Re: Redirecting standard out in a single namespace
Bengt Richter wrote: On 20 Jan 2006 07:37:15 -0800, Fuzzyman [EMAIL PROTECTED] wrote: Hello, I'm trying to redirect standard out in a single namespace. I can replace sys.stdout with a custom object - but that affects all namespaces. There will be code running simultaneously that could import sys afterwards - so I don't want to make the change in the sys module. I have an idea to redefine __import__ for the relevant namespace - so that an attempt to import sys will return a different module with a custom object for stdout. As sys is a builtin module this might not work for the print statement, which is what I want to redirect. [snip..] Is there another way to shadow the sys module from a single namespace ? It wouldn't be shadowing, but I suppose you could replace sys.stdout with a custom object whose methods check where they were called from. Then you could give the object initialization parameters as to which namespace you want to have the effect in, and/or methods to control the action or turn it on or off etc. BTW, how about stderr? I've just tried checking __name__ in my custom stdout object. Unfortunately __name__ is always the module in which the new stdout object lives. In theory I could go up (down?) the stack to the previous frame and check __name__ there - but it sounds like a hack. Any other ways of checking where sys.stdout is called from ? All the best, Fuzzyman http://www.voidspace.org.uk/python/index.shtml Regards, Bengt Richter -- http://mail.python.org/mailman/listinfo/python-list
Re: Redirecting standard out in a single namespace
Bengt Richter wrote: On 20 Jan 2006 07:37:15 -0800, Fuzzyman [EMAIL PROTECTED] wrote: Hello, I'm trying to redirect standard out in a single namespace. I can replace sys.stdout with a custom object - but that affects all namespaces. There will be code running simultaneously that could import sys afterwards - so I don't want to make the change in the sys module. I have an idea to redefine __import__ for the relevant namespace - so that an attempt to import sys will return a different module with a custom object for stdout. As sys is a builtin module this might not work for the print statement, which is what I want to redirect. [snip..] Is there another way to shadow the sys module from a single namespace ? It wouldn't be shadowing, but I suppose you could replace sys.stdout with a custom object whose methods check where they were called from. Then you could give the object initialization parameters as to which namespace you want to have the effect in, and/or methods to control the action or turn it on or off etc. BTW, how about stderr? Redirecting stderr is identical in concept to redirecting stdout. The following in the write method of the custom out object works : sys._getframe(1).f_globals['__name__'] sys.stdout.write is *always* called from at least one frame deep in the stack - so it works. However the Python docs say of sys._getframe : This function should be used for internal and specialized purposes only. Might this approach be brittle ? All the best, Fuzzyman http://www.voidspace.org.uk/python/index.shtml Regards, Bengt Richter -- http://mail.python.org/mailman/listinfo/python-list
Re: Redirecting standard out in a single namespace
Ido Yehieli wrote: I'm sorry, but i don't see how this will solve the problem? It is exactly the same, only now you've replaced everything in sys except just sys.stdout? In the solution above (which I haven't had a chance to test) you're just chaning hte reference to sys to point to a different module, so you're not messing with sys itself. This won't affect other code that uses the sys module. Because of the builtin status of the sys module I'm not *convinced* it will work. I'll try it though. At any rate, perhapse the code you will write will be more maintainable if instead of redirecting sys.stdout for some of the code just use a different function (instead of print) for the times where you wish it to be redirected somewhere else? it will probably make your code longer, but the maintainer will have one less gotcha to worry about a few months/years down the road. perhapse it is best to not do the clever thing this time ;-) ? We're executing code from another module that uses the print statement a lot. That module isn't our code - other wise we wouldn't have a problem. :-) Changing the module will mean a great deal more to maintain, not less. All the best, Fuzzyman http://www.voidspace.org.uk/python/index.shtml -- http://mail.python.org/mailman/listinfo/python-list
Re: Redirecting standard out in a single namespace
oh, ok... I guess people have to learn to use a logger instead of print in production code... -- http://mail.python.org/mailman/listinfo/python-list
Redirecting standard out in a single namespace
Hello, I'm trying to redirect standard out in a single namespace. I can replace sys.stdout with a custom object - but that affects all namespaces. There will be code running simultaneously that could import sys afterwards - so I don't want to make the change in the sys module. I have an idea to redefine __import__ for the relevant namespace - so that an attempt to import sys will return a different module with a custom object for stdout. As sys is a builtin module this might not work for the print statement, which is what I want to redirect. I'm not in a position to test my idea until later : __import = __import__ def __import__(name): if name == 'sys': return __import('newsys') else: return __import(name) import sys Is there another way to shadow the sys module from a single namespace ? All the best, Fuzzyman http://www.voidspace.org.uk/python/index.shtml -- http://mail.python.org/mailman/listinfo/python-list
Re: Redirecting standard out in a single namespace
Fuzzyman wrote: Is there another way to shadow the sys module from a single namespace ? I've never actually tried this, but try making a copy of the sys module then replacing the stdout object with your own object. Then you can replace sys of the namespace with your custom sys module. I guess it would look something like this: import mysys #My dummy sys module import sys #Actual sys module #Copy sys module into dummy sys module mysys.__dict__.update(sys.__dict__) #Replace stdout with custom stdout mysys.stdout = MyStdout() #Replace sys of namespace namespace.sys = mysys This seems like it should work, however I don't know if copying the entire dictionary of one module to another is a safe thing to do. -Farshid -- http://mail.python.org/mailman/listinfo/python-list
Re: Redirecting standard out in a single namespace
I'm sorry, but i don't see how this will solve the problem? It is exactly the same, only now you've replaced everything in sys except just sys.stdout? At any rate, perhapse the code you will write will be more maintainable if instead of redirecting sys.stdout for some of the code just use a different function (instead of print) for the times where you wish it to be redirected somewhere else? it will probably make your code longer, but the maintainer will have one less gotcha to worry about a few months/years down the road. perhapse it is best to not do the clever thing this time ;-) ? -- http://mail.python.org/mailman/listinfo/python-list