11package io .digiservices .notificationservice .service .impl ;
22
3+ import com .sendgrid .*;
4+ import com .sendgrid .helpers .mail .Mail ;
5+ import com .sendgrid .helpers .mail .objects .Content ;
6+ import com .sendgrid .helpers .mail .objects .Email ;
37import io .digiservices .notificationservice .exception .ApiException ;
48import io .digiservices .notificationservice .service .EmailService ;
5- import jakarta .mail .internet .MimeMessage ;
69import lombok .RequiredArgsConstructor ;
710import lombok .extern .slf4j .Slf4j ;
811import org .springframework .beans .factory .annotation .Value ;
9- import org .springframework .mail .javamail .JavaMailSender ;
10- import org .springframework .mail .javamail .MimeMessageHelper ;
1112import org .springframework .scheduling .annotation .Async ;
1213import org .springframework .stereotype .Service ;
1314import org .thymeleaf .TemplateEngine ;
1415import org .thymeleaf .context .Context ;
1516
17+ import java .io .IOException ;
1618import java .util .Map ;
1719
1820import static io .digiservices .notificationservice .utils .EmailUtils .getResetPasswordUrl ;
2426public class EmailServiceImpl implements EmailService {
2527
2628 public static final String NEW_USER_ACCOUNT_VERIFICATION = "New Account Verification" ;
27- public static final String UTF_8_ENCODING = "UTF-8" ;
2829 public static final String ACCOUNT_VERIFICATION_TEMPLATE = "newaccount" ;
2930 public static final String PASSWORD_RESET_TEMPLATE = "resetpassword" ;
31+ public static final String PASSWORD_RESET_REQUEST = "Reset Password Request" ;
3032 public static final String NEW_TICKET_TEMPLATE = "newticket" ;
3133 public static final String NEW_COMMENT_TEMPLATE = "newcomment" ;
3234 public static final String NEW_FILE_TEMPLATE = "newfile" ;
3335 public static final String NEW_TICKET_REQUEST = "New Support Ticket" ;
34- public static final String PASSWORD_RESET_REQUEST = "Password Reset Request" ;
35- private final JavaMailSender emailSender ;
36+
3637 private final TemplateEngine templateEngine ;
38+
39+ @ Value ("${spring.sendgrid.api.key}" )
40+ private String sendGridApiKey ;
41+
42+ @ Value ("${spring.sendgrid.from.email}" )
43+ private String fromEmail ;
44+
45+ @ Value ("${spring.sendgrid.from.name}" )
46+ private String fromName ;
47+
3748 @ Value ("${verify.email.host}" )
3849 private String host ;
39- @ Value ("${spring.mail.username}" )
40- private String fromEmail ;
4150
4251 @ Override
4352 @ Async
@@ -48,55 +57,74 @@ public void sendNewAccountHtmlEmail(String name, String to, String token) {
4857 "name" , name ,
4958 "url" , getVerificationUrl (host , token )
5059 ));
51- var text = templateEngine .process (ACCOUNT_VERIFICATION_TEMPLATE , context );
52- MimeMessage message = getMimeMessage ();
53- MimeMessageHelper helper = new MimeMessageHelper (message , true , UTF_8_ENCODING );
54- helper .setPriority (1 );
55- helper .setSubject (NEW_USER_ACCOUNT_VERIFICATION );
56- helper .setFrom (fromEmail );
57- helper .setTo (to );
58- helper .setText (text , true );
59- emailSender .send (message );
60+ var htmlContent = templateEngine .process (ACCOUNT_VERIFICATION_TEMPLATE , context );
61+
62+ sendEmail (to , NEW_USER_ACCOUNT_VERIFICATION , htmlContent );
63+ log .info ("Account verification email sent to: {}" , to );
6064 } catch (Exception exception ) {
61- log .error (exception .getMessage (), exception );
65+ log .error ("Error sending account verification email: {}" , exception .getMessage (), exception );
6266 throw new ApiException ("Unable to send email" );
6367 }
6468 }
6569
6670 @ Override
71+ @ Async
6772 public void sendPasswordResetHtmlEmail (String name , String to , String token ) {
6873 try {
6974 var context = new Context ();
7075 context .setVariables (Map .of (
7176 "name" , name ,
7277 "url" , getResetPasswordUrl (host , token )
7378 ));
74- var text = templateEngine .process (PASSWORD_RESET_TEMPLATE , context );
75- MimeMessage message = getMimeMessage ();
76- MimeMessageHelper helper = new MimeMessageHelper (message , true , UTF_8_ENCODING );
77- helper .setPriority (1 );
78- helper .setSubject (PASSWORD_RESET_REQUEST );
79- helper .setFrom (fromEmail );
80- helper .setTo (to );
81- helper .setText (text , true );
82- emailSender .send (message );
79+ var htmlContent = templateEngine .process (PASSWORD_RESET_TEMPLATE , context );
80+
81+ sendEmail (to , PASSWORD_RESET_REQUEST , htmlContent );
82+ log .info ("Password reset email sent to: {}" , to );
8383 } catch (Exception exception ) {
84- log .error (exception .getMessage (), exception );
84+ log .error ("Error sending password reset email: {}" , exception .getMessage (), exception );
8585 throw new ApiException ("Unable to send email" );
8686 }
8787 }
8888
8989 @ Override
9090 public void sendNewTicketHtmlEmail (String name , String email , String ticketTitle , String ticketNumber , String priority ) {
91-
91+ // TODO: Implement when needed
9292 }
9393
9494 @ Override
9595 public void sendNewFilesHtmlEmail (String name , String email , String files , String ticketTitle , String ticketNumber , String priority , String date ) {
96-
96+ // TODO: Implement when needed
9797 }
9898
99- private MimeMessage getMimeMessage (){
100- return emailSender .createMimeMessage ();
99+ /**
100+ * Core method to send email using SendGrid
101+ */
102+ private void sendEmail (String toEmail , String subject , String htmlContent ) {
103+ Email from = new Email (fromEmail , fromName );
104+ Email to = new Email (toEmail );
105+ Content content = new Content ("text/html" , htmlContent );
106+ Mail mail = new Mail (from , subject , to , content );
107+
108+ SendGrid sg = new SendGrid (sendGridApiKey );
109+ Request request = new Request ();
110+
111+ try {
112+ request .setMethod (Method .POST );
113+ request .setEndpoint ("mail/send" );
114+ request .setBody (mail .build ());
115+
116+ Response response = sg .api (request );
117+
118+ if (response .getStatusCode () >= 200 && response .getStatusCode () < 300 ) {
119+ log .info ("Email sent successfully to {}. Status: {}" , toEmail , response .getStatusCode ());
120+ } else {
121+ log .error ("Failed to send email to {}. Status: {}, Body: {}" ,
122+ toEmail , response .getStatusCode (), response .getBody ());
123+ throw new ApiException ("Failed to send email. Status: " + response .getStatusCode ());
124+ }
125+ } catch (IOException ex ) {
126+ log .error ("Error calling SendGrid API: {}" , ex .getMessage (), ex );
127+ throw new ApiException ("Failed to send email via SendGrid" );
128+ }
101129 }
102- }
130+ }
0 commit comments