Retrieving emails from Latest to oldest Java Mail API - java

public class testemail {
Properties properties = null;
private Session session = null;
private Store store = null;
private Folder inbox = null;
private String userName = "xxx#gmail.com"; //
private String password = "xxx";
public testemail() {
}
public void readMails() throws Exception {
properties = new Properties();
properties.setProperty("mail.host", "imap.gmail.com");
properties.setProperty("mail.port", "995");
properties.setProperty("mail.transport.protocol", "imaps");
session = Session.getInstance(properties,
new javax.mail.Authenticator() {
protected PasswordAuthentication getPasswordAuthentication() {
return new PasswordAuthentication(userName, password);
}
});
try {
store = session.getStore("imaps");
store.connect();
inbox = store.getFolder("INBOX");
inbox.open(Folder.READ_ONLY);
Message messages[] = inbox.search(new FlagTerm(
new Flags(Flag.SEEN), false));
System.out.println("Number of mails = " + messages.length);
for ( Message message : messages ) {
Address[] from = message.getFrom();
System.out.println("-------------------------------");
System.out.println("Date : " + message.getSentDate());
System.out.println("From : " + from[0]);
System.out.println("Subject: " + message.getSubject());
System.out.println("Content :");
Object content = message.getContent();
Multipart multiPart = (Multipart) content;
procesMultiPart(multiPart);
System.out.println("--------------------------------");
}
inbox.close(true);
store.close();
}
catch (NoSuchProviderException e)
{
e.printStackTrace();
} catch (MessagingException e) {
e.printStackTrace();
}
}
public void procesMultiPart(Multipart content) throws Exception {
int multiPartCount = content.getCount();
for (int i = 0; i < multiPartCount; i++) {
BodyPart bodyPart = content.getBodyPart(i);
Object o;
o = bodyPart.getContent();
if (o instanceof String) {
System.out.println(o);
} else if (o instanceof Multipart) {
procesMultiPart((Multipart) o);
}
}
}
public static void main(String[] args) throws Exception {
testemail sample = new testemail();
sample.readMails();
}}
In the above code I am able to get emails from oldest to newest on my console from gmail. However I would want it to loop from newest to oldest. Is there any way I could get this achieved. Please Help :)

I don't think there's a parameter or method for this in the JavaMail API. You have to reverse the messages array yourself, e.g. by including the Commons.Lang library:
messages = ArrayUtils.reverse(messages);
or iterating over it in the other direction:
for (int i = messages.length - 1; i >= 0; i--) {
Message message = messages[i];

Related

How to retrieve messages which are not flagged as deleted?

I flag a message to be deleted after a treatment :
...
import javax.mail.*;
...
public void delete(Message message) throws MessagingException {
try {
message.setFlag(Flags.Flag.DELETED, true);
} catch (Exception e) {
e.printStackTrace();
throw e;
}
}
...
Then I want to get messages :
...
import com.sun.mail.pop3.POP3Store;
import java.util.Properties;
...
#Value("${mail.host}")
private String host;
#Value("${mail.storeType}")
private String storeType;
#Value("${mail.port}")
private int port;
#Value("${mail.username}")
private String username;
#Value("${mail.password}")
private String password;
#Value("${mail.auth}")
private boolean auth;
#Value("${mail.ssl.trust}")
private String sss_trust;
private POP3Store emailstore = null;
private boolean start = true;
...
public POP3Store getEmailStore() throws Exception {
Properties properties = new Properties();
properties.setProperty("mail.store.protocol", storeType);
properties.setProperty("mail." + storeType + ".host", host);
properties.setProperty("mail." + storeType + ".port", String.valueOf(port));
properties.setProperty("mail." + storeType + ".auth", String.valueOf(auth));
properties.setProperty("mail." + storeType + ".socketFactory.class", "javax.net.ssl.SSLSocketFactory");
properties.setProperty("mail." + storeType + ".ssl.trust", sss_trust);
try {
Session emailSession = Session.getDefaultInstance(properties);
POP3Store emailStore = (POP3Store) emailSession.getStore(storeType);
return emailStore;
} catch (NoSuchProviderException e) {
e.printStackTrace();
throw e;
}
}
Folder emailFolder = emailstore.getFolder("INBOX");
emailFolder.open(Folder.READ_ONLY);
Message[] messages = emailFolder.getMessages(); // how to get messages that are not flagged as deleted ?
if (messages != null) {
for (Message message : messages) {
try {
mailService.createTicket(message);
mailService.delete(message);
} catch (Exception ex) {
throw ex;
}
}
}
emailFolder.close(true);
As I commented I want to get messages that are not flagged deleted. How to do that ?
Based on Message class, you can do something like this:
for (Message message : messages) {
if (!message.getFlags().contains(Flags.Flag.DELETED)) { // This will hopefully help
try {
mailService.createTicket(message);
mailService.delete(message);
} catch (Exception ex) {
throw ex;
}
}
}

Unable to render outlook invitation on different email service providers

I am sending an outlook invitation using java mail to four different email servers:
web.de
gmx.net
gmail.com
company's private email server (which is configured on outlook)
The invitation is rendered/previewed on gmail only but we need to render/preview it on every platform.
My main class is
public class Email {
// Constants for the ICalendar methods.
public static final String METHOD_CANCEL = "CANCEL";
public static final String METHOD_PUBLISH = "PUBLISH";
public static final String METHOD_REQUEST = "REQUEST";
// Apply this organizer, if no organizer is given.
private static final String DEFAULT_ORGANIZER = "zain#company.com";
// Common ICalendar fields.
private String method;
private Calendar beginDate;
private Calendar endDate;
private String location;
private int uid;
private String description;
private String subject;
private String organizer;
/*
* #param args
*/
public static void main(String[] args) {
try {
Email email = new Email();
email.send();
} catch (Exception e) {
e.printStackTrace();
} finally {
System.exit(0);
}
}
public void send() throws Exception {
try {
String from = "mansoor#company.com";
Properties prop = new Properties();
Address[] receivers = new InternetAddress[] {
new InternetAddress("abc#company.com")
, new InternetAddress("abc#gmail.com")
, new InternetAddress("abc#web.de")
, new InternetAddress("abc#gmx.de")
};
prop.put("mail.transport.protocol", "smtp");
prop.put("mail.smtp.host", "smtp.company.com");
prop.put("mail.smtp.port", "587");
prop.put("mail.smtp.auth", "true");
Authenticator authenticator = new Authenticator() {
protected PasswordAuthentication getPasswordAuthentication() {
return new PasswordAuthentication("smtp#company.com", "password");
}
};
Session session = Session.getDefaultInstance(prop, authenticator);
// Define message
MimeMessage message = new MimeMessage(session);
message.addHeaderLine("method=REQUEST");
message.addHeaderLine("charset=UTF-8");
message.addHeaderLine("component=VEVENT");
message.setFrom(new InternetAddress(from));
message.addRecipients(Message.RecipientType.TO, receivers);
message.setSubject("Outlook Meeting Request Using JavaMail");
this.subject = "Meeting Request Test Subject";
this.description = "PLEASE IGNORE THIS MAIL AS IT IS A TEST.";
this.beginDate = new GregorianCalendar(2018, 07-01, 17, 19, 00);
this.endDate = new GregorianCalendar(2018, 07-01, 17, 19, 45);
this.method = Email.METHOD_REQUEST;
this.location = "Office # 13";
// Create the calendar part
BodyPart calendarPart = new MimeBodyPart();
// Fill the message
calendarPart.setHeader("Content-Class", "urn:content- classes:calendarmessage");
calendarPart.setHeader("Content-ID", "calendar_message");
calendarPart.setHeader("Content-Disposition", "inline;filename=Test_invite1.ics");
calendarPart.setFileName("Test_invite1");
calendarPart.setDataHandler(
new DataHandler(
new ByteArrayDataSource(createMessage(), "text/calendar")));// very important
// Create a Multipart
Multipart multipart = new MimeMultipart();
// Add part one
multipart.addBodyPart(calendarPart);
// Put parts in message
message.setContent(multipart);
// send message
Transport.send(message);
for(Address receiver: receivers){
System.out.println(receiver);
}
} catch (MessagingException me) {
System.out.println("Failed sending email");
me.printStackTrace();
} catch (Exception ex) {
System.out.println("Failed sending email");
ex.printStackTrace();
} finally {
System.out.println("End sending email");
System.exit(0);
}
}
public String createMessage() {
// Create the proper date format string required by the ICalendar spec.
final SimpleDateFormat formatter = new SimpleDateFormat("yyyyMMdd'T'HHmmss");
final String stringBeginDate = formatter.format(beginDate.getTime());
final String stringEndDate = formatter.format(endDate.getTime());
// Encode the description => mark new lines.
final String encodedDescription = description.replaceAll("\r\n", "\\\\n");
// Use the default organizer if none is given.
if (this.organizer == null) {
this.organizer = DEFAULT_ORGANIZER;
}
// Content string as array.
String[] contents = {
"BEGIN:VCALENDAR",
"METHOD:" + this.method,
"BEGIN:VEVENT",
"UID:" + this.uid,
"DTSTART:" + stringBeginDate,
"DTEND:" + stringEndDate,
"LOCATION:" + this.location,
"DESCRIPTION:" + encodedDescription,
"ATTENDEE;RSVP=TRUE:MAILTO:" + this.organizer,
"ORGANIZER:" + this.organizer,
"SUMMARY:" + this.subject,
"END:VEVENT",
"END:VCALENDAR"
};
// Build a well-formatted string from the array.
StringBuilder sb = new StringBuilder();
for (String line : contents) {
if (sb.length() > 0) {
sb.append("\n");
}
sb.append(line);
}
return sb.toString();
}
}
Please add comment if you have any ambiguity before down voting. I have seen so many question on stackoverflow.com but found no proper solution.

AJAX call to Servlet fails to store values in Session object

I have a Java web application in which a page ReceiveMail.jsp shows a progress bar which indicates how many emails have been received. A Refresh button on the page makes an AJAX call to a servlet named EmailRecServlet.java.
Codes for both the files are as follows
ReceiveMail.jsp JavaScript function that gives an AJAX call to the servlet:
<head>
<script type="text/javascript">
var requestObj = false;
if (window.XMLHttpRequest) {
requestObj = new XMLHttpRequest();
} else if (window.ActiveXObject) {
requestObj = new ActiveXObject("Microsoft.XMLHTTP");
}
function getUpdates()
{
if (requestObj) {
requestObj.open("GET", "http://localhost:8084/AyreonDepartmentManager/EmailRecServlet/*");
requestObj.onreadystatechange = function ()
{
if (requestObj.readyState == 4 && requestObj.status == 200) {
document.getElementById("progressbar").value = requestObj.responseText;
if(document.getElementById("progressbar").value == 3) {
window.location.href = "abc.jsp";
}
}
}
requestObj.send(null);
}
}
        
EmailRecServlet.java is the Servlet file :
public class EmailRecServlet extends HttpServlet {
#Override
protected void doGet(HttpServletRequest request, HttpServletResponse response)
throws ServletException {
response.setContentType("text/html;charset=UTF-8");
try (PrintWriter out = response.getWriter()) {
HttpSession session = request.getSession();
ServletContext context = request.getServletContext();
final String user = context.getInitParameter("user");
final String password = context.getInitParameter("pass");
int oldinboxsize = Integer.parseInt(context.getAttribute("Old Inbox Size").toString());
//1) get the session object
Properties properties = new Properties();
properties.put("mail.store.protocol", "imaps");
Session emailSession = Session.getDefaultInstance(properties,
new javax.mail.Authenticator() {
protected PasswordAuthentication getPasswordAuthentication() {
return new PasswordAuthentication(user, password);
}
});
//2) create the POP3 store object and connect with the pop server
Store emailStore = emailSession.getStore("imaps");
emailStore.connect("imap.gmail.com", user, password);
//3) create the folder object and open it
Folder emailFolder = emailStore.getFolder("INBOX");
emailFolder.open(Folder.READ_ONLY);
//4) retrieve the messages from the folder in an array and print it
Message[] messages = emailFolder.getMessages();
int msgindex = 0;
int newinboxsize = messages.length;
if (newinboxsize > oldinboxsize) {
for(int i = 1; i <= (newinboxsize-oldinboxsize); i++) {
msgindex = messages.length-i;
Message message = messages[msgindex];
BodyPart clearTextPart = null;
out.write("Forming Message");
if (message instanceof MimeMessage) {
MimeMessage m = (MimeMessage) message;
Object contentObject = m.getContent();
if (contentObject instanceof Multipart) {
clearTextPart = null;
Multipart content = (Multipart) contentObject;
int count = content.getCount();
for (int j = 0; j < count; j++) {
BodyPart part = content.getBodyPart(j);
if (part.isMimeType("text/plain")) {
clearTextPart = part;
out.println("clearText obtained");
out.println("clearText is : ");
out.println(clearTextPart.getContent().toString());
}
}
session.setAttribute((message.getFrom()[msgindex].toString()), (String) clearTextPart.getContent());
out.println("written into session");
}
}
}
String difference = Integer.toString(newinboxsize - oldinboxsize);
out.write(difference);
}
//5) close the store and folder objects
emailFolder.close(false);
emailStore.close();
}
catch(MessagingException e) { e.printStackTrace(); }
catch(IOException e) { e.printStackTrace(); }
catch(Exception e) { e.printStackTrace(); }
}
}
The error that I am getting is that the AJAX call is working properly, but when the control is inside the servlet it only executes till the line:
out.println(clearTextPart.getContent().toString());
and because of this, my progress bar also stays at 0 and does not progress to reflect the new emails I received.
The response body for that particular request shows blank strings when viewed in Network tab in IE debugger.
What could possibly cause the error? And how do I remove this error? How do I get the email content into my Session object so that I can access it on my JSP page?
Please help me out.
The error got resolved. What worked for me was:
session.setAttribute((message.getFrom()[0].toString()), (String) clearTextPart.getContent());

How to open each email in gmail?

Could you please help with follow?
I need to open each email that I have in my Inbox.
Get a content from it.
public void main() {
driver.get("https://mail.google.com");
// gmail login
driver.findElement(By.id("Email")).sendKeys("email");
driver.findElement(By.id("next")).click();
driver.findElement(By.id("Passwd")).sendKeys("password");
driver.findElement(By.id("signIn")).click();
List<WebElement> unreademeil = driver.findElements(By.xpath("//*[#class='zF']"));
// Mailer name for which i want to check do i have an email in my inbox
String MyMailer = "Команда Gmail";
// real logic starts here
for(int i=0;i<unreademeil.size();i++){
if(unreademeil.get(i).isDisplayed()==true){
if(unreademeil.get(i).getText().equals(MyMailer)){
System.out.println("Yes we have got mail form " + MyMailer);
break;
}else{
System.out.println("No mail form " + MyMailer);
}
}
}
//open a mail from the gmail inbox.
List<WebElement> a = driver.findElements(By.xpath("//*[#class='yW']/span"));
System.out.println(a.size());
for (int i = 0; i < a.size(); i++) {
System.out.println(a.get(i).getText());
if (a.get(i).getText().equals("Я")) //to click on a specific mail.
{
a.get(i).click();
System.out.println(driver.findElement(By.xpath("//*[#id=\":9v\"]/div[1]")).getText());
driver.navigate().back();
}
}
I've tried JavaMail API as well.
But it seems that I do something wrong in their code.
public static void bot() throws Exception {
Properties props = System.getProperties();
props.setProperty("mail.store.protocol", "imaps");
Session session = Session.getDefaultInstance(props, null);
Store store = session.getStore("imaps");
store.connect("imap.gmail.com", "#gmail.com",
"password");
Folder folder = store.getFolder("INBOX");
folder.open(Folder.READ_WRITE);
System.out.println("Total Message:" + folder.getMessageCount());
System.out.println("Unread Message:"
+ folder.getUnreadMessageCount());
Message[] messages = null;
boolean isMailFound = false;
Message mailFromGod= null;
//Search for mail from God
for (int i = 0; i < 5; i++) {
messages = folder.search(new SubjectTerm("t");
folder.getMessages());
//Wait for 10 seconds
if (messages.length == 0) {
Thread.sleep(10000);
}
}
for (Message mail : messages) {
if (!mail.isSet(Flags.Flag.SEEN)) {
mailFromGod = mail;
System.out.println("Message Count is: "
+ mailFromGod.getMessageNumber());
isMailFound = true;
}
}
String line;
StringBuffer buffer = new StringBuffer();
BufferedReader reader = new BufferedReader(
new InputStreamReader(mailFromGod
.getInputStream()));
while ((line = reader.readLine()) != null) {
buffer.append(line);
System.out.println(buffer);
String registrationURL = buffer.toString().split("http://www./?")[0]
.split("href=")[1];
System.out.println(registrationURL);
}
}
}
and try this
package Bots;
import javax.mail.*;
import java.util.Properties;
public class checkemail {
public static void check(String host, String storeType, String user,
String password)
{
try {
//create properties field
Properties properties = new Properties();
properties.put("mail.pop3.host", host);
properties.put("mail.pop3.port", "995");
properties.put("mail.pop3.starttls.enable", "true");
Session emailSession = Session.getDefaultInstance(properties);
//create the POP3 store object and connect with the pop server
Store store = emailSession.getStore("pop3s");
store.connect(host, user, password);
//create the folder object and open it
Folder emailFolder = store.getFolder("INBOX");
emailFolder.open(Folder.READ_ONLY);
// retrieve the messages from the folder in an array and print it
Message[] messages = emailFolder.getMessages();
System.out.println("messages.length---" + messages.length);
for (int i = 0, n = messages.length; i < n; i++) {
Message message = messages[i];
System.out.println("---------------------------------");
System.out.println("Email Number " + (i + 1));
System.out.println("Subject: " + message.getSubject());
System.out.println("From: " + message.getFrom()[0]);
System.out.println("Text: " + message.getContent().toString());
//System.out.println("Message" + message.getDescription().toString());
}
//close the store and folder objects
emailFolder.close(false);
store.close();
} catch (NoSuchProviderException e) {
e.printStackTrace();
} catch (MessagingException e) {
e.printStackTrace();
} catch (Exception e) {
e.printStackTrace();
}
}
public static void main(String[] args) {
String host = "pop.gmail.com";// change accordingly
String mailStoreType = "pop3";
String username = "test#gmail.com";// change accordingly
String password = "test";// change accoredingly
check(host, mailStoreType, username, password);
}
}
Result:
...
Email Number 7
Subject: test
From: Google
Text: javax.mail.internet.MimeMultipart#612fc6eb
Email Number 8
Subject: test
From: Google
Text: javax.mail.internet.MimeMultipart#1060b431
but how to get normal text from the message
message.getContent().toString()
Above code works for plain text for multipart messages please include below piece of code in you for loop.
Multipart multipart = (Multipart) message.getContent();
for (int j = 0; j < multipart.getCount(); j++) {
BodyPart bodyPart = multipart.getBodyPart(j);
System.out.println("Body: "+bodyPart.getContent());
content= bodyPart.getContent().toString();
System.out.println(content);
}
Lets update if your issue resolves by this.
I've modified code a bit. Everything seems to be working as expected.
import org.openqa.selenium.Alert;
import org.openqa.selenium.By;
import org.openqa.selenium.WebDriver;
import org.openqa.selenium.WebElement;
import org.openqa.selenium.chrome.ChromeDriver;
import org.testng.annotations.AfterMethod;
import org.testng.annotations.BeforeMethod;
import org.testng.annotations.Test;
import java.util.ArrayList;
import java.util.List;
import java.util.concurrent.TimeUnit;
public class email {
private WebDriver driver;
#BeforeMethod
public void beforeMethod() {
String exePath = "chromedriver_win32\\chromedriver.exe";
System.setProperty("webdriver.chrome.driver", exePath);
driver = new ChromeDriver();
driver.manage().timeouts().implicitlyWait(10, TimeUnit.SECONDS);
driver.manage().window().maximize();
driver.get("https://google.com/");
}
#AfterMethod
public void afterMethod() {
driver.quit();
}
#Test
public void main() throws InterruptedException {
String email = "email";
String password = "password";
driver.get("https://mail.google.com");
driver.findElement(By.id("Email")).sendKeys(email);
driver.findElement(By.id("next")).click();
driver.findElement(By.id("Passwd")).sendKeys(password);
driver.findElement(By.id("signIn")).click();
// now talking un-read email form inbox into a list
List<WebElement> unreademeil = driver.findElements(By.xpath("//*[#class='zF']"));
// Mailer name for which i want to check do i have an email in my inbox
String MyMailer = "FROMTESTEMAIL";
String bodyemail = "";
int i = 0;
for (i = 0; i < unreademeil.size(); i++) {
if (unreademeil.get(i).isDisplayed() == true) {
unreademeil.get(i).click();
System.out.println(bodyemail);
driver.findElement(By.xpath("//a[contains(text(),'Click here')]")).click();
Thread.sleep(5000);
System.out.println("Your current page is: " + driver.getTitle());
ArrayList<String> tabs2 = new ArrayList<String>(driver.getWindowHandles());
driver.switchTo().window(tabs2.get(0));
driver.close();
driver.switchTo().window(tabs2.get(1));
System.out.println("Your current page is: " + driver.getTitle());
driver.findElement(By.xpath("/html/body/div/div[5]/div[2]/div[1]/a")).click();
System.out.println("It is started");
Thread.sleep(3000);
// do something after clicking on the required link
// ...
try {
Alert confirmationAlert = driver.switchTo().alert();
String alertText = confirmationAlert.getText();
System.out.println("Alert text is " + alertText);
confirmationAlert.accept();
} catch (Exception e) {
System.out.println("The alerts haven't been found");
e.printStackTrace();
}
driver.get("https://mail.google.com");
Thread.sleep(5000);
i--;
unreademeil = driver.findElements(By.xpath("//*[#class='zF']"));
}
}
}
}

JavaMail : Folder.hasNewMessages() and .getMessageCount() don't seem to work properly

I have this simple code to perdiodically access a pop3 server and check if there are new messages in the inbox folder
public static void main(String[] args) {
try {
String storeType = "pop3";
String host = "...";
int port = ...;
String user = "...";
String psw = "...";
//
int delay = 1;
long mins = 200 * 60 * delay;
firstAccess = true;
Properties properties = new Properties();
properties.put("mail.pop3.host", host);
properties.put("mail.pop3.user", user);
properties.put("mail.pop3.socketFactory.class", "javax.net.ssl.SSLSocketFactory");
properties.put("mail.pop3.port", port);
RomasAuthenticator r = new RomasAuthenticator(user, psw);
Session session = Session.getDefaultInstance(properties, r);
POP3Store emailStore = (POP3Store) session.getStore(storeType);
emailStore.connect(host, port, user, psw);
Folder emailFolder = emailStore.getFolder("INBOX");
emailFolder.open(Folder.READ_ONLY);
while (true) {
if (checkInbox(emailFolder)) {
//prepara la notifica per il voice_service
System.out.println("mes!");
}
firstAccess = false;
Thread.sleep(mins);
}
} catch (Exception ex) {
//return null;
}
}
private static boolean checkInbox(Folder inbox_folder) throws MessagingException, IOException {
System.out.println("checking");
boolean res = false;
try {
int email_actual_count = inbox_folder.getMessageCount();
if (email_actual_count > email_prev_count /*or hasNewMessages()*/) {
if (!firstAccess) {
res = true;
}
}
//bisogna aggiornare comunque email_count in caso siano stati cancellati messaggi
email_prev_count = email_actual_count;
}
catch (Exception e) {
e.printStackTrace();
}
return res;
}
Both getMessageCount() and hasNewMessages() do not work, because the first always returns the same number of messages, and the second always returns false. What's that I'm doing wrong?
I don't want to use a messagelistener because this code will run on a robot with really low performances..
thanks everyone
The JavaMail FAQ explains why these features don't work with the POP3 protocol.

Categories

Resources