Commit d1d584f4 authored by Guido van Rossum's avatar Guido van Rossum

SF patch #462628 (Travers Naran) NNTPLib supports saving BODY to a file.

  I modified nntplib so the body method can accept an
  optional second parameter pointing to a filehandle or
  filename (string). This way, really long body
  articles can be stored to disk instead of kept in
  memory. The way I made the modification should make
  it easy to extend this functionality to other extended
  return methods.
parent d016e45f
...@@ -31,6 +31,7 @@ are strings, not numbers, since they are rarely used for calculations. ...@@ -31,6 +31,7 @@ are strings, not numbers, since they are rarely used for calculations.
# Imports # Imports
import re import re
import socket import socket
import types
__all__ = ["NNTP","NNTPReplyError","NNTPTemporaryError", __all__ = ["NNTP","NNTPReplyError","NNTPTemporaryError",
"NNTPPermanentError","NNTPProtocolError","NNTPDataError", "NNTPPermanentError","NNTPProtocolError","NNTPDataError",
...@@ -210,20 +211,35 @@ class NNTP: ...@@ -210,20 +211,35 @@ class NNTP:
raise NNTPProtocolError(resp) raise NNTPProtocolError(resp)
return resp return resp
def getlongresp(self): def getlongresp(self,fileHandle=None):
"""Internal: get a response plus following text from the server. """Internal: get a response plus following text from the server.
Raise various errors if the response indicates an error.""" Raise various errors if the response indicates an error."""
resp = self.getresp()
if resp[:3] not in LONGRESP: openedFile = None
raise NNTPReplyError(resp) try:
list = [] # If a string was passed then open a file with that name
while 1: if isinstance(fileHandle, types.StringType):
line = self.getline() openedFile = fileHandle = open(fileHandle, "w")
if line == '.':
break resp = self.getresp()
if line[:2] == '..': if resp[:3] not in LONGRESP:
line = line[1:] raise NNTPReplyError(resp)
list.append(line) list = []
while 1:
line = self.getline()
if line == '.':
break
if line[:2] == '..':
line = line[1:]
if fileHandle:
fileHandle.write(line + "\n")
else:
list.append(line)
finally:
# If this method created the file, then it must close it
if openedFile:
openedFile.close()
return resp, list return resp, list
def shortcmd(self, line): def shortcmd(self, line):
...@@ -231,10 +247,10 @@ class NNTP: ...@@ -231,10 +247,10 @@ class NNTP:
self.putcmd(line) self.putcmd(line)
return self.getresp() return self.getresp()
def longcmd(self, line): def longcmd(self, line, fileHandle=None):
"""Internal: send a command and get the response plus following text.""" """Internal: send a command and get the response plus following text."""
self.putcmd(line) self.putcmd(line)
return self.getlongresp() return self.getlongresp(fileHandle)
def newgroups(self, date, time): def newgroups(self, date, time):
"""Process a NEWGROUPS command. Arguments: """Process a NEWGROUPS command. Arguments:
...@@ -339,9 +355,9 @@ class NNTP: ...@@ -339,9 +355,9 @@ class NNTP:
"""Process a LAST command. No arguments. Return as for STAT.""" """Process a LAST command. No arguments. Return as for STAT."""
return self.statcmd('LAST') return self.statcmd('LAST')
def artcmd(self, line): def artcmd(self, line, fileHandle=None):
"""Internal: process a HEAD, BODY or ARTICLE command.""" """Internal: process a HEAD, BODY or ARTICLE command."""
resp, list = self.longcmd(line) resp, list = self.longcmd(line,fileHandle)
resp, nr, id = self.statparse(resp) resp, nr, id = self.statparse(resp)
return resp, nr, id, list return resp, nr, id, list
...@@ -356,16 +372,18 @@ class NNTP: ...@@ -356,16 +372,18 @@ class NNTP:
return self.artcmd('HEAD ' + id) return self.artcmd('HEAD ' + id)
def body(self, id): def body(self, id, fileHandle=None):
"""Process a BODY command. Argument: """Process a BODY command. Argument:
- id: article number or message id - id: article number or message id
- fileHandle: Filename string or file object to store the article in
Returns: Returns:
- resp: server response if successful - resp: server response if successful
- nr: article number - nr: article number
- id: message id - id: message id
- list: the lines of the article's body""" - list: the lines of the article's body or an empty list
if fileHandle was used"""
return self.artcmd('BODY ' + id) return self.artcmd('BODY ' + id, fileHandle)
def article(self, id): def article(self, id):
"""Process an ARTICLE command. Argument: """Process an ARTICLE command. Argument:
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment