Back to index

python3.2  3.2.2
Public Member Functions | Public Attributes | Static Public Attributes
smtpd.MailmanProxy Class Reference
Inheritance diagram for smtpd.MailmanProxy:
Inheritance graph
[legend]
Collaboration diagram for smtpd.MailmanProxy:
Collaboration graph
[legend]

List of all members.

Public Member Functions

def process_message
def handle_accepted
def __repr__
def add_channel
def del_channel
def create_socket
def set_socket

Public Attributes

 socket
 family_and_type

Static Public Attributes

 channel_class = SMTPChannel
 debug = False
 connected = False
 accepting = False
 closing = False
 addr = None
tuple ignore_log_types = frozenset(['warning'])

Detailed Description

Definition at line 536 of file smtpd.py.


Member Function Documentation

def asyncore.dispatcher.__repr__ (   self) [inherited]

Definition at line 264 of file asyncore.py.

00264 
00265     def __repr__(self):
00266         status = [self.__class__.__module__+"."+self.__class__.__name__]
00267         if self.accepting and self.addr:
00268             status.append('listening')
00269         elif self.connected:
00270             status.append('connected')
00271         if self.addr is not None:
00272             try:
00273                 status.append('%s:%d' % self.addr)
00274             except TypeError:
00275                 status.append(repr(self.addr))
00276         return '<%s at %#x>' % (' '.join(status), id(self))

def asyncore.dispatcher.add_channel (   self,
  map = None 
) [inherited]

Definition at line 279 of file asyncore.py.

00279 
00280     def add_channel(self, map=None):
00281         #self.log_info('adding channel %s' % self)
00282         if map is None:
00283             map = self._map
00284         map[self._fileno] = self

Here is the caller graph for this function:

def asyncore.dispatcher.create_socket (   self,
  family,
  type 
) [inherited]

Definition at line 294 of file asyncore.py.

00294 
00295     def create_socket(self, family, type):
00296         self.family_and_type = family, type
00297         sock = socket.socket(family, type)
00298         sock.setblocking(0)
00299         self.set_socket(sock)

Here is the caller graph for this function:

def asyncore.dispatcher.del_channel (   self,
  map = None 
) [inherited]

Definition at line 285 of file asyncore.py.

00285 
00286     def del_channel(self, map=None):
00287         fd = self._fileno
00288         if map is None:
00289             map = self._map
00290         if fd in map:
00291             #self.log_info('closing channel %d:%s' % (fd, self))
00292             del map[fd]
00293         self._fileno = None

Here is the caller graph for this function:

def smtpd.SMTPServer.handle_accepted (   self,
  conn,
  addr 
) [inherited]

Reimplemented in test.test_smtplib.SimSMTPServer.

Definition at line 448 of file smtpd.py.

00448 
00449     def handle_accepted(self, conn, addr):
00450         print('Incoming connection from %s' % repr(addr), file=DEBUGSTREAM)
00451         channel = self.channel_class(self, conn, addr)

def smtpd.MailmanProxy.process_message (   self,
  peer,
  mailfrom,
  rcpttos,
  data 
)
Override this abstract method to handle messages from the client.

peer is a tuple containing (ipaddr, port) of the client that made the
socket connection to our smtp port.

mailfrom is the raw address the client claims the message is coming
from.

rcpttos is a list of raw addresses the client wishes to deliver the
message to.

data is a string containing the entire full text of the message,
headers (if supplied) and all.  It has been `de-transparencied'
according to RFC 821, Section 4.5.2.  In other words, a line
containing a `.' followed by other text has had the leading dot
removed.

