2016-08-26 39 views
1

我有一些python代碼發送帶有嵌入"<a href="link">Link</a>"標籤內的URL的電子郵件。Gmail和Outlook向超鏈接URL中注入空格

點擊來自Gmail或Outlook 365網絡郵件客戶端的鏈接會導致破損的頁面,因爲它們都顯示爲在URL中插入空格字符或'%20'。有趣的是,它似乎發生在兩個客戶的同一地點。

鏈接是Kibana儀表板鏈接,因此嵌入Rison代碼。

鏈接應該是以下幾點:

<a href="http://localhost:5601/app/kibana?#/visualize/edit/BetterPie?_g=(refreshInterval:(display:Off,pause:!f,value:0),time:(from:now-60d,mode:quick,to:now))&_a=(filters:!(('$state':(store:appState),meta:(alias:!n,disabled:!f,index:'animals',key:breed,negate:!f,value:'lion'),query:(match:(breed:(query:lion,type:phrase)))),('$state':(store:appState),meta:(alias:!n,disabled:!f,index:'animals',key:age,negate:!f,value:'2'),query:(match:(age:(query:2,type:phrase)))),('$state':(store:appState),meta:(alias:!n,disabled:!f,index:'animals',key:name,negate:!f,value:'nala'),query:(match:(name:(query:nala,type:phrase))))),linked:!f,query:(query_string:(analyze_wildcard:!t,query:'*')),uiState:(spy:(mode:(fill:!f,name:!n))),vis:(aggs:!((id:'1',params:(),schema:metric,type:count),(id:'2',params:(field:breed,order:desc,orderBy:'1',size:5),schema:segment,type:terms),(id:'3',params:(field:age,order:desc,orderBy:'1',size:5),schema:segment,type:terms),(id:'4',params:(field:name,order:desc,orderBy:'1',size:5),schema:segment,type:terms)),listeners:(),params:(addLegend:!t,addTooltip:!t,isDonut:!f,shareYAxis:!t),title:'BetterPie',type:pie))">Dashboard Link</a> 

但無論是「%20」或空間被這裏注入:

query:'*')),%20uiState 

我使用Python的smtplib模塊編碼消息併發送電子郵件,通過執行以下操作:

htmlEnc = MIMEText(body, 'html') 

不確定爲什麼spac e被注入,所以任何幫助將不勝感激。

+0

是否有可能將中間URL縮短器/重定向視爲隱藏網絡郵件客戶端真實URL的方式?電子郵件服務提供商默認在所有電子郵件鏈接上進行跟蹤。 – revelt

+0

@revelt這是一個選項,但我不確定這是否會100%解決問題。由於電子郵件正文的長度,客戶端可能會插入空格,所以即使url鏈接較短,仍可能會出現空格,因爲正在添加的html中還有其他信息。 – funseiki

+0

我無法確認100%,但如果我沒有記錯,電子郵件中的URL有256個字符的限制。它可能更少。但是由於你的URL沒有被切斷,這是一個不同的情況。關於電子郵件中的空格,它是Word渲染引擎添加虛構紙張會結束的空間,但再次,它是一個不同的,因爲你得到%20添加,這是不同的.. – revelt

回答

3

我在發送電子郵件方面有相同的問題。我的問題是每行1000個字符的問題,這會自動導致在第1000個字符處插入換行符......這可能只是您的URL。要解決PHP發送的電子郵件中的問題,首先我將Content-Transfer-Encoding:引用打印的添加到電子郵件標題。其次,我通過PHP函數處理了我的電子郵件的主體quoted_printable_encode()。我不知道Python的等價函數,但希望我對相同類型問題的解決方案有助於您指出正確的方向。

2

問題是電子郵件行最多隻能有998個字符。如果您發送一封更長的郵件到Postfix服務器,Postfix會在將郵件轉發到最終目的地之前將換行符插入到郵件中。換行符在HTML電子郵件中被視爲空格。

您不應該發送超過998個字符的行;實際上標準的recommends每行最多有78個字符。用長度超過998個字符的行發送HTML的方法是使用所謂的Content-Transfer-Encoding,例如quoted-printable或base64。幸運的是,如果您使用的是Python標準模塊,則可以按如下方式實現。

您應該使用Charset實例調用Message.set_charset()方法,該實例指定quoted-printable的Content-Transfer-Encoding。

from email.charset import Charset, QP 
import email.message 
def fix_content_transfer_encoding(message: email.message.Message): 
    charset = Charset('utf-8') 
    charset.body_encoding = QP 
    message.set_charset(charset) 

Django的項目使用引用可打印從Django的1.10起違約;見Django #22561 (EmailMessage should respect RFC2822 on max line length)


關於在電子郵件線長度限制的題目是:不是所有的郵件服務器服從998個字符的限制爲嚴格的Postfix的軟件。事實上,雅虎網絡郵件客戶端將愉快地發送帶有引用的無效電子郵件: - 超過998個字符的標題。由於雅虎嚴格的DMARC策略要求References:標頭不會被中間郵件服務器更改,所以如果通過不知名的Postfix服務器轉發,合法的Yahoo郵件將被DMARC拒絕。