首先让我说我知道最好使用子进程模块,但我正在编辑其他人的代码,我正在尝试尽可能少地进行更改,其中包括避免导入任何新模块。所以我想尽可能坚持当前导入的模块(os,sys和path)。
代码目前(在你们中的一些人可能熟悉的名为postfix-to-mailman.py的文件中):
if local in ('postmaster', 'abuse', 'mailer-daemon'):
os.execv("/usr/sbin/sendmail", ("/usr/sbin/sendmail", 'first@place.com'))
sys.exit(0)
这很好用(虽然我认为sys.exit(0)可能永远不会被调用,因此是不必要的。)
我相信这会替换当前进程,调用/ usr / sbin / sendmail将参数/ usr / sbin / sendmail(对于argv [0] ie本身)和'someaddress@someplace.com'传递给它,然后通过当前进程的环境 - 包括sys.stdin中的电子邮件消息 - 到子进程。
我想做的主要是在执行此操作之前发送另一份邮件副本。我不能再次使用execv,因为执行将停止。所以我尝试了以下内容:
if local in ('postmaster', 'abuse', 'mailer-daemon'):
os.spawnv(os.P_WAIT, "/usr/sbin/sendmail", ("/usr/sbin/sendmail", 'other@place.com'))
os.execv("/usr/sbin/sendmail", ("/usr/sbin/sendmail", 'first@place.com'))
sys.exit(0)
但是,当它将消息发送到other@place.com时,它永远不会将其发送到first@place.com
这让我感到惊讶,因为我认为使用spawn会启动子进程,然后在返回时继续执行当前进程(或者不等待,如果使用了P_NOWAIT)。
顺便说一句,我首先尝试了os.P_NOWAIT,但是我在other@place.com上收到的消息是空的,所以至少当我使用P_WAIT时,消息完好无损。但它仍然没有被发送到first@place.com这是一个问题。
我宁愿不使用os.system,如果我可以避免它,因为如果可以避免,我宁愿不去shell环境(安全问题,可能的性能?我承认我在这里偏执,但如果我能避免使用os.system,我仍然愿意。)
我唯一能想到的是对os.spawnv的调用以某种方式消耗/清空sys.stdin的内容,但这也没有意义。想法?
答案 0 :(得分:1)
虽然这可能没有意义,但事实确实如此
import os
os.spawnv(os.P_WAIT,"/usr/bin/wc", ("/usr/bin/wc",))
os.execv("/usr/bin/wc", ("/usr/bin/wc",))
$ cat j.py | python j.py
4 6 106
0 0 0
在这种情况下你可能会做这样的事情
import os
import sys
buf = sys.stdin.read()
wc = os.popen("usr/sbin/sendmail other@place.com","w")
wc.write(buf)
wc.close()
wc = os.popen("usr/sbin/sendmail first@place.com","w")
wc.write(buf)
wc.close()
sys.exit(0)
答案 1 :(得分:0)
sys.stdin是一个管道,它们是不可搜索的,所以你永远不能倒回那个类文件对象来再次读取它的内容。要实际调用sendmail(1)两次,您需要保存stdin的内容,最好是在临时文件中,但如果数据保证有限,则可以在内存中保护它。
但为什么要经历麻烦呢?您是否特别需要将电子邮件副本作为单独排队的电子邮件(如果是,为什么)?只需在原始调用sendmail(1)中添加所需的收件人即可。电子邮件标题中将不会显示其他收件人。
if local in ('postmaster', 'abuse', 'mailer-daemon'):
os.execv("/usr/sbin/sendmail", ("/usr/sbin/sendmail",
'first@place.com',
'otheruser@example.com'))
sys.exit(0)
哦,如果os.execv()由于某种原因失败,将执行sys.exit(0)行。如果无法执行/ usr / sbin / sendmail,则会发生这种情况,例如如果可执行文件不存在或实际上不可执行。换句话说,这是一个你应该照顾的错误条件。