我應該以什麼數據類型將電子郵件地址儲存在數據庫中?
我知道 254 個字元的電子郵件地址是有效的,但我研究過的實現傾向於使用 varchar(60) 到 varchar(80) 或等效的。例如:此 SQL Server 建議使用 varchar(80) 或此 Oracle 範例
是否有理由不使用最大 254 個字元?根據定義,varchar 不是只使用儲存數據所需的儲存空間嗎?
是否存在顯著的性能影響/權衡導致如此多的實現使用少於全部 254 個可能的字元?
我一直用
varchar(320)
,但真的應該是varchar(319)
。這就是為什麼。該標準規定了以下限制:
- “本地部分”(使用者名)為64 個字元。
@
符號1 個字元。- 域名的254 個字元(我一直相信 255,但根據這個勘誤表我錯了- 它實際上是 256 減去可能的
<
周圍尖括號>
)。現在,有些人會說您需要支持的不僅僅是這些。有些人還會說您需要為域名支持 Unicode(這意味著您必須切換到 Unicode
nvarchar
)。雖然標準可能會在此期間發生變化(我已經有一段時間沒有參與遊戲了),但我非常有信心,此時世界上大多數伺服器都不會接受 Unicode 電子郵件地址,我敢肯定許多伺服器在創建和/或接受大於 319 個字元(可能大於 254/255/256)的地址時會遇到問題。一個合理的上限應該更像是 128 個字元,因為實際上,比這更長的 e-amil 地址根本不實用,即使它們是在某些服務之外自動完成的。也就是說,您現在可以為最壞的情況做好準備,如果您願意(並且如果您在 SQL Server 2008 R2 或更高版本中使用數據壓縮,您將受益於 Unicode 壓縮,這意味著您只需為實際需要的字元支付 2 字節的損失它)。這樣,您可以使您的專欄盡可能寬,並且您可以讓人們在其中塞入他們想要的任何太長的垃圾 - 如果他們給您垃圾,他們就不會收到電子郵件,就像他們不會一樣如果插入失敗,將收到一封電子郵件。問題是如果你讓無效的垃圾進入,你必須處理它。而且無論您製作什麼大小 - 如果有人試圖將 400 個字元填充到 319 個字元的列中,那麼有人會嘗試將 1025 個字元填充到 1024 個字元的列中。任何明智的人都沒有理由擁有大於 319 個字元的電子郵件地址,除非他們使用它來明確測試系統邊界。
但我認為我們需要停止就此徵求意見- 並停止查看其他實現以獲得指導(在這種情況下發生的情況是,您引用的那些沒有費心做自己的功課,只是從中挑選數字,嗯,你知道的)。您可以直接訪問該標準- 確保您查閱最新版本,至少支持該標準,並保持在標準之上,以便您可以適應規範的變化。
編輯感謝@ypercube 在聊天中的 ping。
順便說一句,也許您一開始就不想將整個地址轉儲到單個列中。規範化可能表明您不想儲存
@hotmail.com
1500 萬次,因為更精簡的 FK int 可以正常工作並且沒有可變長度列的額外成本。您還可以規範化使用者名,john.smith@hotmail.com
並john.smith@gmail.com
共享一個共同的使用者名 - 他們彼此不認識,但您的數據庫並不關心這一點。我在這裡談到了一些:
然而,這對上述 254 個字元的限制提出了挑戰,因為對於將有效的 255 個字元的域與有效的 1 個字元的本地部分組合時會發生什麼似乎並沒有達成共識。這應該被世界上大多數伺服器接受,但似乎違反了這個 254 個字元的限制。那麼,當域可以重新用作有效的 255 個字元的 URL時,您是否會創建一個
Domains
人為地降低電子郵件地址長度限制的表?編輯有一條評論:
想為 postgres 添加這個,不要使用 varchar(n) wiki.postgresql.org/wiki/…
也許你可以在電子郵件列上使用檢查約束
雖然我同意“無限”字元串列的案例,但這不是其中之一。當您從完善的標準中了解數據域時,您應該使用它們。該連結討論瞭*如果您選擇不當,*這可能會導致最終使用者出錯。所以呢?沒有理由讓人們在域之外插入值(例如,一個 6 億字元長的電子郵件地址),以免他們這樣做時出錯。事實上,我認為電子郵件正是連結所討論的那種反例。
至少在 SQL Server 中正確定義列意味著您不會遭受記錄在案的類型性能損失或
max
由於varchar/nvarchar
聲明太寬而浪費記憶體。雖然使用檢查約束來限制長度使得以後在任一方向上調整最大長度變得更加容易,但這似乎與正確的列定義相比沒有任何其他好處(使用者無論哪種方式都會出錯)。