2009-07-16 6 views
2

Итак, я хотел расширить класс SMTPServer smtpd Python, чтобы он мог обрабатывать соединения SMTP AUTH. Показался достаточно просто ...Добавить поддержку SMTP AUTH для библиотеки smtpd Python ... не может переопределить метод?

Так, казалось, я мог бы просто начать так:

def smtp_EHLO(self, arg): 
    print 'got in arg: ', arg 
    # do stuff here... 

Но по какой-то причине, что никогда не вызывается. Библиотека Python smtpd вызывает другие подобные методы, как это:

 method = None 
     i = line.find(' ') 
     if i < 0: 
      command = line.upper() 
      arg = None 
     else: 
      command = line[:i].upper() 
      arg = line[i+1:].strip() 
     method = getattr(self, 'smtp_' + command, None) 

Почему не это называют мой метод?

После этого я подумал, что я мог бы, вероятно, просто переопределить весь метод found_terminator (self):, но это тоже не работает.

def found_terminator(self): 
    # I add this to my child class and it never gets called... 

Я делаю что-то глупое или ...? Может быть, я просто еще не проснулся полностью еще сегодня ...

import smtpd 
import asyncore 

class CustomSMTPServer(smtpd.SMTPServer): 

    def smtp_EHLO(self, arg): 

     print 'got in arg: ', arg 

    def process_message(self, peer, mailfrom, rcpttos, data): 
     print 'Receiving message from:', peer 
     print 'Message addressed from:', mailfrom 
     print 'Message addressed to :', rcpttos 
     print 'Message length  :', len(data) 
     print 'HERE WE ARE MAN!' 
     return 

    # Implementation of base class abstract method 
    def found_terminator(self): 
     print 'THIS GOT CALLED RIGHT HERE!' 

     line = EMPTYSTRING.join(self.__line) 
     print >> DEBUGSTREAM, 'Data:', repr(line) 
     self.__line = [] 
     if self.__state == self.COMMAND: 
      if not line: 
       self.push('500 Error: bad syntax') 
       return 
      method = None 
      i = line.find(' ') 
      if i < 0: 
       command = line.upper() 
       arg = None 
      else: 
       command = line[:i].upper() 
       arg = line[i+1:].strip() 
      method = getattr(self, 'smtp_' + command, None) 

      print 'looking for: ', command 
      print 'method is: ', method 

      if not method: 
       self.push('502 Error: command "%s" not implemented' % command) 
       return 
      method(arg) 
      return 
     else: 
      if self.__state != self.DATA: 
       self.push('451 Internal confusion') 
       return 
      # Remove extraneous carriage returns and de-transparency according 
      # to RFC 821, Section 4.5.2. 
      data = [] 
      for text in line.split('\r\n'): 
       if text and text[0] == '.': 
        data.append(text[1:]) 
       else: 
        data.append(text) 
      self.__data = NEWLINE.join(data) 
      status = self.__server.process_message(self.__peer, 
                self.__mailfrom, 
                self.__rcpttos, 
                self.__data) 
      self.__rcpttos = [] 
      self.__mailfrom = None 
      self.__state = self.COMMAND 
      self.set_terminator('\r\n') 
      if not status: 
       self.push('250 Ok') 
      else: 
       self.push(status) 

server = CustomSMTPServer(('127.0.0.1', 1025), None) 

asyncore.loop() 

ответ

3

Вам нужно расширить SMTPChannel - это где реализованы smtp_ методы глагола; ваше расширение SMTPServer просто должно вернуть ваш собственный подкласс канала.

+0

Gah, по-видимому, я * сегодня * спал. Благодаря! –

+2

Небольшой пример того, как переопределить SMTPChannel, было бы неплохо, если бы стали такими глупыми людьми, как я ... :-) – nalply