APOP認証でPOPサーバーにログインする - C#

APOP認証でPOPサーバーにログインする方法を紹介します。

ログインのフロー

APOP認証は以下の認証フローで認証します。

1.サーバーからのレスポンス

クライアント側がPOPサーバーに接続するとサーバー側から次のレスポンスが返されます。
+OK Dovecot ready. <963.15d2.4c6387a4.rmfFKz4oYeXdSP8GagMOaw==@pop.ipentec.com>

2.タイムスタンプの取得

返されたレスポンスのタイムスタンプ(<>で囲まれた部分)を切り出します。上記の例の場合は次の文字列がタイムスタンプになります。
 <963.15d2.4c6387a4.rmfFKz4oYeXdSP8GagMOaw==@pop.ipentec.com>
`

3.ダイジェスト文字列の準備

クライアント側はタイムスタンプの後ろにパスワードをつなげた文字列を用意し、そのMD5を求めます。MD5の求め方についてはこちらを参照。
パスワードが"PENGUIN"の場合は次の文字列のMD5を求めます。
 <963.15d2.4c6387a4.rmfFKz4oYeXdSP8GagMOaw==@pop.ipentec.com>PENGUIN

4.APOPコマンドの送信

求めたMD5文字列(ダイジェスト文字列)を以下の形式で送信します。
APOP (ユーザー名) (ダイジェスト文字列)
```
ユーザー名がduckの場合は次の文字列を送信します。(ダイジェスト文字列は一例です。)
APOP duck 5fd89c353d3f9ef0ead92923240d7714

5.APOP認証の成功

認証が成功するとサーバー側から以下のレスポンスが戻ります。以降はPOPと同じ動作となります。(LISTやRETRコマンドの送信など)
+OK Logged in.

コードのサンプル

APOP認証用のタイムスタンプを切り取る

//APOP認証用のタイムスタンプを切り取る
private string GetAPopTimeStamp(string receiveStr)
{
  receiveStr = receiveStr.Trim();
  System.Text.RegularExpressions.Regex reg = new System.Text.RegularExpressions.Regex(@"(?<TimeStamp>\<.*\>?)");
  System.Text.RegularExpressions.Match match = reg.Match(receiveStr);

  string timeStamp="";
  if (match.Success == true) {
    timeStamp = match.Groups["TimeStamp"].Value;
  }
  return timeStamp;
}

MD5算出

private string GetMD5String(string input)
{
  byte[] sourcebyte = System.Text.Encoding.ASCII.GetBytes(input);
  MD5CryptoServiceProvider md5 = new MD5CryptoServiceProvider(); 
  byte[] md5byte = md5.ComputeHash(sourcebyte); 
  string result = BitConverter.ToString(md5byte).ToLower().Replace("-","");
  return result;  
} 

APOPコマンドの送信

string Digest = GetMD5String(APopTimeStamp + password);
//パスワードとくっつけてダイジェスト文字列を作成
SendData = Encoding.ASCII.GetBytes(string.Format("APOP {0:s} {1:s}\r\n", userID, Digest));
著者
iPentecのメインプログラマー
C#, ASP.NET の開発がメイン、少し前まではDelphiを愛用
最終更新日: 2021-08-24
作成日: 2010-08-12
iPentec all rights reserverd.