- ベストアンサー
メール送信を行うJavaプログラム
import java.io.*; import java.net.*; public class sendMail { public static void main(String [] args) { try { Socket MailSocket = new Socket((メールサーバのIPアドレス), 25); BufferdReader BufferIn = new BufferedReader(new InputStreamReader(MailSocket.getInputStream())); BufferedWriter BufferOut = new BufferedWriter(new OutputStreamWriter(MailSocket.getOutputStream(), "ISO2022JP")); if(!BufferIn.readLine().startsWith("220")) System.exit(1); BufferOut.write("HELO (SMTPクライアントのFQDN)\r\n"); if(!BufferIn.readLine().startsWith("250")) System.exit(1); BufferOut.write("MAIL FROM: (送信元メールアドレス)\r\n"); if(!BufferIn.readLine().startsWith("250")) System.exit(1); BufferOut.write("RCPT TO: (宛先メールアドレス)\r\n"); if(!BufferIn.readLine().startsWith("250")) System.exit(1); BufferOut.write("DATA\r\n"); if(!BufferIn.readLine().startsWith("354")) System.exit(1); BufferOut.write("Subject:テスト\r\n\r\n"); BufferOut.write("これはテストメールです。\r\n.\r\n"); if(!BufferIn.readLine().startsWith("250")) System.exit(1); BufferOut.write("QUIT\r\n"); if(!BufferIn.readLine().startsWith("221")) System.exit(1); BufferOut.flush(); MailSocket.close(); } catch(Exception e) { System.err.println(e); System.exit(1); } } } 以上のようなプログラムを作ったのですが、「java sendMail」で実行しようとすると、何のエラーも表示されずに止まってしまいます。もちろんメールも送信されていません。(javacは正常にできました。) どこが悪いのかご指摘ください。よろしくお願いいたします。
- みんなの回答 (4)
- 専門家の回答
質問者が選んだベストアンサー
APIを使わずにってことですよね。 以前に作ったものを載せて起きますので 参考にしてください。 /********************************************* * JavaMail (アプリケーション) * *********************************************/ // ライブラリの利用 import java.net.*; import java.io.*; import java.util.*; /*********************************************************** * Mailクラス * * Mailクラスは,Mailプログラムの本体です。 * ***********************************************************/ public class JavaMail { // SMTP接続用ポート番号(25番) final int intSmtp_Port = 25; // 送信用サーバ String strSmtp_Server = ""; // 自分のメールアドレス String strMy_Email_Addr = "" ; /*********************************************************************** * sendCommandAndResultCheckメソッド * * SMTPコマンドをサーバに送信し,返答コードの確認を行います。 * ***********************************************************************/ //SMTPコマンドをサーバに送信し、resultCheckを用いて返答コードを確認する public void sendCommandAndResultCheck (Socket smtp, BufferedReader smtp_in, PrintWriter smtp_out, String command, int success_code) throws IOException { //コマンドの送信 smtp_out.print(command + "\r\n"); /********************************************** ファイルに対して確実に出力を行うためには, ストリームのフラッシュを行わなければならない **********************************************/ smtp_out.flush(); //送信内容の表示 System.out.println("送信内容表示> " + command); //結果のチェック resultCheck(smtp, smtp_in, smtp_out, success_code); } /*************************************************************** resultCheckメソッド 返答コードをチェックして,エラーならばコネクションを閉じます ***************************************************************/ // resultCheckで返答コードをチェックし、エラーならばコネクションを閉じる public void resultCheck (Socket smtp, BufferedReader smtp_in, PrintWriter smtp_out, int success_code) throws IOException { //返答コードの読み取り String strRes = smtp_in.readLine(); System.out.println("返答コード> " + strRes); // もし返答コードが期待されるコード(success_code)でなければ・・・ if (Integer.parseInt(strRes.substring(0,3)) != success_code) { // コネクションを閉じます smtp.close(); throw new RuntimeException(strRes); } } /***************************** sendメソッド SMTPのセッションを進めます *****************************/ public void send(String subject, String[] to,String[] msgs) throws IOException { /**************************************** CONNECT Socketクラスのオブジェクトsmtpを使って、 ****************************************/ Socket smtp = new Socket(strSmtp_Server, intSmtp_Port); //ネットワーク入出力に必要なストリームを作成する BufferedReader smtp_in = new BufferedReader (new InputStreamReader(smtp.getInputStream())); PrintWriter smtp_out = new PrintWriter(smtp.getOutputStream()); //resultCheckメソッドで返答コード(220)をチェックする resultCheck(smtp, smtp_in, smtp_out, 220); /********************************************************** HELOコマンドの送付 getLocalHost,getHostNameで自分のコンピュータ名を取出す **********************************************************/ String strMyName = InetAddress.getLocalHost().getHostName(); /************************************************ sendCommandAndResultCheckでメールサーバにHELO コマンドを送付、返答コードをチェック ************************************************/ sendCommandAndResultCheck (smtp, smtp_in, smtp_out, "HELO " + strMyName, 250); /******************************************************* MAIL FROMコマンドの送付 sendCommandAndResultCheckでメールサーバにMAIL FROM コマンドを送付、返答コードをチェック *******************************************************/ sendCommandAndResultCheck (smtp, smtp_in, smtp_out, "MAIL FROM:" + strMy_Email_Addr, 250); /*************************** RCPT TOコマンドの送付 送先が複数の場合繰返し ***************************/ for (int i = 0; i < to.length; i++) { // sendCommandAndResultCheckでメールサーバにRCPT TO sendCommandAndResultCheck(smtp, smtp_in, smtp_out, "RCPT TO:" + to[i], 250); } /********************************************************************* DATAコマンドによるメールの送付 sendCommandAndResultCheckでメールサーバにDATA、Subjectヘッダの送付 *********************************************************************/ sendCommandAndResultCheck(smtp, smtp_in, smtp_out, "DATA", 354); /*************************************** コマンドを送付、返答コードをチェック Subjectを送付 ***************************************/ smtp_out.print("Subject:" + subject + "\r\n"); System.out.println("送信> " + "Subject:" + subject) ; //空白を送付 smtp_out.print("\r\n"); /******************************** メッセージ各行の送付 メッセージが複数の場合繰返し ********************************/ for(int i = 0; i<msgs.length - 1; ++i) { //メッセージmsgsを送付 smtp_out.print(msgs[i]+"\r\n"); System.out.println("送信> " + msgs[i]) ; } sendCommandAndResultCheck(smtp, smtp_in, smtp_out, "\r\n.", 250); /************************************************ QUITコマンドの送付 sendCommandAndResultCheckでメールサーバにQUIT ************************************************/ sendCommandAndResultCheck(smtp, smtp_in, smtp_out, "QUIT", 221); /************************************** コネクションのクローズ コマンドを送付、返答コードをチェック **************************************/ smtp.close(); } /******************************************************************* setAddressメソッド 送信に利用するメールサーバや利用者のメールアドレスをセットします *******************************************************************/ public void setAddress(){ String strBuf = "" ; /******************************************************* * InputStreamReader * * バイトストリームから文字ストリームへの橋渡し * *******************************************************/ BufferedReader BufLineread = new BufferedReader(new InputStreamReader(System.in)) ; boolean blnCnt = true ; try{ //アドレス入力のループ while(blnCnt) { System.out.println("メールサーバのアドレスを入力して下さい") ; //メールサーバを取得,smtp_serverに格納 strSmtp_Server = BufLineread.readLine() ; System.out.println("あなたのメールアドレスを入力して下さい") ; //利用者メールを取得,my_email_addressに格納 strMy_Email_Addr = BufLineread.readLine() ; System.out.println(" メールサーバのアドレス:" + strSmtp_Server) ; System.out.println(" あなたのメールアドレス:" + strMy_Email_Addr) ; System.out.println("以上でよろしいですか?(y/n)") ; strBuf = BufLineread.readLine() ; if("y".equals(strBuf)) blnCnt = false ; } } catch(Exception e) { e.printStackTrace(); System.exit(1); } } /******************************** setMsgsメソッド 送信メッセージを取り込みます ********************************/ public String[] setMsgs() { String strBuf = "" ; BufferedReader BufLineread = new BufferedReader(new InputStreamReader(System.in)) ; boolean blnCnt = true ; Vector msgs_Velist = new Vector(); String[] ArrayMsg = null ; try { System.out.println("送信したいメッセージを入力して下さい") ; System.out.println(" (改行してピリオドで終了)") ; // メッセージの入力 while(blnCnt) { //入力したメッセージを一行ことにstrBufに取り込み strBuf = BufLineread.readLine() ; //strBufをmsgs_listに格納する msgs_Velist.addElement(strBuf); //”.”まで繰り返す if(".".equals(strBuf)) blnCnt = false ; } ArrayMsg = new String[msgs_Velist.size()]; //msgs_listの内容をArrayMsgにコピーする msgs_Velist.copyInto(ArrayMsg); } catch(Exception e) { e.printStackTrace(); System.exit(1); } return(ArrayMsg) ; } /*********************************************************************** * mainprocメソッド * * 引数の処理などを行います * ***********************************************************************/ public void mainproc(String[] args){ String strMessage = "JavaMail subject to-address"; String strSubject = ""; Vector Velist = new Vector(); //サブジェクトや宛先の処理 //subject部分をstrSubjectに格納する strSubject=args[0]; //送信先は一つではないので、ループですべての送信先を格納 for (int i=1; i<args.length; i++) { //送り先のアドレスをVelistに格納する Velist.addElement(args[i]); } // 入力された引数の文字列へ変換 if (Velist.size() > 0) { try { String[] strTo = new String[Velist.size()]; /****************************************************** * copyInto() * * Vector の要素を、指定された配列にコピーします。 * ******************************************************/ //Velistの中の値を文字列に変換し、toに格納する Velist.copyInto(strTo); //メールサーバの情報を取得し、setAddressを呼出し setAddress() ; //メッセージを入力させる、msgsに格納する String[] msgs = setMsgs() ; // sendメソッドを呼出し、送信する send(strSubject, strTo, msgs); } catch(IOException e) { e.printStackTrace(); } } else { System.out.println("Message: " + strMessage); } } /*************************************** mainメソッド Mailクラスのオブジェクトを生成します ***************************************/ public static void main(String[] args) { //オブジェクト生成 JavaMail m = new JavaMail() ; //mainprocメソッドを呼出し、引数リストargsを渡す m.mainproc(args) ; } }
その他の回答 (3)
- chi-kon
- ベストアンサー率43% (58/132)
#02のものです。 flushは最後だけしているようですが、 最後だけでなくコマンド(?)ごとに送らなければ inputStreamからreadすることができないようです。 とまっているところもたぶんinputstreamのreadだと思いますよ。 sysoutを一行一行いれてみるとわかると思います。
お礼
回答ありがとうございます。 おぉぉぉ!!! コマンドごとにflush()を実行してみたところ、見事メールを送信することができました。 なるほどー!!! そういうことだったのですね。 ありがとうございました!!!!
- chi-kon
- ベストアンサー率43% (58/132)
writeしたらflushしないとだめじゃないですか?
お礼
回答ありがとうございます。 >writeしたらflushしないとだめじゃないですか? プログラム内で「BufferOut.flush()」としているのですが、それではだめなのでしょうか。もう少し詳しく説明してくださるとありがたいです。 よろしくお願いいたします。
- kamkamkam3
- ベストアンサー率42% (216/514)
私はjava.netパッケージを使った事がないので、分かりませんが、Javaでメールプログラムを作るときはJavaMailを使用するんじゃないでしょうか?そっちの方が簡単で確かだと思いますが。。 JavaMailについては、以下のURLか書籍などに載っています。
お礼
回答ありがとうございます。 >Javaでメールプログラムを作るときは >JavaMailを使用するんじゃないでしょうか? おっしゃるとおりなのですが、今回は事情がありまして、JavaMailを使用しないでメール送信のプログラムを作らなければならないのです。 ですので、申し訳ありませんが「JavaMail抜き」ということでよろしくお願いいたします。 (参考文献拝見しました。今後の参考にさせていただきます。)
お礼
回答ありがとうございます。 さっそく実行してみたところ、スムーズに実行できました!!! これからじっくりと腰を据えて解読していきたいと思っています。 非常に丁寧なプログラムを載せていただき、ありがとうございました。