This issue tracker has been migrated to GitHub, and is currently read-only.
For more information, see the GitHub FAQs in the Python's Developer Guide.

classification
Title: Importing pydoc and overwriting sys.stdout, causes one char to be sent to the console when calling help()
Type: behavior Stage: test needed
Components: Library (Lib) Versions: Python 3.1, Python 2.7, Python 2.6, Python 2.5
process
Status: closed Resolution: fixed
Dependencies: 1700304 Superseder:
Assigned To: Nosy List: ajaksu2, farialima, georg.brandl
Priority: low Keywords: easy

Created on 2010-03-22 05:22 by farialima, last changed 2022-04-11 14:56 by admin. This issue is now closed.

Messages (3)
msg101479 - (view) Author: François Granade (farialima) Date: 2010-03-22 05:22
When the "pydoc" module is imported, and the sys.stdout is overwriten, a end-of-line is sent to the console (on sdtout) when the help() function is sent.

to reproduce (this is on Python 2.5 but the same happens on Pythjon 3.1):

bash-3.2$ python2.5 -c "import pydoc; import sys; from StringIO import StringIO; sys.stdout = StringIO(); help(sys)"

bash-3.2$ 

(note the one empty line)

whereas:

bash-3.2$ python2.5 -c "import sys; from StringIO import StringIO; sys.stdout = StringIO(); help(sys)"
bash-3.2$ 

(no empty line)

The funny thing is that the difference only occurs if sys.stdout is redirected; if it is not, importing pydoc doesn't change anything to the output:

bash-3.2$ python2.5 -c "import pydoc; import sys; help(sys)" | wc
     256    1298   10690
bash-3.2$ python2.5 -c "import sys; help(sys)" | wc
     256    1298   10690
bash-3.2$ 




Note that this is related to 1700304, but is actually *one specific case* since *only one character* is not redirected - I would expect them all or none
msg101981 - (view) Author: Daniel Diniz (ajaksu2) * (Python triager) Date: 2010-03-31 06:14
Nice buglet, please take a look at Lib/pydoc.py to follow :)

As you point out, this is issue 1700304.
 
'plainpager', which outputs the help in these cases, uses 'sys.stdout.write(plain(text))', but Helper.help has a         "self.output.write('\n')" line that causes the behavior you see.

We could change "self.output.write('\n')" to "pager('\n')", but the real bug is that self.output is bound early to sys.stdout. So 'help()' is still redirecting to the old sys.stdout with your test.

I see a solution by turning Helper.output into a property, but it smells of over-engineering :) Passing all output to pagers should work too, unless we need Helper.output as a sort of sys.stderr.

The patch below shows that importing pydoc sets self.output prematurely and includes the "self.output.write('\n')" line.

Index: pydoc.py
===================================================================
--- pydoc.py    (revision 79447)
+++ pydoc.py    (working copy)
@@ -1765,6 +1765,7 @@
         elif isinstance(request, Helper): self()
         else: doc(request, 'Help on %s:')
         self.output.write('\n')
+        print >> sys.stderr, repr(self.output)

     def intro(self):
         self.output.write('''
msg112212 - (view) Author: Georg Brandl (georg.brandl) * (Python committer) Date: 2010-07-31 21:51
Fixed in r83370 by making input and output properties -- as Daniel noted, that is a nice and backwards compatible solution.
History
Date User Action Args
2022-04-11 14:56:58adminsetgithub: 52445
2010-07-31 21:51:53georg.brandlsetstatus: open -> closed

nosy: + georg.brandl
messages: + msg112212

resolution: fixed
2010-07-31 19:42:36georg.brandllinkissue1700304 superseder
2010-03-31 06:14:32ajaksu2setpriority: low

dependencies: + pydoc.help samples sys.stdout and sys.stdin at import time
type: behavior

keywords: + easy
nosy: + ajaksu2
messages: + msg101981
stage: test needed
2010-03-22 05:22:02farialimacreate