implemented EMailSender

This commit is contained in:
schrom01 2022-11-28 08:00:31 +01:00
parent 2d88c9ea91
commit fbf1700c34
10 changed files with 225 additions and 59 deletions

View File

@ -42,6 +42,8 @@ dependencies {
implementation 'com.fasterxml.jackson.datatype:jackson-datatype-jsr310:2.13.4' implementation 'com.fasterxml.jackson.datatype:jackson-datatype-jsr310:2.13.4'
implementation 'com.fasterxml.jackson.datatype:jackson-datatype-jdk8:2.13.4' implementation 'com.fasterxml.jackson.datatype:jackson-datatype-jdk8:2.13.4'
testImplementation 'org.mockito:mockito-core:4.3.+' testImplementation 'org.mockito:mockito-core:4.3.+'
implementation 'com.sun.mail:javax.mail:1.6.2'
} }
test { test {

View File

@ -1,22 +1,23 @@
package ch.zhaw.gartenverwaltung; package ch.zhaw.gartenverwaltung;
import ch.zhaw.gartenverwaltung.bootstrap.AppLoader; import ch.zhaw.gartenverwaltung.bootstrap.AppLoader;
import ch.zhaw.gartenverwaltung.notifier.Notifier; import ch.zhaw.gartenverwaltung.backgroundtasks.BackgroundTasks;
import javafx.application.Application; import javafx.application.Application;
import javafx.stage.Stage; import javafx.stage.Stage;
import java.io.IOException; import java.io.IOException;
import java.util.Timer;
public class HelloApplication extends Application { public class HelloApplication extends Application {
Timer backGroundTaskTimer = new Timer();
BackgroundTasks backgroundTasks;
@Override @Override
public void start(Stage stage) throws IOException { public void start(Stage stage) throws IOException {
AppLoader appLoader = new AppLoader(); AppLoader appLoader = new AppLoader();
Notifier notifier = new Notifier(appLoader.getGardenSchedule()); backgroundTasks = new BackgroundTasks(appLoader.getTaskList(), appLoader.getGarden(), appLoader.getPlantList());
Thread notificationThread = new Thread(notifier); backGroundTaskTimer.scheduleAtFixedRate(backgroundTasks, 0, 1000);
notificationThread.start();
notificationThread.interrupt();
appLoader.loadSceneToStage("MainFXML.fxml", stage); appLoader.loadSceneToStage("MainFXML.fxml", stage);
@ -24,6 +25,11 @@ public class HelloApplication extends Application {
stage.show(); stage.show();
} }
@Override
public void stop(){
backGroundTaskTimer.cancel();
}
public static void main(String[] args) { public static void main(String[] args) {
launch(); launch();
} }

View File

@ -1,13 +1,23 @@
package ch.zhaw.gartenverwaltung; package ch.zhaw.gartenverwaltung;
import ch.zhaw.gartenverwaltung.backgroundtasks.email.SmtpCredentials;
import ch.zhaw.gartenverwaltung.types.HardinessZone; import ch.zhaw.gartenverwaltung.types.HardinessZone;
import javafx.beans.property.BooleanProperty; import javafx.beans.property.BooleanProperty;
import javafx.beans.property.SimpleBooleanProperty; import javafx.beans.property.SimpleBooleanProperty;
import java.util.List;
public class Settings { public class Settings {
private static final Settings instance;
private HardinessZone currentHardinessZone = HardinessZone.ZONE_8A; private HardinessZone currentHardinessZone = HardinessZone.ZONE_8A;
private static Settings instance;
private final BooleanProperty showTutorial = new SimpleBooleanProperty(false); private final BooleanProperty showTutorial = new SimpleBooleanProperty(false);
private SmtpCredentials smtpCredentials = new SmtpCredentials("imap.gmail.com", "587", "pm3.hs22.it21b.win.team1@gmail.com", "pm3.hs22.it21b.win.team1@gmail.com", "bisefhhjtrrhtoqr", true);
// Gmail Address: pm3.hs22.it21b.win.team1@gmail.com
// Gmail Passwort: Gartenverwaltung.PM3.2022
// E-Mail Inbox: https://www.mailinator.com/v4/public/inboxes.jsp?to=pm3.hs22.it21b.win.team1
private String mailNotificationReceivers = "pm3.hs22.it21b.win.team1@mailinator.com";
private String mailNotificationSubjectTemplate = "Task %s is due!"; // {0} = Task Name
private String mailNotificationTextTemplate = "Dear user\nYour gardentask %s is due since %tF. Don't forget to confirm in your application if the task is done.\nTask description:\n%s"; // {0} = Task Name, {1} = nextExecution, {2} = Task description
static { static {
instance = new Settings(); instance = new Settings();
@ -38,4 +48,20 @@ public class Settings {
public boolean getShowTutorial() { public boolean getShowTutorial() {
return this.showTutorial.get(); return this.showTutorial.get();
} }
public SmtpCredentials getSmtpCredentials() {
return smtpCredentials;
}
public String getMailNotificationReceivers() {
return mailNotificationReceivers;
}
public String getMailNotificationSubjectTemplate() {
return mailNotificationSubjectTemplate;
}
public String getMailNotificationTextTemplate() {
return mailNotificationTextTemplate;
}
} }

View File

@ -0,0 +1,42 @@
package ch.zhaw.gartenverwaltung.backgroundtasks;
import ch.zhaw.gartenverwaltung.io.PlantList;
import ch.zhaw.gartenverwaltung.io.TaskList;
import ch.zhaw.gartenverwaltung.models.Garden;
import javax.mail.MessagingException;
import java.io.IOException;
import java.util.TimerTask;
public class BackgroundTasks extends TimerTask {
private final TaskList taskList;
private final Garden garden;
private final PlantList plantList;
private final Notifier notifier;
//TODO uncomment: privat final WeatherGardenTaskPlaner weatherGardenTaskPlaner;
public BackgroundTasks(TaskList taskList, Garden garden, PlantList plantList) {
this.taskList = taskList;
this.garden = garden;
this.plantList = plantList;
notifier = new Notifier(taskList, garden, plantList);
//TODO uncomment: weatherGardenTaskPlaner = new WeatherGardenTaskPlaner(taskList);
}
@Override
public void run() {
// TODO uncomment: weatherGardenTaskPlaner.refreshTasks();
try {
try {
notifier.sendNotifications();
} catch (MessagingException e) {
e.printStackTrace();
// TODO logger
}
} catch (IOException e) {
e.printStackTrace();
// TODO logger
}
}
}

View File

@ -0,0 +1,42 @@
package ch.zhaw.gartenverwaltung.backgroundtasks;
import ch.zhaw.gartenverwaltung.Settings;
import ch.zhaw.gartenverwaltung.backgroundtasks.email.EMailSender;
import ch.zhaw.gartenverwaltung.io.PlantList;
import ch.zhaw.gartenverwaltung.io.TaskList;
import ch.zhaw.gartenverwaltung.models.Garden;
import ch.zhaw.gartenverwaltung.types.Task;
import javax.mail.MessagingException;
import java.io.IOException;
import java.time.LocalDate;
public class Notifier {
private final TaskList taskList;
private final Garden garden;
private final PlantList plantList;
private final EMailSender eMailSender = new EMailSender();
public Notifier(TaskList taskList, Garden garden, PlantList plantList) {
this.taskList = taskList;
this.garden = garden;
this.plantList = plantList;
}
private void sendNotification(Task task) throws MessagingException {
String messageSubject = String.format(Settings.getInstance().getMailNotificationSubjectTemplate(), task.getName());
String messageText = String.format(Settings.getInstance().getMailNotificationTextTemplate(), task.getName(), task.getNextExecution(), task.getDescription());
//TODO create Exception for email sent fail
eMailSender.sendMails(Settings.getInstance().getMailNotificationReceivers(), messageSubject, messageText);
}
public void sendNotifications() throws IOException, MessagingException {
System.out.println("sending Notifications");
for (Task task : taskList.getTaskList(LocalDate.MIN, LocalDate.MAX)) {
if (task.getNextNotification() != null && task.getNextNotification().isBefore(LocalDate.now().minusDays(1))) {
sendNotification(task);
task.setNextNotification(LocalDate.now().plusDays(1));
}
}
}
}

View File

@ -0,0 +1,44 @@
package ch.zhaw.gartenverwaltung.backgroundtasks.email;
import ch.zhaw.gartenverwaltung.Settings;
import javax.mail.Address;
import javax.mail.Message;
import javax.mail.MessagingException;
import javax.mail.Transport;
import javax.mail.internet.InternetAddress;
import javax.mail.internet.MimeMessage;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.Date;
import java.util.List;
public class EMailSender {
public EMailSender(){
}
public void sendMails(String recipients, String subject, String text) throws MessagingException {
// TODO replace printMail with implementation
printMail(recipients, subject, text); // TODO Remove Printing E-Mail to console to test it
MimeMessage message = new MimeMessage(Settings.getInstance().getSmtpCredentials().getSession());
message.addHeader("Content-type", "text/HTML; charset=UTF-8");
message.addHeader("format", "flowed");
message.addHeader("Content-Transfer-Encoding", "8bit");
message.setFrom(new InternetAddress(Settings.getInstance().getSmtpCredentials().fromAddress()));
message.setReplyTo(InternetAddress.parse(Settings.getInstance().getSmtpCredentials().fromAddress(), false));
message.setSubject(subject);
message.setText(text);
message.setSentDate(new Date());
message.setRecipients(Message.RecipientType.TO, InternetAddress.parse(recipients, false));
System.out.println("Message is ready: ");
Transport.send(message);
}
private void printMail(String receiver, String subject, String text){
System.out.printf("\nSending E-Mail:\nTo: %s\nSubject: %s\nMessage:\n%s\n", receiver, subject, text);
}
}

View File

@ -0,0 +1,41 @@
package ch.zhaw.gartenverwaltung.backgroundtasks.email;
import javax.mail.PasswordAuthentication;
import javax.mail.Session;
import java.net.Authenticator;
import java.util.Properties;
public record SmtpCredentials(
String host,
String port,
String fromAddress,
String username,
String password,
boolean startTLS
) {
private Properties getProperties() {
Properties properties = new Properties();
properties.put("mail.smtp.host", host);
properties.put("mail.smtp.port", port);
properties.put("mail.smtp.auth", "true");
properties.put("mail.smtp.starttls.enable", startTLS ? "true" : "false");
return properties;
}
private javax.mail.Authenticator getAuthenticator() {
return new javax.mail.Authenticator() {
@Override
protected PasswordAuthentication getPasswordAuthentication() {
return new PasswordAuthentication(username, password);
}
};
}
public Session getSession() {
return Session.getInstance(getProperties(), getAuthenticator());
}
}

View File

@ -10,7 +10,6 @@ import ch.zhaw.gartenverwaltung.io.TaskList;
import ch.zhaw.gartenverwaltung.models.Garden; import ch.zhaw.gartenverwaltung.models.Garden;
import ch.zhaw.gartenverwaltung.models.GardenSchedule; import ch.zhaw.gartenverwaltung.models.GardenSchedule;
import ch.zhaw.gartenverwaltung.models.PlantListModel; import ch.zhaw.gartenverwaltung.models.PlantListModel;
import ch.zhaw.gartenverwaltung.notifier.Notifier;
import javafx.fxml.FXMLLoader; import javafx.fxml.FXMLLoader;
import javafx.scene.Scene; import javafx.scene.Scene;
import javafx.scene.control.DialogPane; import javafx.scene.control.DialogPane;
@ -157,7 +156,15 @@ public class AppLoader {
}; };
} }
public GardenSchedule getGardenSchedule() { public PlantList getPlantList() {
return gardenSchedule; return plantList;
}
public Garden getGarden() {
return garden;
}
public TaskList getTaskList() {
return taskList;
} }
} }

View File

@ -1,48 +0,0 @@
package ch.zhaw.gartenverwaltung.notifier;
import ch.zhaw.gartenverwaltung.models.GardenSchedule;
import ch.zhaw.gartenverwaltung.types.Task;
import java.io.IOException;
import java.time.LocalDate;
import java.util.function.Consumer;
public class Notifier implements Runnable{
private final GardenSchedule gardenSchedule;
private boolean interrupted = false;
public Notifier(GardenSchedule gardenSchedule) {
this.gardenSchedule = gardenSchedule;
}
private void sendNotification(Task task){
// TODO implement
}
private void sendNotifications(){
System.out.println("sending Notifications");
try {
gardenSchedule.getTaskList().forEach(task -> {
if(task.getNextNotification() != null && task.getNextNotification().isBefore(LocalDate.now().minusDays(1))){
sendNotification(task);
task.setNextNotification(task.getNextExecution());
}
});
} catch (IOException e) {
// TODO Logger
e.printStackTrace();
}
}
@Override
public void run() {
while(!interrupted){
try {
sendNotifications();
Thread.sleep(3000);
} catch (InterruptedException e) {
interrupted = true;
}
}
}
}

View File

@ -5,6 +5,8 @@ module ch.zhaw.gartenverwaltung {
requires com.fasterxml.jackson.datatype.jsr310; requires com.fasterxml.jackson.datatype.jsr310;
requires com.fasterxml.jackson.datatype.jdk8; requires com.fasterxml.jackson.datatype.jdk8;
requires java.logging; requires java.logging;
requires java.mail;
opens ch.zhaw.gartenverwaltung to javafx.fxml; opens ch.zhaw.gartenverwaltung to javafx.fxml;
opens ch.zhaw.gartenverwaltung.types to com.fasterxml.jackson.databind; opens ch.zhaw.gartenverwaltung.types to com.fasterxml.jackson.databind;
@ -13,6 +15,8 @@ module ch.zhaw.gartenverwaltung {
exports ch.zhaw.gartenverwaltung.types; exports ch.zhaw.gartenverwaltung.types;
exports ch.zhaw.gartenverwaltung.models; exports ch.zhaw.gartenverwaltung.models;
exports ch.zhaw.gartenverwaltung.json; exports ch.zhaw.gartenverwaltung.json;
exports ch.zhaw.gartenverwaltung.notifier; exports ch.zhaw.gartenverwaltung.backgroundtasks;
opens ch.zhaw.gartenverwaltung.notifier to javafx.fxml; opens ch.zhaw.gartenverwaltung.backgroundtasks to javafx.fxml;
exports ch.zhaw.gartenverwaltung.backgroundtasks.email;
opens ch.zhaw.gartenverwaltung.backgroundtasks.email to javafx.fxml;
} }