pymilter
pymilter copied to clipboard
StringIO and BytesIO with pymilter
In the MilterBase class the body function receives the content (as string?) from the milter interface. But in py3 the StringIO/BytesIO pops up. My fist assumption was I've to switch from the "old" StringIO to BytesIO - but the milter interfaces provides strings. So I switched back to StringIO. But then I receive a TypeError: string argument expected, got 'bytes'
in the body
function if I send a mail with an attachment.
So in my opinion I must decode/encode the string/bytes. But where and how?
Code (same as your milter-template.py):
def envform (self, mailfrom, *str):
[....]
self.messageToParse = io.StringIO()
[...]
def body(self, chunk):
self.messageToParse.write(chunk)
return Milter.CONTINUE
Running Python version 3.6.8
Here's what I have that works in python3:
def envfrom(self, f, *str):
[...]
self.fp = io.BytesIO()
def header(self, name, val):
[...]
if self.fp:
self.fp.write(b"%s: %s\n" % (codecs.encode(name, 'ascii'), codecs.encode(val, 'ascii')))
def eoh(self):
if self.fp:
self.fp.write(b"\n") # terminate headers
def body(self, chunk): # copy body to temp file
if self.fp:
self.fp.write(chunk) # IOError causes TEMPFAIL in milter
[...]
def eom(self):
if not self.fp:
return Milter.ACCEPT # no message collected - so no eom processing
[...]
self.fp.seek(0)
txt = self.fp.read()
[...]
If indendation is not preserved, I apologize in advance.
Scott K
Actually,
Looking at that, the use of ascii is probably a bug in my code. I suspect that should be utf-8.
Scott K
Thank you for the hint ... will test it.