BSMTP DLL 2003.02.11 更新 BSMTP DLLは、メール送信APIとメール受信APIを提供します。これをあなたのVisual Basic/C++ソースから呼出せばメール送受信が簡単にできます。メール受信時にコールバック関数を指定することにより、受信バイト数確認やキャンセルができます。 Visual C++とDelphiから使えます。1つのAPIを呼出すだけでメール送信OK。 Visual Basic/VBAからも使えます。 FlushMail API追加しました。2003/02/11 Update! Java環境でSMTP/POP3などのメールをテストするには、 Jamesをどうぞ。 ダウンロードファイル一覧 * bsmtp.dll  本体 * bsmtp.h   ヘッダファイル * bsmtp.lib  Visual C++ 6.0 用LIBファイル Visual Basicからの使い方 Declareステートメントを次のように使ってください。 Private Declare Function SendMail Lib "bsmtp" _ (szServer As String, szTo As String, szFrom As String, _ szSubject As String, szBody As String, szFile As String) As String Private Declare Function SendMailEx Lib "bsmtp" _ (szLogfile As String, szServer As String, szTo As String, _ szFrom As String, szSubject As String, szBody As String, szFile As String) As String Private Declare Function RcvMail Lib "bsmtp" _ (szServer As String, szUser As String, szPass As String, _ szCommand As String, szDir As String) As Variant Private Declare Function RcvMail2 Lib "bsmtp" _ (szServer As String, szUser As String, szPass As String, _ szCommand As String, szDir As String, callback As Long) As Variant Private Declare Function ReadMail Lib "bsmtp" _ (szFilename As String, szPara As String, szDir As String) As Variant Private Declare Function SortMail Lib "bsmtp" _ (szDir As String, szHeader As String, opt As Long, _ szFilter As String,delflag As Long) As Variant Private Declare Function FlushMail Lib "bsmtp" _ (szServer As String, szDir As String, szLogfile As String) As Long メール送信APIの使い方(Visual C++ 6.0/5.0) * bsmtp.dll をsystem32ディレクトリにコピー。BASP21 DLLを既にインストールしてあれば不要。 * C++ 6.0 :bsmtp.lib を適当なディレクトリにコピー(例:c:\babaq\bsmtp.lib) * C++ 5.0 :bsmtp50.lib を適当なディレクトリにコピー(例:c:\babaq\bsmtp50.lib) * 関数プロトタイプを次のように定義 // Bsmtp DLL extern "C" __declspec(dllimport) int BSendMail( LPCSTR szServer, // smtp server name LPCSTR szTo, // to (最大文字数は8192バイトです) LPCSTR szFrom, // from LPCSTR szSubject, // subject LPCSTR szBody, // body LPCSTR szFile, // Attach Files (フルパスでタブで区切って複数指定可) LPSTR msg); // error message * 次のようにBSendMail関数を呼出す char msg[80]; int ok = BSendMail(server, // サーバー名。タブで区切ってポート番号を // 指定できます。 // サーバ名の代わりにディレクトリ名(メールキュー)を指定すると // メールファイルを作成します。2003/2/6 Update! // 戻り値は、メールキュー内のメールファイル数になります。 // 作成したメールファイルは、FlushMail APIファイルでサーバに送信します。 to, // to mail address (e.g., who@who.com\twho2...) from, // from e-mail address subj, // Message subject body, // Message body files, // Attach Files msg); // error message if (!ok) { sprintf(buffer,"送信エラー (%s) %s %s %s %s", msg,server,to,from,subj); } // メールファイル指定の場合2003/2/6 Update! if (ok <= 9) { // エラー } * リンクライブラリに c:\babaq\bsmtp.lib(C++ 6.0の場合) c:\babaq\bsmtp50.lib(C++ 5.0の場合)を指定してリンク。 bsmtp50.libは、リンクオプション /LINK50COMPATで作成しました。THNX!福嶋さん。 メール送信APIの使い方(Visual C++ 4.2の場合) Visual C++ 4.2 ではbsmtp50.libのリンク時にエラーが出るようです。この場合は、bsmtp50.lib を使えません。 LoadLibrary/GetProcAddressを使って関数をコールしてください。 // 関数のプロトタイプをtypedefを使って定義します。 typedef int (*pBSendMail)( LPCSTR szServer, LPCSTR szTo, LPCSTR szFrom, LPCSTR szSubject, LPCSTR szBody, LPCSTR szFile, LPSTR msg); // ライブラリをロードします HINSTANCE hInst = ::LoadLibrary("bsmtp.dll"); if (hInst == NULL) return false; // 関数ポインタを定義 pBSendMail pBs; // BSendMail関数アドレスを設定 pBs = (pBSendMail)::GetProcAddress(hInst,"BSendMail"); if (pBs == NULL) { FreeLibrary(hInst); return false; } // ポインタを使ってBSendMailをコール int ok = pBs(Server,To,From,Sub,Body,"",msg); // 最後にライブラリをアンロード FreeLibrary(hInst); メール送信APIの使い方(Delphi) Delphiでも動くようです。Delphiの場合は、libファイルは使えません。平野@ラネックスさん、サンプルをありがとうございます。 Function BSendMail( szServer, // smtp server name szTo, // to szFrom, // from szSubject, // subject szBody, // body szFile:LPCSTR; // Attach Files split by tab char msg:LPSTR):Integer; // error message cdecl external 'Bsmtp.dll'; procedure TForm1.Button1Click(Sender: TObject); var wkstr : array[0..80]of Char; begin if (BSendMail( PChar(Edit1.Text), // smtp server name PChar(Edit2.Text), // to PChar(Edit3.Text), // from PChar(Edit4.Text), // subject PChar(''), // body PChar(Edit5.Text), // Attach Files split by tab char wkstr) <> 0 )Then begin Showmessage('出力しました'); end else begin Showmessage(wkstr); end; end; Delphiでのメール受信のサンプルです。Thanks です北畑さん。 unit BSMTP; interface uses Windows; type TBSMTPStatus = record Counter: integer; Status : array[0..255] of LPSTR; end; TPBSMTPStatus = ^TBSMTPStatus; function BSendMail( szServer, // smtp server name szTo, // to szFrom, // from szSubject, // subject szBody, // body szFile:LPCSTR; // Attach Files split by tab char msg:LPSTR // error message ):Integer; cdecl external 'Bsmtp.dll'; procedure BFreeArray(Status:TPBSMTPStatus); cdecl external 'Bsmtp.dll'; function BPOP3( szServer, // pop3 server name szName, // NAME szPass, // PASSWORD szCommand, // COMMAND szPath:LPCSTR; // directory Status:TPBSMTPStatus; // return ARRAY LIST msg:LPSTR // 80 bytes length message area ):Integer; cdecl external 'Bsmtp.dll'; function BMIME( szCommand, // command name szFileName, // Target Name szPath:LPCSTR; // Target Name Status:TPBSMTPStatus; // return ARRAY LIST msg:LPSTR // 80 bytes length message area ):Integer; cdecl external 'Bsmtp.dll'; implementation end. FlushMail APIの使い方2003/02/11 New ! BSendMail API関数でメールキューに作成したメールファイルをSMTPプロトコルでメール送信します。複数メールファイルを一度のTCPコネクションで送信するので効率よくメールが送れます。バックグラウンド(別プロセスでbsendm.exeがFlushMailメソッドを実行)モードでの送信も可能です。 メールファイルは以下のようなテキスト形式です。 1行目:宛先メールアドレス 2行目:送信元メールアドレス 3行目:件名 4行目:添付ファイル名 5行目以降:本文 * 関数プロトタイプを次のように定義 extern "C" __declspec(dllimport) int BFlushMail(LPCSTR szServer, // smtp server name LPCSTR szDir, // メールキュー名 LPCSTR szLogfile); // ログファイル名PASSWORD char svr[] = "smtp-server"; // バックグラウンド指定は "&smtp-server" char mdir[] = "c:\\temp\\maildir"; char logfile[] = "c:\\temp\\log.txt"; int rc = BFlushMail(svr,mdir,logfile); cc/bcc/reply-toや任意のヘッダーの使い方 宛先メールIDパラメータの中にタブで区切ってcc/bcc/reply-to キーワードを指定します。任意のヘッダーは、">"文字をつけてそのまま指定します。 使用例: ●宛先が id1 、CC に id2、Message-IDヘッダーの例 szTo = "id1\tcc\tid2\t>Message-ID: 12345" ●宛先が id1とid2 、CC に id3の例 szTo = "id1\tid2\tcc\tid2" ●宛先が id1とid2 、CC に id3 id4 の例 szTo = "id1\tid2\tcc\tid3\tid4" ●宛先が id1 、BCC に id2の例 szTo = "id1\tbcc\tid2" ●宛先が id1 、CC に id2、BCCに id3の例 szTo = "id1\tcc\tid2\tbcc\tid3" ●宛先が id1 、Reply-To に id2の例 szTo = "id1\treply-to\tid2" ●CC に id2の例 szTo = "cc\tid2" ●BCC に id2の例 szTo = "bcc\tid2" ●メール送信の拡張オプション 2000/01/23 のバージョンから次のオプションがサポートされます。 1. 代表宛先名 "@to-header" 先頭が"@" ならば 先頭の "@" を削除して To: ヘッダーとして送信します。メールアドレス以外の名前を使えます。日本語も使えます。メーリングリストに最適。必ず、bccあるいはcc と共に使うこと。例: mailto = "@Centerfolds-ML-User\tbcc\twho@hoge.com"; 次のように送信します。 To: Centerfolds-ML-User 2. 転送モード ">#xfr file-name" 指定されたファイルを転送します。RcvMail メソッドで作成されたファイルを指定します。 To: ヘッダーは、削除されますので宛先を指定してください。サブジェクトは、上書きされます。サブジェクトが"" なら元のサブジェクトをそのまま送信します。パラメータとして指定された本文と添付ファイルは、無視されます。次のヘッダーは、ファイルから削除されます。 X-Mailer: X-Mail-Agent: Status: To: Return-Path: Delivered-To: 例1: mailto = "who@hoge.com\t>#xfr c:\\mail\\b21xxx.tmp"; 例2: mailto = "@ML-user\t>#xfr c:\\mail\\b21xxx.tmp\tbcc\twho@hoge.com"; 3. 転送モード時のヘッダー削除 ">#d" 転送するメールの該当ヘッダーを削除したいときに指定します。例: mailto = "@ML-user\t>#xfr c:\\mail\\b21xxx.tmp\t>#dcc:\tbcc\twho@hoge.com"; 4. Bcc ファイル入力モード ">#bcc file-name" メールアドレスをファイルから1行ずつ入力して メールを送信します。送信アドレスは、ヘッダーとして送信しない Bcc として処理しますメールアドレスは、メールIDのみを指定してください。例: mailto = "@ML-user\t>#xfr c:\\mail\\b21xxx.tmp\t>#bcc c:\\mai\\mailto.txt"; mailto.txt の内容: # comment 1桁目が "#" の行はコメントとして無視されます who@hoge.com who1@hoge.com who2@hoge.com SMTPサーバ名の確認方法 SMTPサーバ名は、telnet コマンドで確認できます。次のようにポート番号25を使って telnet コマンドを打って応答が返ってくるサーバ名がSMTPサーバです。 > telnet サーバ名 25 メール受信APIの使い方 POP3プロトコルでメールを受信します。 * 関数プロトタイプを次のように定義 struct RetArray { int counter; char* array[256]; }; extern "C" __declspec(dllimport) void BFreeArray(RetArray* parray); extern "C" __declspec(dllimport) int BPOP3( LPCSTR szServer, // pop3 server name LPCSTR szName, // NAME LPCSTR szPass, // PASSWORD LPCSTR szCommand,// COMMAND LPCSTR szPath, // directory RetArray* RetArray, // return ARRAY LIST LPSTR msg // 80 bytes length message area ); extern "C" __declspec(dllimport) int BMIME( LPCSTR szCommand, // command name LPCSTR szFileName, // Target Name LPCSTR szPath, // Target Name RetArray* RetArray, // return ARRAY LIST LPSTR msg // 80 bytes length message area ); * BPOP3関数 BPOP3関数は、メールサーバからメールを受信してファイルに書込みます。 パラメータの説明: szServer * POP3サーバ名を指定。IPアドレスでも可。タブで区切ってポート番号を 指定できます。 szName  * メールアカウントのユーザ名 szPass * メールアカウントのパスワード名 2000/05/20 APOPをサポート APOP 認証をするには、パスワードの前に "a" または "A" に 1個の ブランクをつけます。 "a xxxx" : サーバがAPOP 未対応なら通常のUSER/PASS 処理をします。 "A xxxx" : サーバがAPOP 未対応ならエラーになります。 szCommand * 処理コマンド。大文字小文字どちらでも可。 STAT ...... メール数と総バイト数のみを返します LIST ...... すべてのメールのSubject、From、Dateヘッダーの内容のみを 返します。 SAVE n .... n番目のメールを受信します SAVD n .... n番目のメールを受信し、サーバのメールボックスから 削除します SAVEALL ... 全てのメールを受信します SAVEALLD .. 全てのメールを受信し、サーバのメールボックスから 削除します szPath * 受信したメールを保存するディレクトリ名を指定します。 RetArray * メール受信の結果を配列で返します。配列内容はコマンドによって 次のようになります。エラーが発生した場合は、配列を返しません。 SAVExxx - 受信ファイル名。 STAT - メール数と総バイト数。 LIST - タブで区切られたSubject、From、Dateヘッダーの内容 msg * メッセージ領域(80バイト) 戻り値 * 1以上だと正常終了。 * BMIME関数 BMIME関数は、BPOP3関数で受信したRFC822形式のファイルを読込みます。 パラメータの説明: szCommand * コマンド。大文字小文字どちらでも可。 GET ...... メールをヘッダー、本文、添付ファイルを読込みます。 GETNOF ... メールをヘッダー、本文のみ読込みます。 HEAD ...... メールのヘッダーのみ読込みます。 szFileName * BPOP3で書込まれたRFC822形式のファイル名 szPath * 添付ファイルを保存するディレクトリ名を指定します。 RetArray * メール受信の結果を配列で返します。配列内容はコマンドによって 次のようになります。エラーが発生した場合は、配列を返しません。 HEAD - ヘッダー。 GET - ヘッダー、本文、添付ファイル名。 GETNOF - ヘッダー、本文。 msg * メッセージ領域(80バイト) 戻り値 * 1以上だと正常終了。 * BFreeArray関数 BFreeArray関数は、BPOP3関数とBMIME関数で使用した配列メモリを開放します。 パラメータの説明: parray * RetArray構造体のアドレス # BPOP3関数とBMIME関数の使い方 char msgx[80]; RetArray ret1,ret2; int rc = BPOP3( "server1","user1","pass1", "save 1","c:\\mail",&ret1,msgx); if (rc <= 0) return false; rc = BMIME("get",ret1.array[0],"c:\\mail",&ret2,msgx); if (rc > 0) { FILE *fp = ::fopen("c:\\mail\\mail.txt","wb"); for (int i= 0;i < rc ;i++) { ::fwrite(ret2.array[i],1,strlen(ret2.array[i]),fp); ::fwrite("\015\012",1,2,fp); // put CRLF } ::fclose(fp); } DeleteFile(ret1.array[0]); BFreeArray(&ret1); BFreeArray(&ret2); # BPOP3関数でのコールバック関数の使い方 typedef BOOL (APIENTRY *pcallback)(int itemno,int len); static BOOL APIENTRY CallBack(int itemno,int len) { return 0; // 1 でキャンセルできます } char msgx[80]; RetArray ret1; char name[200]; // ユーザ名 [tab] コールバック関数アドレス wsprintf(name,"user1\t%ld",(long)CallBack); int rc = BPOP3( "server1",name,"pass1", "saveall","c:\\mail",&ret1,msgx); ご注意 Visual C++以外のコンパイラでの動作確認を行っておりません。 babaqフリーソフトのご使用上の注意 ●プログラムを使って発生した損害に関しては、一切の責任を負いません。 ●使用、配布に制限はありません。自由にお使いください。 ●動作の保証はありません。 ●動作を確認したOSは、Windows NT 4.0 とWindows 95/98/Me/XP/2000のみです。 ========================================================================================== ========================================================================================== Visual Basic Tips 2003.02.11 更新 Visual BasicやVBAならBASP21コンポーネントを使わなくてもメール送受信や正規表現処理が簡単にできます。 BSMTP DLLやBREGEXP DLLを直接Visual Basicから呼出せばいいのです。 Excelでのメール送信サンプルは、 http://homepage1.nifty.com/gak/MSTips/multimail.htmをどうぞ。 メールを送信する SendMail関数を呼んでメールを送信するサンプルです。 BSMTP.DLLをWindowsのsystemディレクトリかVBアプリケーションを置くディレクトリにコピーします。 Option Explicit Private Declare Function SendMail Lib "bsmtp" _ (szServer As String, szTo As String, szFrom As String, _ szSubject As String, szBody As String, szFile As String) As String Private Declare Function FlushMail Lib "bsmtp" _ 2003/02/11 New ! (szServer As String, szDir As String, szLogfile As String) As Long Private Sub Form_Load() Dim ret As String Dim szServer As String, szTo As String, szFrom As String Dim szSubject As String, szBody As String, szFile As String szServer = "your smtp" ' SMTPサーバ名。 'タブで区切ってポート番号を指定できます。 szTo = "who@who.com" ' 宛先 ' 複数の宛先に送付するときは、アドレスをタブで区切って ' いくらでも指定できます。 szTo = "who1@who1.com" & vbTab & "who2@who2.com" ' 複数宛先 ' CCを指定するには次のようにします。 szTo = "who@who.com" & vbTab & "cc" & vbTab & "who2@who2.com" & _ vbTab & "who3@who3.com" ' BCCを指定するには次のようにします。 szTo = "who@who.com" & vbTab & "bcc" & vbTab & "who2@who2.com" & _ vbTab & "who3@who3.com" ' ヘッダを指定するには次のようにタブで区切り、>をヘッダの前に ' つけます。 szTo = "who@who.com" & vbTab & ">Message-ID: 12345" szFrom = "my@my.com" ' 送信元 szSubject = "はじめまして" ' 件名 ' 本文内で改行するには、vbCrLfを使います。 szBody = "こんにちは。" & vbCrLf & "さようなら" ' 本文 ' ファイルを添付するときは、ファイル名をフルパスで指定します。 ' ファイルを複数指定するときは、タブで区切ってください。 szFile = "c:\a1.gif" & vbTab & "c:\a2.jpeg" ' ファイル2個 ' ファイルを添付しないときは次のようにします。 szFile = "" ' ファイル添付なし ret = SendMail(szServer, szTo, szFrom, szSubject, szBody, szFile) ' 送信エラーのときは、戻り値にエラーメッセージが返ります。 If Len(ret) <> 0 Then msgbox "エラー" & ret End If ' メールキューにメールファイルを作成2003/02/11 New ! Dim mdir As String, szLogfile As String Dim rcnt As Long mdir= "c:\temp\mdir" ' メールファイルを作成するフォルダ(メールキュー) rcnt = SendMail(mdir, szTo, szFrom, szSubject, szBody, szFile) ' rcnt にはメールキュー内のメールファイル数が返ります。 ' szLogfile = "c:\temp\log.txt" ' ログファイル名 rcnt = FlushMail(szServer, szTo, mdir, szLogfile) ' rcnt には送信OKのメール数が返ります。 End Sub SMTPサーバ名って何でしょう サーバ名とはSMTPプロトコルをサポートしたメールサーバソフトが動作しているマシン名です。インターネットメールサーバ名ともいいます。 Outlookなどのメールソフトでインターネットメールの設定プロパティの [メールボックス情報]-[インターネットメールサーバー]に指定する名前です。 次に名前が正しいかどうか確認する方法を説明します。 メール送信するPCでコマンドプロンプトに入ります。 telnet コマンドをSMTPサーバ名とポート番号25で実行します。 > telnet server 25 これで次のような応答が返ってくれば正しいサーバ名です。 220 xxxxxxxxxxxxxxxxxx ESMTP Sendmail 8.8.7/xxxxx ready at Sat, 29 Nov 1997 10:21:26 +0900 SMTPコネクションを切断するには quit コマンドを打ちます。 > quit SendMail関数が遅いんです SendMail関数を呼出すとメールサーバにメールデータを送信し終わるまで待ちます。 次に紹介するSendMailEx関数を使えばすぐに処理が戻ります。 SendMailEx関数は、メール送信処理を別プロセス(Bsendm.exe)に任せてさっさと終了します。 SendMailEx関数を使うにはBsendm.exeをWindowsのsystemディレクトリにコピーしておく必要があります。 Option Explicit Private Declare Function SendMailEx Lib "bsmtp" _ (szLogfile As String, szServer As String, szTo As String, _ szFrom As String, szSubject As String, szBody As String, szFile As String) As String Private Sub Form_Load() Dim ret As String Dim szLogfile As String Dim szServer As String, szTo As String, szFrom As String Dim szSubject As String, szBody As String, szFile As String ' メール送信結果を記録するファイル名を指定します。 szLogfile = "c:\log.txt" szServer = "your smtp" ' SMTPサーバ名 'タブで区切ってポート番号を指定できます。 szTo = "who@who.com" ' 宛先 szFrom = "my@my.com" ' 送信元 szSubject = "はじめまして" ' 件名 szBody = "こんにちは。" & vbCrLf & "さようなら" ' 本文 szFile = "c:\a1.gif" & vbTab & "c:\a2.jpeg" ' ファイル2個 ret = SendMailEx(szLogfile,szServer, szTo, szFrom, szSubject, szBody, szFile) ' パラメータエラーのときは、戻り値にエラーメッセージが返ります。 If Len(ret) <> 0 Then msgbox "エラー" & ret End If End Sub メールを受信したい メールを受信するにはRcvMail関数を使います。RcvMail関数でメールボックスからメールを取出してみましょう。 Option Explicit Private Declare Function RcvMail Lib "bsmtp" _ (szServer As String, szUser As String, szPass As String, _ szCommand As String, szDir As String) As Variant Private Sub Form_Load() Dim szServer As String, szUser As String, szPass As String Dim szCommand As String, szDir As String Dim ar As Variant, v As Variant szServer = "your pop3 server" 'SMTPサーバ名と同じでよい。 'タブで区切ってポート番号を指定できます。 szUser = "your-name" 'メールアカウント名 szPass = "pass" 'パスワード 2000/05/20 APOPをサポート APOP 認証をするには、パスワードの前に "a" または "A" に 1個の ブランクをつけます。 "a xxxx" : サーバがAPOP 未対応なら通常のUSER/PASS 処理をします。 "A xxxx" : サーバがAPOP 未対応ならエラーになります。 szCommand = "SAVE 1-3" 'コマンド メールの1件目から3件目までを受信 szDir = "c:\maildata" '受信したメールを保存するディレクトリ ar = RcvMail(szServer, szUser, szPass, szCommand, szDir) '戻り値が返る変数は、Variantタイプを指定すること。 '受信したメール1通ごとにファイルが作成されます。 'メールに添付されたファイルは、本文と共に1つのファイルに含まれます。 'ReadMail関数で添付ファイルを取出します。 If IsArray(ar) Then '正常終了時のSAVEコマンドの戻り値は、配列になります。 For Each v In ar Debug.Print v 'メールデータが保存されたファイル名がフルパスで戻ります。 'このファイル名をReadMailのパラメータとして渡します。 Next Else Debug.Print ar 'エラー発生時は、配列でなくメッセージが戻ります。 End If End Sub コマンドは、次のように指定します。  STAT ...... メールボックスに到着しているメール数と総バイト数のみを返します  LIST [n[-n2]] ...... メールのSubject、From、Dateヘッダーの内容のみを   返します。範囲も指定できます。  SAVE n[-n2] .... n番目のメールを受信します。範囲も指定できます。  SAVD n[-n2] .... n番目のメールを受信し、サーバのメールボックスから   削除します。範囲も指定できます。  SAVEALL ... 全てのメールを受信します  SAVEALLD .. 全てのメールを受信し、サーバのメールボックスから   削除します  DELE n[-n2] .... n番目のメールをメールボックスから削除します。        範囲も指定できます。 RcvMail関数の戻り値は、Variantタイプで指定します。正常に処理が終了したとき 配列で値が返されます。エラーが発生した場合は、配列を返しません。 配列内容はコマンドによって次のようになります。  STAT - メール数と総バイト数。例:output(0) -> 2 4011  LIST - タブで区切られたSubject、From、Dateヘッダーの内容  例:output(0) -> こんにちは\txxxx@xxxx.xxx\t1998/09/15 11:11:30   output(1) -> こんにちは2\txxxx@xxxx.xxx\t1998/09/15 12:11:30  SAVE/SAVED/SAVEALL/SAVEALLD - 受信したメールを保存したファイル名。 DELE - メッセージが返ります。  例:"3 message(s) deleted" メールが保存されるファイルの内容は、RFC822タイプの形式です。 添付ファイルも同じファイルに含まれています。 このRFC822タイプのファイルを読んでヘッダーや本文、添付ファイルを取出したりするには 次に説明するReadMail関数を使います。 メールの受信状態を知りたい メールを受信状態を知るにはRcvMail2関数を使います。RcvMail2関数でコールバック関数を指定すると受信中のメールごとに受信バイト数が通知されます。コールバック関数でメールの受信処理をキャンセルすることもできます。 Option Explicit Private Declare Function RcvMail2 Lib "bsmtp" _ (szServer As String, szUser As String, szPass As String, _ szCommand As String, szDir As String, callback As Long) As Variant Private Sub Form_Load() Dim szServer As String, szUser As String, szPass As String Dim szCommand As String, szDir As String Dim ar As Variant, v As Variant szServer = "your pop3 server" 'SMTPサーバ名と同じでよい。 szUser = "your-name" 'メールアカウント名 szPass = "pass" 'パスワード szCommand = "SAVE 1-3" 'コマンド メールの1件目から3件目までを受信 szDir = "c:\maildata" '受信したメールを保存するディレクトリ ar = RcvMail2(szServer, szUser, szPass, szCommand, szDir, AddressOf RcvMailCallBack) End Sub ' コールバック関数は、モジュールに配置すること Public Function RcvMailCallBack(ByVal item As Long, ByVal totlen As Long) As Long Debug.Print item ' 受信数 Debug.Print totlen ' 受信バイト数 RcvMailCallBack = 0 ' キャンセルするとき 戻り値に 1 を指定 End Function パラメータや戻り値は、RcvMail関数と同じです。 コールバック関数が有効になるのは、次のSAVE 系のコマンドのみです。  SAVE n[-n2] .... n番目のメールを受信します。範囲も指定できます。  SAVD n[-n2] .... n番目のメールを受信し、サーバのメールボックスから   削除します。範囲も指定できます。  SAVEALL ... 全てのメールを受信します  SAVEALLD .. 全てのメールを受信し、サーバのメールボックスから   削除します その他の LIST コマンドなどでは、コールバック関数の呼出しは行いません。 ReadMail関数を使ってメールの内容を読む RcvMail関数でメールボックスから取出したメールを読むには、ReadMail関数を使います。 Option Explicit Private Declare Function ReadMail Lib "bsmtp" _ (szFilename As String, szPara As String, szDir As String) As Variant Private Sub Form_Load() Dim szFilename As String, szPara As String, szDir As String Dim retv As Variant, v As Variant szFilename = ar(0) ' ファイル名にはRcvMailの戻り値の配列からファイル名を設定 szDir = "c:\mail" ' 添付ファイルが保存されるディレクトリ szPara = "subject:from:date:" ' ヘッダーの指定 ' nofile: とすると添付ファイルを保存しません。 retv = ReadMail(szFilename,szPara,szDir) If IsArray(retv) Then For Each v In retv Debug.Print v Next Else Debug.Print retv End If End SUb ReadMail関数は、読込んだメールの内容を配列で返します。 入力となるファイル名は、RcvMailで作成されたファイルを指定します。 ヘッダー、本文、添付ファイル名の順番に設定されます。 エラーが発生した場合は、配列を返しません。 例:output(0) -> To: xxxx@xxxx.xxx output(1) -> From: who@who.com output(2) -> Date: 1998/09/15 12:30:31 output(3) -> ..... output(4) -> Body: 本文 output(5) -> File: ファイル名1 output(6) -> File: ファイル名2 SortMail関数を使ってメールの内容をソート SortMail関数を使えば RcvMail関数で保存したメールをソートしたり選択したりできます。 Option Explicit Private Declare Function SortMail Lib "bsmtp" _ (szDir As String, szHeader As String, opt As Long, _ szFilter As String,delflag As Long) As Variant Private Sub Form_Load() Dim szDir As String, szHeader As String, opt As Long Dim szFilter As String, delflag As Long Dim retv As Variant, v As Variant szDir = "c:\mail" ' メールファイルのディレクトリ szFilter = "date:" ' ソートヘッダーの指定 opt = 1 ' 逆順ソート szFilter = "from:=babaq" ' 送信元が babaq delflag = 0 ' 削除しない retv = SortMail(szDir,szHeader,opt,szFilter,delflag) If IsArray(retv) Then For Each v In retv Debug.Print v Next Else Debug.Print retv End If End Sub szDir : メールファイルのディレクトリ名。 szHeader : ソート対象のヘッダ名。ソートしない場合(選択や削除のみ)は、""。 * で総称名が使えます。 例: "From:" - 送信元でソート "Date:" - 送信日付でソート "Subject:" - 件名でソート "X-Mail*" - X-Mailer または X-Mail-Agent ヘッダでソート。 opt : ソートオプションを数字で指定。デフォルト値は、0。 0 - 順ソート 1 - 逆順ソート 2 - 大文字小文字無視 szFilter : 選択オプション。デフォルトは、"" ですべて選択します。 ヘッダ名 + 条件 + 文字列で指定します。 ヘッダ名は、*: で総称指定できます。 文字列は、大文字小文字を無視します。 文字列を指定しないと、ヘッダが存在するしないで選択できます。 本文("Body:")や添付ファイル("File:")も指定可能。 条件: = 後続の文字列を含むものを選択 ! 後続の文字列を含まないものを選択 例: "From:=babaq" - 送信元にbabaq を含むメール "To:!hoge" - 宛先に hoge を含まないメール "Body:=babaq" - 本文に babaq を含むメール "References:=" - References ヘッダを含むメール "References:!" - References ヘッダを含まないメール "X-Mail*:=outlook" - Microsoft OutLook で送信したメール X-Mailer または X-Mail-Agent: ヘッダが該当します。 delflag : 削除オプション。選択オプションと共に使います。デフォルトは、0。 0 - 削除しません。 1 - 選択条件に一致したものを削除します。 outarray : ソート(あるいは選択、削除)されたファイル名を配列で返します。 エラーや該当するメールファイルがないときは配列でなく文字列が返ります。 使用例: Dim dirx As String, outarray As Variant dirx = "d:\mail" outarray = SortMail(dirx,"date:",1,"",0) ' 最新日付の順にソート ' 古い日付の順にソート。Fromヘッダに hoge が含まれているメールのみ outarray = SortMail(dirx,"date:",0,"from:==hoge",0) ' Fromヘッダに hoge が含まれているメールのみ削除 outarray = SortMail(dirx,"",0,"from:==hoge",1) ' 添付ファイルがあるメールのみ削除 outarray = SortMail(dirx,"",0,"File:=",1) ' Beckyで送信されたメールのみ取出す outarray = SortMail(dirx,"",0,"X-Mailer:=becky",0) 正規表現を使ってみたい 正規表現は、文字列をパターンとして処理することができます。ここではBREGEXP DLLが提供するMatch/MatchEx/Replace/Translate/Split関数を紹介します。はじめに、BREGEXP.DLLをWindowsのsystemディレクトリかVBアプリケーションを置くディレクトリにコピーします。 Private Declare Function Match Lib "bregexp" _ (szRegstr As String, szTarget As String) As String Private Declare Function MatchEx Lib "bregexp" _ (szRegstr As String, szTarget As String, mode As Long) As Variant Private Declare Function Replace Lib "bregexp" _ (szRegstr As String, szTarget As String) As String Private Declare Function Translate Lib "bregexp" _ (szRegstr As String, szTarget As String, ret As String) As Long Private Declare Function Split Lib "bregexp" _ (szRegstr As String, szTarget As String, limit As Long) As Variant '◆Match ' Match関数は、パターンマッチで文字列検索を行ない、"1" または偽 ("0") を返します。 ' グループメタ文字"()"を使った場合は、マッチした文字列を返します。 ' szRegstr : パターン。 ' szTarget : 対象文字列。 ' 戻り値 : "1"または"0"またはマッチした文字列。 ' パターンは、次のように指定します。パターンの詳細は、Perlのマニュアルを参照。 ' /PATTERN/gik ' g グローバルにマッチ、つまり、すべてを探し出す ' i 大文字、小文字を区別しない ' k 日本語を処理する。日本語をシングル文字として処理しない。 ' m 文字列を複数行として扱う。 ' ret = Match("/\d{3}/", szTarget) If ret then '数字が3桁含まれている End If ' 連続している3桁の数字を取出す ret = Match("m/(\d{3})/", szTarget) ' ' '◆MatchEx ' MatchEx関数は、パターンマッチの拡張版です。正規表現メモリ(Perl の $1 $2 に対応)や ' すべてのマッチ文字を' を返します。グループメタ文字"()"は、マッチした文字を記憶します。 ' szRegstr : パターン。 ' szTarget : 対象文字列。 ' mode : マッチモードを数字で指定します。 ' 0 : 正規表現メモリモード ' 1 : すべてのマッチ文字を返します ' 戻り値 : マッチ結果を配列で返します。 ' 正規表現メモリモード: ' out(0) : マッチした文字列そのもの。Perl では $& 。 ' out(1) : マッチ文字列の前の文字列。Perl では $` 。 ' out(2) : マッチ文字列の後の文字列。Perl では $' 。 ' out(3) : メモリ1の文字列。Perl では $1 。 ' out(4) : メモリ2の文字列。Perl では $2 。 ' out(n) : メモリnの文字列。Perl では $n 。 ' すべてのマッチ: ' out(0) : マッチした文字列1。 ' out(1) : マッチした文字列2。 ' out(2) : マッチした文字列3。 ' out(n) : マッチした文字列n。 ' ' ret = MatchEx("/\d{3}/", szTarget,1) ' すべての3桁の数字を求める If IsArray(ret) then ' 配列のとき、マッチ Dim v As Variant For Each v In ret Debug.Print v Next End If ' ' '◆Replace ' Replace関数は、文字列中でパターンを検索し、もし見つかれば、置換テキストで置き換えた ' 文字列を返します。 ' szRegstr : パターン。 ' szTarget : 対象文字列。 ' 戻り値 : 置換後の文字。 ' パターンは、次のように指定します。パターンの詳細は、Perlのマニュアルを参照。 ' s/PATTERN/REPLACEMENT/gikm ' ' 数字をすべてxに変更する例。 ret = Replace("s/\d/x/g", szTarget) ' ' Perlのマニュアルに出てた最初の 2 語を入替える例。なんの意味があるのでしょうか(笑) ret = Replace("s/^([^ ]*) *([^ ]*)/$2 $1/",szTarget) ' ' '◆Translate ' Translate関数は、検索リスト (SEARCHLIST) に含まれる文字を、対応する置換リスト ' (REPLACEMENTLIST) の文字に変換します。また、置換または削除が行なわれた、文字数を返します。 ' szRegstr : パターン。 ' szTarget : 対象文字列。 ' ret : 置換後の文字列。 ' 戻り値 : 文字数。 ' パターンは、次のように指定します。パターンの詳細は、Perlのマニュアルを参照。 ' tr/SEARCHLIST/REPLACEMENTLIST/cds ' ' オプションには、 ' c SEARCHLIST を補集合にする ' d 見つかったが置換されなかった文字を削除する ' s 置換された文字が重なったときに圧縮する ' k 日本語を処理する。日本語をシングル文字として処理しない。 ' ' 小文字を大文字に変更する例。 Dim ctr as Long ctr = Translate("tr/a-z/A-Z/", szTarget, ret) ' ' '◆Split ' Split関数は 文字列を文字列の配列に分割して、それを返します。 ' szRegstr : パターン。Match関数と同じ。 ' szTarget : 対象文字列。 ' limit : 配列数の制限値。0を指定すると無制限。 ' 戻り値 : 配列。 Dim retv as Variant,v as Variant retv = Split("/\d/k", "5,4,6,c", 30) If IsArray(retv) Then For Each v In retv Debug.Print v Next Else Debug.Print retv End If プログラムコードのご使用上の注意 ●プログラムコードを使って発生した損害に関しては、一切の責任を負いません。 ●使用、配布に制限はありません。自由にお使いください。 ●動作の保証はありません。 ●動作を確認したOSは、Windows NT 4.0 とWindows 95/98/Me/XP/2000のみです。