Android - 使用JavaMail和OAuth2发送电子邮件

4

我正在开发一个基本的电子邮件发送应用程序,仅向Gmail发送电子邮件。经过一段时间的研究,我弄清楚了Google现在要求使用GoogleAuthUtil API中的getToken()方法进行身份验证的OAuth2的完整方案。

我在网上搜索了JavaMail代码,以便使用从API检索的令牌发送电子邮件,我找到了以下代码,现在正在使用:

package com.provider;

import java.io.ByteArrayInputStream;
import java.io.IOException;
import java.io.InputStream;
import java.io.OutputStream;
import java.security.Provider;
import java.security.Security;
import java.util.Properties;

import javax.activation.DataHandler;
import javax.activation.DataSource;
import javax.mail.Session;
import javax.mail.Transport;
import javax.mail.URLName;
import javax.mail.Message;
import javax.mail.internet.InternetAddress;
import javax.mail.internet.MimeMessage;
import javax.mail.util.ByteArrayDataSource;

import android.util.Log;

import com.sun.mail.smtp.SMTPTransport;
import com.sun.mail.util.BASE64EncoderStream;

public class GMailOauthSender {
private Session session;

private String mailhost = "smtp.gmail.com";   
private int port = 587;
private String user;   
private String password;   



public SMTPTransport connectToSmtp(String host, int port, String userEmail,
        String oauthToken, boolean debug) throws Exception {

    Properties props = new Properties();
    props.put("mail.smtp.starttls.enable", "true");
    props.put("mail.smtp.starttls.required", "true");
    props.put("mail.smtp.sasl.enable", "true");
    props.put("mail.smtp.auth", "true");
    props.put("mail.imap.auth.login.disable", "true");
    props.put("mail.imap.auth.plain.disable", "true");
    session = Session.getInstance(props);
    session.setDebug(debug);


    final URLName unusedUrlName = null;
    SMTPTransport transport = new SMTPTransport(session, unusedUrlName);
    // If the password is non-null, SMTP tries to do AUTH LOGIN.
    final String emptyPassword = null;
    transport.connect(host, port, userEmail, emptyPassword);

            byte[] response = String.format("user=%s\1auth=Bearer %s\1\1", userEmail,
            oauthToken).getBytes();
    response = BASE64EncoderStream.encode(response);

    transport.issueCommand("AUTH XOAUTH2 " + new String(response),
            235);

    return transport;
}

public synchronized void sendMail(String subject, String body, String user,
        String oauthToken, String recipients) {
    try {

        SMTPTransport smtpTransport = connectToSmtp("smtp.gmail.com",
                587,
                user,
                oauthToken,
                true);

        MimeMessage message = new MimeMessage(session);
        DataHandler handler = new DataHandler(new ByteArrayDataSource(body.getBytes(), "text/plain"));   
                message.setSender(new InternetAddress(user));   
                message.setSubject(subject);   
                message.setDataHandler(handler);   
        if (recipients.indexOf(',') > 0)   
            message.setRecipients(Message.RecipientType.TO, InternetAddress.parse(recipients));   
        else  
            message.setRecipient(Message.RecipientType.TO, new InternetAddress(recipients));   
        smtpTransport.sendMessage(message, message.getAllRecipients());   


    } catch (Exception e) {
        //Log.d("test", e.getMessage());
    }

}

很不幸,这段代码根本就不起作用。我已经卡在这里三个多星期了,但是还没有任何进展。有什么建议吗?

1个回答

4

第一次进行此操作时,我真的很痛苦,要使其正常工作..请按照以下步骤进行

首先,您需要在开发人员控制台中为应用程序设置OAuth2,请参阅此链接以获取详细信息

现在,您需要添加这4个文件,它们将帮助在后台发送邮件。当用户打开应用程序时,用户将看到一个同意屏幕(文件AUthActivity.java中的代码),并且必须允许应用程序使用Gmail,这是一次性活动,以后不再需要。当用户执行此操作时,用户正在请求从Google服务器获得令牌,并将保存在首选项中,以便以后不再询问用户(AuthPreferences.java)。经过用户批准后,您可以使用以下方式发送邮件:

GMailSender gMailSender = new GMailSender();
gMailSender.sendMail("hi", "hi", authPreferences.getUser(), authPreferences.getToken(), "somemailid@gmail.com");

在Github上的文件链接: https://gist.github.com/ranjithnair02/1c6dab7dec51971abfec

您还需要将以下jar文件添加到您的项目中:

http://javamail-android.googlecode.com/files/mail.jar

http://javamail-android.googlecode.com/files/activation.jar

http://javamail-android.googlecode.com/files/additionnal.jar

您还需要在Androidmanifest.xml中添加以下内容:

<uses-permission android:name="android.permission.GET_ACCOUNTS" />
<uses-permission android:name="android.permission.INTERNET" />
<uses-permission android:name="android.permission.USE_CREDENTIALS" />
<uses-permission android:name="android.permission.INTERNET" />
<uses-permission android:name="android.permission.ACCESS_NETWORK_STATE" />

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接