1
0

More than 1 year has passed since last update.

【Java初心者】添付ファイル付きのメール処理

Last updated at Posted at 2022-02-19

ビジネスシーンでは電子メール処理は現役

前回の記事 https://qiita.com/sev01/items/6c8ea0c1a82324341fdd ではメールの送信をしましたが、受信したメールを保存し、そこからデータを抽出することは日常業務の中でよく使われます。

マルチパートって色々あります

マルチパートの中に、さらにマルチパートとなっていることがあります。
つまり、入れ子になっていることがあるため、ある種の再起処理が必要になります。

添付ファイルの名前が文字化けする問題に遭遇

JavaMailのMimeUtility.decodeText を利用します。


package mailreceivetest;

import java.io.BufferedOutputStream;
import java.io.FileOutputStream;
import java.io.IOException;
import java.io.InputStream;
import java.io.OutputStream;
import java.util.Properties;
import java.util.StringJoiner;
import javax.mail.BodyPart;
import javax.mail.Folder;
import javax.mail.Message;
import javax.mail.MessagingException;
import javax.mail.NoSuchProviderException;
import javax.mail.Session;
import javax.mail.Store;
import javax.mail.Multipart;
import javax.mail.internet.MimeMultipart;
import javax.mail.internet.MimeUtility;

public class MailRecieveTest {

    /**
     * @param args the command line arguments
     * @throws javax.mail.NoSuchProviderException
     * @throws java.io.IOException
     */
    public static void main(String[] args) throws NoSuchProviderException, MessagingException, IOException {

        String host = "XXXXXXXX.jp";
        int port = 993;
        String user = "<ユーザー名>";
        String password = "<パスワード>";

        String target_folder = "INBOX";
        
        Properties props = System.getProperties();
        Session session = Session.getInstance(props, null);
        session.setDebug(false); // trueにするとサーバーとのやりとりが見られます

        try ( Store store = session.getStore("imaps")) {
            store.connect(host, port, user, password);
            Folder inboxFolder = store.getFolder(target_folder);
            if (inboxFolder.exists()) {
                inboxFolder.open(Folder.READ_ONLY); // Folder.READ_WRITEすると読み書き
                for (Message message : inboxFolder.getMessages()) {
                    String subject = message.getSubject();
                    System.out.println("タイトル:" + MimeUtility.decodeText(subject));
                    Object objContent = message.getContent();
                    if (objContent instanceof Multipart) {
                        System.out.println("親マルチパート");
                        MimeMultipart mmp = (MimeMultipart) message.getContent();
                        int multipartCount = mmp.getCount();
                        System.out.println("パートの数:" + multipartCount);
                        for (int i = 0; i < multipartCount; i++) {
                            System.out.println(saveMultiPart(mmp.getBodyPart(i)));
                        }
                    } else {
                        System.out.println("マルチパートではない");
                    }
                    // message.setFlag(Flags.Flag.DELETED, true); // 消去フラグ
                }
                inboxFolder.close(false); // trueにするとフラグが反映される
            } else {
                System.out.printf("%s というフォルダーはありません。", target_folder);
            }
        }

    }

    /**
     * マルチパートのファイルを保存しテキストパートの内容を出力
     *
     * @param bodyPart
     * @return
     */
    static String saveMultiPart(BodyPart bodyPart) {
        StringJoiner sj = new StringJoiner(System.lineSeparator());
        try {
            String contentType = bodyPart.getContentType();
            System.out.println("ContentType:" + contentType);
            if (bodyPart.isMimeType("text/plain")) {
                sj.add(bodyPart.getContent().toString());
            }
            if (bodyPart.isMimeType("text/html")) {
                System.out.println("HTMLパートです");
            }
            if (bodyPart.isMimeType("multipart/alternative")) {
                System.out.println("多重マルチパート");
                Object objContent = bodyPart.getContent();
                if (objContent instanceof Multipart) {
                    Multipart name = (Multipart) objContent;
                    int multiPartCount = name.getCount();
                    for (int i = 0; i < multiPartCount; i++) {
                        System.out.println("子マルチパート:" + i);
                        sj.add(saveMultiPart(name.getBodyPart(i)));
                    }

                } else {
                    System.err.println("マルチパートが抽出できませんでした");
                }
            }
            String fileName = bodyPart.getFileName();
            if (fileName != null) {
                String jfileName = MimeUtility.decodeText(fileName);
                System.out.println("保存します:" + jfileName);
                try ( InputStream ins = bodyPart.getInputStream();
                        OutputStream outs = new BufferedOutputStream(new FileOutputStream(jfileName))) {
                    int out;
                    while ((out = ins.read()) != -1) {
                        outs.write(out);
                    }
                }
            }
        } catch (IOException | MessagingException ex) {
            System.err.println("ERR:" + ex.getMessage());
        }
        return sj.toString();
    }
}

1
0
2

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
1
0