很长一段时间以来,我一直在运行 Cyrus imapd,它通常运行良好。现在,我第一次遇到需要使用 cyrdeliver(Cyrus imapd 附带的 MDA)将邮件传递到名称包含空格字符的邮箱的子文件夹中的情况。我已经尝试解决这个问题几个小时了,但没有成功。
出于测试目的,我创建了一个用户ton_pp
,并在她的收件箱中创建了两个子文件夹。这些子文件夹的名称是Health
和Health Reports
。让 cyradm 列出访问权限可确认这两个文件夹具有相同的 IMAP 权限:
localhost> lam user/ton_pp*
user/ton_pp:
ton_pp lrswipkxtecda
cyrus lrswipkxtecda
user/ton_pp/INBOX/Health:
cyrus lrswipkxtecda
ton_pp lrswipkxtecda
user/ton_pp/INBOX/Health Reports:
cyrus lrswipkxtecda
ton_pp lrswipkxtecda
我创建了一条包含以下内容的测试消息:
root@morn ~ # cat testmessage
From: [email protected]
To: [email protected]
Subject: Test message
This is a test message.
当我执行时
/usr/sbin/cyrdeliver -a cyrus -m INBOX/Health ton_pp < testmessage
测试消息立即出现在用户Health
的子文件夹中。到目前为止,一切都很好——这就是我所希望的。INBOX
ton_pp
Health Reports
但是,当尝试对子文件夹(而不是)进行相同操作时Health
,我只是收到一条错误消息:
root@morn ~ # /usr/sbin/cyrdeliver -a cyrus -m "INBOX/Health Reports" ton_pp < testmessage
ton_pp+INBOX/Health Reports: Bad protocol
(需要用引号将邮箱文件夹名称括起来,以防止 shell 将其分割)。
这让我研究得更彻底。首先,我研究了代码mbox2cyrus,用于cyrdeliver
将消息按mbox
格式传输到 Cyrus imapd。代码很容易理解;第 151 至 154 行内容如下:
# Escape spaces in folder names for cyrdeliver. (Otherwise cyrdeliver
# will exit with the error "Bad protocol").
$subfolder =~ s/ /\\ /g;
$subfolder =~ s/,/\\,/g;
尽管我不确定逗号的特殊含义,但这清楚地表明,通过在文件夹名称中添加反斜杠来引用空格字符就足够了。这使得错误消息消失:
root@morn ~ # /usr/sbin/cyrdeliver -a cyrus -m "INBOX/Health\ Reports" ton_pp < testmessage
root@morn ~ #
然而,cyrdeliver
现在默默地丢弃该消息,或者将其放在我找不到的地方;它既不会出现在INBOX
其任何子文件夹中,也不会出现在其任何子文件夹中。
然后我就开始研究IMAPRFC3501(特别是关于正式语法和邮箱命名的章节),由此得到的印象是包含特殊字符(如空格字符)的邮箱名称应该用双引号引起来;也就是说,双引号应该向下传递给cyrdeliver
addition。尝试它只是带回错误消息:
root@morn ~ # /usr/sbin/cyrdeliver -a cyrus -m '"INBOX/Health\ Reports"' ton_pp < testmessage
ton_pp+"INBOX/Health\ Reports": Bad protocol
root@morn ~ # /usr/sbin/cyrdeliver -a cyrus -m '"INBOX/Health Reports"' ton_pp < testmessage
ton_pp+"INBOX/Health\ Reports": Bad protocol
显然,它不喜欢双引号;引用(或不引用)空格字符不会改变任何内容。怀疑未加引号的邮箱/用户名和带引号的“子文件夹”名称的混合可能会出现问题,因此我还尝试了一种语法不同但语义等效的替代方案,根据man deliver
:
root@morn ~ # /usr/sbin/cyrdeliver -a cyrus -m "user/ton_pp/INBOX/Health Reports" < testmessage
+user/ton_pp/INBOX/Health Reports: Bad protocol
root@morn ~ # /usr/sbin/cyrdeliver -a cyrus -m "user/ton_pp/INBOX/Health\ Reports" < testmessage
+user/ton_pp/INBOX/Health\ Reports: Mailbox does not exist
root@morn ~ # /usr/sbin/cyrdeliver -a cyrus -m '"user/ton_pp/INBOX/Health\ Reports"' < testmessage
+"user/ton_pp/INBOX/Health\ Reports": Bad protocol
root@morn ~ # /usr/sbin/cyrdeliver -a cyrus -m '"user/ton_pp/INBOX/Health Reports"' < testmessage
+"user/ton_pp/INBOX/Health Reports": Bad protocol
所以这并没有改善任何事情。
我还找到了一个赛勒斯人网站上的一些信息并尝试像对待@
本常见问题解答中的字符一样对待空格字符。也就是说,我\\\
用而不是重复了上面的测试\
。同样,这不起作用,导致“邮箱不存在”或“协议错误”错误。
现在我完全陷入困境了。有人可以帮我吗?当这些子文件夹名称中包含空格时,我需要做什么才能将cyrdeliver
消息放入 的子文件夹中?INBOX