This function should return None, for a normal `250 Ok' response;
otherwise it returns the desired response string in RFC 821 format.

Reimplemented from smtpd.PureProxy.

Definition at line 537 of file smtpd.py.

00537 
00538     def process_message(self, peer, mailfrom, rcpttos, data):
00539         from io import StringIO
00540         from Mailman import Utils
00541         from Mailman import Message
00542         from Mailman import MailList
00543         # If the message is to a Mailman mailing list, then we'll invoke the
00544         # Mailman script directly, without going through the real smtpd.
00545         # Otherwise we'll forward it to the local proxy for disposition.
00546         listnames = []
00547         for rcpt in rcpttos:
00548             local = rcpt.lower().split('@')[0]
00549             # We allow the following variations on the theme
00550             #   listname
00551             #   listname-admin
00552             #   listname-owner
00553             #   listname-request
00554             #   listname-join
00555             #   listname-leave
00556             parts = local.split('-')
00557             if len(parts) > 2:
00558                 continue
00559             listname = parts[0]
00560             if len(parts) == 2:
00561                 command = parts[1]
00562             else:
00563                 command = ''
00564             if not Utils.list_exists(listname) or command not in (
00565                     '', 'admin', 'owner', 'request', 'join', 'leave'):
00566                 continue
00567             listnames.append((rcpt, listname, command))
00568         # Remove all list recipients from rcpttos and forward what we're not
00569         # going to take care of ourselves.  Linear removal should be fine
00570         # since we don't expect a large number of recipients.
00571         for rcpt, listname, command in listnames:
00572             rcpttos.remove(rcpt)
00573         # If there's any non-list destined recipients left,
00574         print('forwarding recips:', ' '.join(rcpttos), file=DEBUGSTREAM)
00575         if rcpttos:
00576             refused = self._deliver(mailfrom, rcpttos, data)
00577             # TBD: what to do with refused addresses?
00578             print('we got refusals:', refused, file=DEBUGSTREAM)
00579         # Now deliver directly to the list commands
00580         mlists = {}
00581         s = StringIO(data)
00582         msg = Message.Message(s)
00583         # These headers are required for the proper execution of Mailman.  All
00584         # MTAs in existence seem to add these if the original message doesn't
00585         # have them.
00586         if not msg.get('from'):
00587             msg['From'] = mailfrom
00588         if not msg.get('date'):
00589             msg['Date'] = time.ctime(time.time())
00590         for rcpt, listname, command in listnames:
00591             print('sending message to', rcpt, file=DEBUGSTREAM)
00592             mlist = mlists.get(listname)
00593             if not mlist:
00594                 mlist = MailList.MailList(listname, lock=0)
00595                 mlists[listname] = mlist
00596             # dispatch on the type of command
00597             if command == '':
00598                 # post
00599                 msg.Enqueue(mlist, tolist=1)
00600             elif command == 'admin':
00601                 msg.Enqueue(mlist, toadmin=1)
00602             elif command == 'owner':
00603                 msg.Enqueue(mlist, toowner=1)
00604             elif command == 'request':
00605                 msg.Enqueue(mlist, torequest=1)
00606             elif command in ('join', 'leave'):
00607                 # TBD: this is a hack!
00608                 if command == 'join':
00609                     msg['Subject'] = 'subscribe'
00610                 else:
00611                     msg['Subject'] = 'unsubscribe'
00612                 msg.Enqueue(mlist, torequest=1)
00613 
00614 


Here is the call graph for this function:

def asyncore.dispatcher.set_socket (   self,
  sock,
  map = None 
) [inherited]

Definition at line 300 of file asyncore.py.

00300 
00301     def set_socket(self, sock, map=None):
        self.socket = sock

Here is the call graph for this function:

Here is the caller graph for this function:


Member Data Documentation

asyncore.dispatcher.accepting = False [static, inherited]

Definition at line 227 of file asyncore.py.

asyncore.dispatcher.addr = None [static, inherited]

Reimplemented in smtpd.SMTPChannel.

Definition at line 229 of file asyncore.py.

Definition at line 428 of file smtpd.py.

asyncore.dispatcher.closing = False [static, inherited]

Definition at line 228 of file asyncore.py.

asyncore.dispatcher.connected = False [static, inherited]

Reimplemented in asyncore.file_dispatcher.

Definition at line 226 of file asyncore.py.

asyncore.dispatcher.debug = False [static, inherited]

Definition at line 225 of file asyncore.py.

Definition at line 295 of file asyncore.py.

tuple asyncore.dispatcher.ignore_log_types = frozenset(['warning']) [static, inherited]

Definition at line 230 of file asyncore.py.


The documentation for this class was generated from the following file: