Reputation: 4886
I have a requirement to send multiple mails in parallel. Lets say I have 10 person emails (my actual requirement have around 100's of recipients). For sending mails to all those 10 people, I need to hit multiple services for collecting information based on the emailId and it will take a lot of time. Having said my email trigger service is totally isolated function, and I don't have any constraint in the order of mail triggering.
Firstly I used the normal way like as shown below, but it is triggering in sequential order and taking more time.
public static void main(String[] args) {
List<String> emails = Lists.newArrayList();
emails.add("[email protected]");
emails.add("[email protected]");
emails.add("[email protected]");
emails.add("[email protected]");
emails.add("[email protected]");
emails.add("[email protected]");
emails.add("[email protected]");
emails.add("[email protected]");
:
:
for(String email: emails) {
sendMail(email);
}
}
private static void sendMail(final String email) {
// function will call many other services for getting the information required for sending the email
try {
Thread.sleep(10000);
System.out.println("Sending Mail for:"+email);
} catch (InterruptedException e) {
e.printStackTrace();
}
}
Secondly I heard abt Java8 parallel streams (I am very much new to this), So thought of using it like as shown below. It seems a to trigger the mails a little more faster than the sequential order
public static void main(String[] args) {
List<String> emails = Lists.newArrayList();
emails.add("[email protected]");
emails.add("[email protected]");
emails.add("[email protected]");
emails.add("[email protected]");
emails.add("[email protected]");
emails.add("[email protected]");
emails.add("[email protected]");
emails.add("[email protected]");
:
:
emails.stream().parallel().forEach(email -> {
sendMail(email);
});
}
private static void sendMail(final String email) {
// function will call many other services for getting the information required for sending the email
try {
Thread.sleep(10000);
System.out.println("Sending Mail for:"+email);
} catch (InterruptedException e) {
e.printStackTrace();
}
}
Can anyone tell me whether my approach of using Java8 parallel stream is correct for this approach
Upvotes: 2
Views: 1198
Reputation: 15008
No, it's not. The way you use it will resolve to non-concurrent anyway.
What you want is to have an ExecutorService
which you can pass your mail sending logic to.
ExecutorService mailService = Executors.newFixedThreadPool(threadCount);
for (String email : emails) {
mailService.submit(() -> sendMail(email));
}
EDIT:
Since it came up in the comments: You can just as well send them one by one with pretty much the same construct, but:
ExecutorService mailService = Executors.newSingleThreadExecutor();
This will call sendMail
one by one.
The difference to doing it in a straight loop like emails.forEach(m -> sendMail(m))
is that the sending itself is happening in another thread, meaning the main thread doesn't block on calls to sendMail
and is free to do other things.
Upvotes: 3