使用JavaMail发送邮件时判断发送结…

    1、获取邮件发送结果
    网上看大多数例子,都是调用Transport类的sendMessage方法后就收工了。但 sendMessage方法没有返回值的,而且是一个异步的方法(也就是函数调用结束的时候邮件的发送过程并未结束)。我们可以通过 Transport的addTransportListener方法增加邮件发送结果的Listener,Listener 接口有三个方法:
void messageDelivered(TransportEvent arg0);                 // 邮件发送成功
void messageNotDelivered(TransportEvent arg0);           // 邮件发送失败
void messagePartiallyDelivere d(TransportEvent arg0);   // 邮件部分发送成功
    注意,由于 sendMessage是异步方法,我们不能简单的:  addTransportListener ->  sendMessage -> 判断发送是否成功,因为这时候邮件发送的过程可能还没有结束。我们可以通过多线程Future模式来将异步的调用转为阻塞的同步调用,Future相关的代码:
private enum DeliveredState {
        INITIAL, MESSAGE_DELIVERED, MESSAGE_NOT_DELIVERED, MESSAGE_PARTIALLY_DELIVERED,
  }
  private static class DeliveredStateFuture {
        private DeliveredState state = DeliveredState.INITIAL;
        synchronized void waitForReady() throws InterruptedException {
            if (state == DeliveredState.INITIAL) {
                wait();
            }
        }
        synchronized DeliveredState getState() {
            return state;
        }
        synchronized void setState(DeliveredState newState) {
            state = newState;
            notifyAll();
        }
}
    发送邮件的代码:
final DeliveredStateFuture future = new DeliveredStateFuture();
transport.addTransportListener(new TransportListener() {
    public void messageDelivered(TransportEvent arg0) {
        future.setState(DeliveredState.MESSAGE_DELIVERED);
    }
    public void messageNotDelivered(TransportEvent arg0) {
        future.setState(DeliveredState.MESSAGE_NOT_DELIVERED);
    }
    public void messagePartiallyDelivere d(TransportEvent arg0) {
        future.setState(DeliveredState.MESSAGE_PARTIALLY_DELIVERED);
    }
});
transport.connect();
transport.sendMessage(message, message.getRecipients(Message.RecipientType.TO));
future.waitForReady();
    2、设置连接超时和读超时
    使用JavaMail用SMTP发送邮件,可以通过 mail.smtp.connectiontimeout和 mail.smtp.timeout这两个属性分别设置连接超时和读超时。That's all,才怪。因为我这么做可耻地失败了,还是需要等待5分钟才抛出异常。我不生产答案,我是stackoverflow的搬运工: 《Why JavaMail connection timeout is too long》。简单说:那是因为使用的javamail版本太低(开头使用的是1.4),下载最新版(1.5)的javamail jar替换后就可以了。所以如果发现那两个属性设置没有效果,检查一下使用的javamail版本。




  • 1
    点赞
  • 12
    收藏
    觉得还不错? 一键收藏
  • 2
    评论
### 回答1: Java中可以使用JavaMail API来发送邮件。在发送邮件,可以调用Transport类的send()方法来发送邮件。该方法会返回一个void类型,如果没有异常抛出,则表示发送成功。可以在发送邮件用try-catch语句来捕获异常,如果捕获到异常,则表示发送失败。 举个例子: ``` try { Transport.send(message); System.out.println("邮件发送成功"); } catch (MessagingException e) { e.printStackTrace(); System.out.println("邮件发送失败"); } ``` 如果要批量发送邮件,可以在上面的代码中加入循环,每次循环更改邮件收件人地址,然后执行发送邮件的操作。 ### 回答2: 在Java中判断批量发送邮件是否成功,可以通过以下几种方法: 1. 使用JavaMail API的返回值:在JavaMail中,可以通过`Transport.send()`方法来发送邮件。该方法会返回一个`void`类型,如果发送成功,则无异常抛出;如果发送失败,则会抛出`SendFailedException`异常。因此,可以通过捕获该异常来判断批量发送邮件是否成功。 示例代码: ```java try { Transport.send(message); System.out.println("批量发送邮件成功"); } catch (SendFailedException e) { System.out.println("批量发送邮件失败"); e.printStackTrace(); } ``` 2. 验证邮件是否被接收:通过发送邮件后,可以通过检查每个收件人邮箱是否接收到邮件来判断批量发送是否成功。可以使用JavaMail API提供的`getRecipients(Message.RecipientType.TO)`方法获取所有的收件人地址,然后可以调用其他库或API来验证这些收件人地址是否收到了邮件。 示例代码: ```java Transport.send(message); Address[] recipients = message.getRecipients(Message.RecipientType.TO); for (Address recipient : recipients) { // 验证接收方是否接收到邮件 // ... } ``` 需要注意的是,验证接收方是否接收到邮件并非完全可靠,因为有可能邮件被误判为垃圾邮件或被邮件服务器拦截。 3. 监测SMTP服务器日志:在发送邮件过程中,可以通过监测SMTP服务器的日志来判断邮件是否成功发送。具体可以通过配置SMTP服务器,使其将日志输出到某个日志文件中,然后读取该日志文件进行判断。 以上是几种常见的方法,具体选择哪种方法取决于实际需求和系统环境。 ### 回答3: 在Java中判断批量发送邮件是否成功,可以采取以下步骤: 1. 创建一个邮件发送的工具类,可以使用JavaMail库进行邮件发送,该库提供了发送邮件的API。 2. 在工具类中,使用循环或者批量操作来发送多个邮件。可以通过将邮件内容和接收者等信息封装在一个邮件对象中,然后循环发送多个邮件。 3. 在发送邮件的过程中,通过捕获异常来检测是否成功发送邮件。如果在发送邮件出现异常,可以判断发送失败。 4. 可以对每封邮件的发送状态进行统计,通过记录成功发送的数量来判断批量发送是否成功。可以使用计数器变量,每次成功发送一封邮件就将计数器加1。 5. 如果需要更加详细的判断,可以通过邮件服务器的回执机制来确认邮件是否送达成功。在发送邮件,可以设置是否需要回执,如果设置了需要回执,可以通过回执的状态判断是否成功送达。 需要注意的是,邮件发送是否成功不仅仅取决于Java代码本身,还与网络环境、邮件服务器的设置等因素相关。考虑到这些因素,可以通过记录邮件发送成功的数量来初步判断批量发送是否成功,或者根据具体业务需求添加更多的判断逻辑。
评论 2
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值