Tôi đang cố tạo một ứng dụng email đơn giản bằng cách sử dụng API Java Mail Android (https://code.google.com/p/javamail-android/) sẽ gửi thư kèm theo tệp đính kèm. Nhưng cách tiếp cận của tôi không hiệu quả. Nó gửi thành công văn bản email nhưng không thêm phần đính kèm vào email. Tôi đã thêm một nút hình ảnh để chọn tệp cho tệp đính kèm. Tôi đang sử dụng Intent để chọn một tệp. Cũng đã thêm một nút khác để gửi email.Ứng dụng Android để gửi Email có tệp đính kèm bằng cách sử dụng API Java Mail
Lúc đầu bằng cách nhấp vào nút hình ảnh Tôi đang cố gắng chọn tệp và nhận đường dẫn tệp cho tệp đính kèm. Sau đó, tôi đang thiết lập đường dẫn tệp đến phương thức sendmail để gửi thư có tệp đính kèm này.
những gì tôi đang làm là đưa ra dưới đây:
Email.java
package com.android.imran.emailapp003;
import java.util.Date;
import java.util.List;
import java.util.Properties;
import javax.activation.CommandMap;
import javax.activation.DataHandler;
import javax.activation.DataSource;
import javax.activation.FileDataSource;
import javax.activation.MailcapCommandMap;
import javax.mail.BodyPart;
import javax.mail.Multipart;
import javax.mail.PasswordAuthentication;
import javax.mail.Session;
import javax.mail.Transport;
import javax.mail.internet.InternetAddress;
import javax.mail.internet.MimeBodyPart;
import javax.mail.internet.MimeMessage;
import javax.mail.internet.MimeMultipart;
public class Email extends javax.mail.Authenticator {
private String _user;
private String _pass;
private List<String> _to;
private String _from;
private String _port;
private String _sport;
private String _host;
private String _subject;
private String _body;
private boolean _auth;
private boolean _debuggable;
private Multipart _multipart;
public Email() {
_host = "smtp.gmail.com"; // default smtp server
_port = "465"; // default smtp port
_sport = "465"; // default socketfactory port
_user = ""; // username
_pass = ""; // password
_from = ""; // email sent from
_subject = ""; // email subject
_body = ""; // email body
_debuggable = false; // debug mode on or off - default off
_auth = true; // smtp authentication - default on
_multipart = new MimeMultipart();
// There is something wrong with MailCap, javamail can not find a handler for the multipart/mixed part, so this bit needs to be added.
MailcapCommandMap mc = (MailcapCommandMap) CommandMap.getDefaultCommandMap();
mc.addMailcap("text/html;; x-java-content-handler=com.sun.mail.handlers.text_html");
mc.addMailcap("text/xml;; x-java-content-handler=com.sun.mail.handlers.text_xml");
mc.addMailcap("text/plain;; x-java-content-handler=com.sun.mail.handlers.text_plain");
mc.addMailcap("multipart/*;; x-java-content-handler=com.sun.mail.handlers.multipart_mixed");
mc.addMailcap("message/rfc822;; x-java-content-handler=com.sun.mail.handlers.message_rfc822");
CommandMap.setDefaultCommandMap(mc);
}
public Email(String user, String pass) {
this();
_user = user;
_pass = pass;
}
public boolean send() throws Exception {
Properties props = _setProperties();
if(!_user.equals("") && !_pass.equals("") && _to.size() > 0 && !_from.equals("") && !_subject.equals("") && !_body.equals("")) {
Session session = Session.getInstance(props, this);
MimeMessage msg = new MimeMessage(session);
msg.setFrom(new InternetAddress(_from));
InternetAddress[] addressTo = new InternetAddress[_to.size()];
for (int i = 0; i < _to.size(); i++) {
addressTo[i] = new InternetAddress(_to.get(i));
}
msg.setRecipients(MimeMessage.RecipientType.TO, addressTo);
msg.setSubject(_subject);
msg.setSentDate(new Date());
// setup message body
BodyPart messageBodyPart = new MimeBodyPart();
messageBodyPart.setText(_body);
_multipart.addBodyPart(messageBodyPart);
// Put parts in message
msg.setContent(_multipart);
// send email
Transport.send(msg);
return true;
} else {
return false;
}
}
public void addAttachment(String filename) throws Exception {
BodyPart messageBodyPart = new MimeBodyPart();
DataSource source = new FileDataSource(filename);
messageBodyPart.setDataHandler(new DataHandler(source));
messageBodyPart.setFileName(filename);
_multipart.addBodyPart(messageBodyPart);
}
@Override
public PasswordAuthentication getPasswordAuthentication() {
return new PasswordAuthentication(_user, _pass);
}
private Properties _setProperties() {
Properties props = new Properties();
props.put("mail.smtp.host", _host);
if(_debuggable) {
props.put("mail.debug", "true");
}
if(_auth) {
props.put("mail.smtp.auth", "true");
}
props.put("mail.smtp.port", _port);
props.put("mail.smtp.socketFactory.port", _sport);
props.put("mail.smtp.socketFactory.class", "javax.net.ssl.SSLSocketFactory");
props.put("mail.smtp.socketFactory.fallback", "false");
return props;
}
// the getters and setters
public String getBody() {
return _body;
}
public void setBody(String body) {
this._body = body;
}
public List<String> getTo(){
return _to;
}
public void setTo(List<String> toArr) {
this._to = toArr;
}
public String getFrom(){
return _from;
}
public void setFrom(String from){
this._from = from;
}
public String getSubject(){
return _subject;
}
public void setSubject(String string) {
this._subject = string;
}
}
ProcessEmail.java
package com.android.imran.emailapp003;
import android.app.Activity;
import android.app.ProgressDialog;
import android.os.AsyncTask;
import android.util.Log;
import java.util.List;
public class ProcessEmail extends AsyncTask {
private ProgressDialog statusDialog;
private Activity sendMailActivity;
public ProcessEmail(Activity activity) {
sendMailActivity = activity;
}
protected void onPreExecute() {
statusDialog = new ProgressDialog(sendMailActivity);
statusDialog.setMessage("Getting ready...");
statusDialog.setIndeterminate(false);
statusDialog.setCancelable(false);
statusDialog.show();
}
@Override
protected Object doInBackground(Object... args) {
try {
Log.i("SendMailTask", "About to instantiate GMail...");
publishProgress("Processing input....");
Email sendMail = new Email(args[0].toString(), args[1].toString());
publishProgress("Preparing mail message....");
sendMail.setFrom(args[0].toString());
sendMail.setTo((List<String>) args[2]);
sendMail.setSubject(args[3].toString());
sendMail.setBody(args[4].toString());
sendMail.addAttachment(args[5].toString());
publishProgress("Sending email....");
sendMail.send();
publishProgress("Email Sent.");
Log.i("SendMailTask", "Mail Sent.");
} catch (Exception e) {
publishProgress(e.getMessage());
Log.e("SendMailTask", e.getMessage(), e);
}
return null;
}
@Override
public void onProgressUpdate(Object... values) {
statusDialog.setMessage(values[0].toString());
}
@Override
public void onPostExecute(Object result) {
statusDialog.dismiss();
}
}
MainActivity.java
package com.android.imran.emailapp003;
import android.content.Intent;
import android.support.v7.app.AppCompatActivity;
import android.os.Bundle;
import android.util.Log;
import android.view.View;
import android.widget.Button;
import android.widget.ImageButton;
import android.widget.TextView;
import android.widget.Toast;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.List;
public class MainActivity extends AppCompatActivity {
private static int FILE_SELECT_CODE;
private static int SELECT_PICTURE;
String FilePath;
@Override
public void onCreate(Bundle icicle) {
super.onCreate(icicle);
setContentView(R.layout.activity_main);
Button addImage = (Button) findViewById(R.id.send_email);
addImage.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
String fromEmail = "*******@gmail.com";
String fromPassword = "*****";
List<String> toEmails = new ArrayList();
toEmails.add("*******@gmail.com");
toEmails.add("*******@live.com");
String emailSubject = "This is an email sent using my Mail JavaMail wrapper from an Android device.";
String emailBody= "Email body.";
new ProcessEmail(MainActivity.this).execute(
fromEmail, fromPassword, toEmails, emailSubject, emailBody, FilePath);
}
});
ImageButton selectFile= (ImageButton) findViewById(R.id.selectFile);
selectFile.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
Intent intent = new Intent(Intent.ACTION_GET_CONTENT);
intent.setType("*/*");
startActivityForResult(intent, FILE_SELECT_CODE);
}
});
}
@Override
public void onActivityResult(int requestCode, int resultCode, Intent data) {
if ((requestCode == FILE_SELECT_CODE) && (resultCode == -1)) {
FilePath = data.getData().getPath();
//Toast.makeText(this, FilePath, Toast.LENGTH_SHORT).show();
}
}
}
Vui lòng giúp tôi khắc phục sự cố.
Cập nhật: Trình giả lập Genymotion tôi đã chọn tệp. Ứng dụng của tôi hiển thị đường dẫn tệp dưới dạng /bên ngoài/hình ảnh/hình ảnh/14 trong thông báo bánh mì nướng.
Sau đó, khi tôi nhấp vào nút gửi để gửi email. Tôi gặp lỗi sau:
11-17 04:47:46.887 25788-26024/com.android.imran.emailapp003 E/SendMailTask﹕ IOException while sending message
javax.mail.MessagingException: IOException while sending message;
nested exception is:
java.io.FileNotFoundException: /external/images/media/14: open failed: ENOENT (No such file or directory)
at com.sun.mail.smtp.SMTPTransport.sendMessage(SMTPTransport.java:676)
at javax.mail.Transport.send0(Transport.java:189)
at javax.mail.Transport.send(Transport.java:118)
at com.android.imran.emailapp003.Email.send(Email.java:105)
at com.android.imran.emailapp003.ProcessEmail.doInBackground(ProcessEmail.java:42)
at android.os.AsyncTask$2.call(AsyncTask.java:287)
at java.util.concurrent.FutureTask.run(FutureTask.java:234)
at android.os.AsyncTask$SerialExecutor$1.run(AsyncTask.java:230)
at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1080)
at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:573)
at java.lang.Thread.run(Thread.java:841)
Caused by: java.io.FileNotFoundException: /external/images/media/14: open failed: ENOENT (No such file or directory)
at libcore.io.IoBridge.open(IoBridge.java:409)
at java.io.FileInputStream.<init>(FileInputStream.java:78)
at javax.activation.FileDataSource.getInputStream(FileDataSource.java:110)
at javax.activation.DataHandler.writeTo(DataHandler.java:318)
at javax.mail.internet.MimeBodyPart.writeTo(MimeBodyPart.java:1403)
at javax.mail.internet.MimeBodyPart.writeTo(MimeBodyPart.java:874)
at javax.mail.internet.MimeMultipart.writeTo(MimeMultipart.java:444)
at com.sun.mail.handlers.multipart_mixed.writeTo(multipart_mixed.java:102)
at javax.activation.ObjectDataContentHandler.writeTo(DataHandler.java:897)
at javax.activation.DataHandler.writeTo(DataHandler.java:330)
at javax.mail.internet.MimeBodyPart.writeTo(MimeBodyPart.java:1403)
at javax.mail.internet.MimeMessage.writeTo(MimeMessage.java:1745)
at com.sun.mail.smtp.SMTPTransport.sendMessage(SMTPTransport.java:636)
at javax.mail.Transport.send0(Transport.java:189)
at javax.mail.Transport.send(Transport.java:118)
at com.android.imran.emailapp003.Email.send(Email.java:105)
at com.android.imran.emailapp003.ProcessEmail.doInBackground(ProcessEmail.java:42)
at android.os.AsyncTask$2.call(AsyncTask.java:287)
at java.util.concurrent.FutureTask.run(FutureTask.java:234)
at android.os.AsyncTask$SerialExecutor$1.run(AsyncTask.java:230)
at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1080)
at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:573)
at java.lang.Thread.run(Thread.java:841)
Caused by: libcore.io.ErrnoException: open failed: ENOENT (No such file or directory)
at libcore.io.Posix.open(Native Method)
at libcore.io.BlockGuardOs.open(BlockGuardOs.java:110)
at libcore.io.IoBridge.open(IoBridge.java:393)
at java.io.FileInputStream.<init>(FileInputStream.java:78)
at javax.activation.FileDataSource.getInputStream(FileDataSource.java:110)
at javax.activation.DataHandler.writeTo(DataHandler.java:318)
at javax.mail.internet.MimeBodyPart.writeTo(MimeBodyPart.java:1403)
at javax.mail.internet.MimeBodyPart.writeTo(MimeBodyPart.java:874)
at javax.mail.internet.MimeMultipart.writeTo(MimeMultipart.java:444)
at com.sun.mail.handlers.multipart_mixed.writeTo(multipart_mixed.java:102)
at javax.activation.ObjectDataContentHandler.writeTo(DataHandler.java:897)
at javax.activation.DataHandler.writeTo(DataHandler.java:330)
at javax.mail.internet.MimeBodyPart.writeTo(MimeBodyPart.java:1403)
at javax.mail.internet.MimeMessage.writeTo(MimeMessage.java:1745)
at com.sun.mail.smtp.SMTPTransport.sendMessage(SMTPTransport.java:636)
at javax.mail.Transport.send0(Transport.java:189)
at javax.mail.Transport.send(Transport.java:118)
at com.android.imran.emailapp003.Email.send(Email.java:105)
at com.android.imran.emailapp003.ProcessEmail.doInBackground(ProcessEmail.java:42)
at android.os.AsyncTask$2.call(AsyncTask.java:287)
at java.util.concurrent.FutureTask.run(FutureTask.java:234)
at android.os.AsyncTask$SerialExecutor$1.run(AsyncTask.java:230)
at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1080)
at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:573)
at java.lang.Thread.run(Thread.java:841)
11-17 04:48:58.359 25788-25788/com.android.imran.emailapp003 W/EGL_genymotion﹕ eglSurfaceAttrib not implemented
Tôi đã chạy ứng dụng này vào thiết bị Android của mình. Tôi đã chọn tệp và ứng dụng của tôi hiển thị đường dẫn tệp là /tài liệu/hình ảnh: 52721 trong thông báo bánh mì nướng. Nhưng đường dẫn thực tế của tệp là "/ Bộ nhớ trong/DCIM/Camera/01.jpg"
Tôi nghĩ rằng ứng dụng của tôi không nhận được đường dẫn thực sự cho tệp đính kèm. Làm cách nào để có được đường dẫn thực tế cho tệp đính kèm?
Cũng u có thể thử điều này: [link] (http://www.tutorialspoint.com/javamail_api/javamail_api_send_email_with_attachment.htm) –
Cám ơn nhận xét của bạn. Trên thực tế trong Android Studio của tôi, tôi đã chạy mã mà không bình luận dòng sendMail.addAttachment (args [5] .toString()); Nhưng nó vẫn không hoạt động. –
Tôi nghĩ rằng nó không thể nhận ra vị trí tệp của tôi. :( –