1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17 package org.apache.commons.mail2.jakarta;
18
19 import java.io.UnsupportedEncodingException;
20 import java.nio.charset.Charset;
21 import java.time.Duration;
22 import java.util.ArrayList;
23 import java.util.Collection;
24 import java.util.Date;
25 import java.util.HashMap;
26 import java.util.List;
27 import java.util.Map;
28 import java.util.Objects;
29 import java.util.Properties;
30
31 import javax.naming.Context;
32 import javax.naming.InitialContext;
33 import javax.naming.NamingException;
34
35 import org.apache.commons.mail2.core.EmailConstants;
36 import org.apache.commons.mail2.core.EmailException;
37 import org.apache.commons.mail2.core.EmailUtils;
38 import org.apache.commons.mail2.jakarta.util.IDNEmailAddressConverter;
39
40 import jakarta.mail.Authenticator;
41 import jakarta.mail.Message;
42 import jakarta.mail.MessagingException;
43 import jakarta.mail.Session;
44 import jakarta.mail.Store;
45 import jakarta.mail.Transport;
46 import jakarta.mail.internet.AddressException;
47 import jakarta.mail.internet.InternetAddress;
48 import jakarta.mail.internet.MimeMessage;
49 import jakarta.mail.internet.MimeMultipart;
50 import jakarta.mail.internet.MimeUtility;
51
52
53
54
55
56
57
58
59
60 public abstract class Email {
61
62
63
64
65 private static final InternetAddress[] EMPTY_INTERNET_ADDRESS_ARRAY = {};
66
67
68
69
70 private MimeMessage message;
71
72
73
74
75 private String charset;
76
77
78
79
80 private InternetAddress fromAddress;
81
82
83
84
85 private String subject;
86
87
88
89
90 private MimeMultipart emailBody;
91
92
93
94
95 private Object content;
96
97
98
99
100 private String contentType;
101
102
103
104
105 private boolean debug;
106
107
108
109
110 private Date sentDate;
111
112
113
114
115 private Authenticator authenticator;
116
117
118
119
120 private String hostName;
121
122
123
124
125 private String smtpPort = "25";
126
127
128
129
130 private String sslSmtpPort = "465";
131
132
133
134
135 private List<InternetAddress> toList = new ArrayList<>();
136
137
138
139
140 private List<InternetAddress> ccList = new ArrayList<>();
141
142
143
144
145 private List<InternetAddress> bccList = new ArrayList<>();
146
147
148
149
150 private List<InternetAddress> replyList = new ArrayList<>();
151
152
153
154
155
156 private String bounceAddress;
157
158
159
160
161
162
163 private final Map<String, String> headers = new HashMap<>();
164
165
166
167
168 private boolean popBeforeSmtp;
169
170
171
172
173 private String popHost;
174
175
176
177
178 private String popUsername;
179
180
181
182
183 private String popPassword;
184
185
186
187
188 private boolean tls;
189
190
191
192
193 private boolean ssl;
194
195
196
197
198 private int socketTimeout = Math.toIntExact(EmailConstants.SOCKET_TIMEOUT.toMillis());
199
200
201
202
203 private int socketConnectionTimeout = Math.toIntExact(EmailConstants.SOCKET_TIMEOUT.toMillis());
204
205
206
207
208
209 private boolean startTlsEnabled;
210
211
212
213
214
215 private boolean startTlsRequired;
216
217
218
219
220 private boolean sslOnConnect;
221
222
223
224
225
226 private boolean sslCheckServerIdentity;
227
228
229
230
231
232
233 private boolean sendPartial;
234
235
236
237
238 private Session session;
239
240
241
242
243 public Email() {
244
245 }
246
247
248
249
250
251
252
253
254
255
256
257 public Email addBcc(final String email) throws EmailException {
258 return addBcc(email, null);
259 }
260
261
262
263
264
265
266
267
268
269
270
271 public Email addBcc(final String... emails) throws EmailException {
272 EmailException.checkNonEmpty(emails, () -> "BCC list invalid.");
273 for (final String email : emails) {
274 addBcc(email, null);
275 }
276 return this;
277 }
278
279
280
281
282
283
284
285
286
287
288
289
290 public Email addBcc(final String email, final String name) throws EmailException {
291 return addBcc(email, name, charset);
292 }
293
294
295
296
297
298
299
300
301
302
303
304 public Email addBcc(final String email, final String name, final String charset) throws EmailException {
305 bccList.add(createInternetAddress(email, name, charset));
306 return this;
307 }
308
309
310
311
312
313
314
315
316
317
318
319 public Email addCc(final String email) throws EmailException {
320 return addCc(email, null);
321 }
322
323
324
325
326
327
328
329
330
331
332
333 public Email addCc(final String... emails) throws EmailException {
334 EmailException.checkNonEmpty(emails, () -> "CC list invalid.");
335 for (final String email : emails) {
336 addCc(email, null);
337 }
338 return this;
339 }
340
341
342
343
344
345
346
347
348
349
350
351
352 public Email addCc(final String email, final String name) throws EmailException {
353 return addCc(email, name, charset);
354 }
355
356
357
358
359
360
361
362
363
364
365
366 public Email addCc(final String email, final String name, final String charset) throws EmailException {
367 ccList.add(createInternetAddress(email, name, charset));
368 return this;
369 }
370
371
372
373
374
375
376
377
378
379 public void addHeader(final String name, final String value) {
380 if (EmailUtils.isEmpty(name)) {
381 throw new IllegalArgumentException("name can not be null or empty");
382 }
383 if (EmailUtils.isEmpty(value)) {
384 throw new IllegalArgumentException("value can not be null or empty");
385 }
386 headers.put(name, value);
387 }
388
389
390
391
392
393
394
395
396
397
398
399 public Email addReplyTo(final String email) throws EmailException {
400 return addReplyTo(email, null);
401 }
402
403
404
405
406
407
408
409
410
411
412
413
414 public Email addReplyTo(final String email, final String name) throws EmailException {
415 return addReplyTo(email, name, charset);
416 }
417
418
419
420
421
422
423
424
425
426
427
428 public Email addReplyTo(final String email, final String name, final String charset) throws EmailException {
429 replyList.add(createInternetAddress(email, name, charset));
430 return this;
431 }
432
433
434
435
436
437
438
439
440
441
442
443 public Email addTo(final String email) throws EmailException {
444 return addTo(email, null);
445 }
446
447
448
449
450
451
452
453
454
455
456
457 public Email addTo(final String... emails) throws EmailException {
458 EmailException.checkNonEmpty(emails, () -> "To list invalid.");
459 for (final String email : emails) {
460 addTo(email, null);
461 }
462 return this;
463 }
464
465
466
467
468
469
470
471
472
473
474
475
476 public Email addTo(final String email, final String name) throws EmailException {
477 return addTo(email, name, charset);
478 }
479
480
481
482
483
484
485
486
487
488
489
490 public Email addTo(final String email, final String name, final String charset) throws EmailException {
491 toList.add(createInternetAddress(email, name, charset));
492 return this;
493 }
494
495
496
497
498
499
500
501
502
503 public void buildMimeMessage() throws EmailException {
504 if (message != null) {
505
506
507 throw new IllegalStateException("The MimeMessage is already built.");
508 }
509
510 try {
511 message = createMimeMessage(getMailSession());
512
513 if (EmailUtils.isNotEmpty(subject)) {
514 if (EmailUtils.isNotEmpty(charset)) {
515 message.setSubject(subject, charset);
516 } else {
517 message.setSubject(subject);
518 }
519 }
520
521
522 updateContentType(contentType);
523
524 if (content != null) {
525 if (EmailConstants.TEXT_PLAIN.equalsIgnoreCase(contentType) && content instanceof String) {
526
527
528 message.setText(content.toString(), charset);
529 } else {
530 message.setContent(content, contentType);
531 }
532 } else if (emailBody != null) {
533 if (contentType == null) {
534 message.setContent(emailBody);
535 } else {
536 message.setContent(emailBody, contentType);
537 }
538 } else {
539 message.setText("");
540 }
541
542 if (fromAddress != null) {
543 message.setFrom(fromAddress);
544 } else if (session.getProperty(EmailConstants.MAIL_SMTP_FROM) == null && session.getProperty(EmailConstants.MAIL_FROM) == null) {
545 throw new EmailException("From address required");
546 }
547
548 if (toList.size() + ccList.size() + bccList.size() == 0) {
549 throw new EmailException("At least one receiver address required");
550 }
551
552 if (!EmailUtils.isEmpty(toList)) {
553 message.setRecipients(Message.RecipientType.TO, toInternetAddressArray(toList));
554 }
555
556 if (!EmailUtils.isEmpty(ccList)) {
557 message.setRecipients(Message.RecipientType.CC, toInternetAddressArray(ccList));
558 }
559
560 if (!EmailUtils.isEmpty(bccList)) {
561 message.setRecipients(Message.RecipientType.BCC, toInternetAddressArray(bccList));
562 }
563
564 if (!EmailUtils.isEmpty(replyList)) {
565 message.setReplyTo(toInternetAddressArray(replyList));
566 }
567
568 if (!EmailUtils.isEmpty(headers)) {
569 for (final Map.Entry<String, String> entry : headers.entrySet()) {
570 final String foldedValue = createFoldedHeaderValue(entry.getKey(), entry.getValue());
571 message.addHeader(entry.getKey(), foldedValue);
572 }
573 }
574
575 if (message.getSentDate() == null) {
576 message.setSentDate(getSentDate());
577 }
578
579 if (popBeforeSmtp) {
580
581 final Store store = session.getStore("pop3");
582 store.connect(popHost, popUsername, popPassword);
583 }
584 } catch (final MessagingException e) {
585 throw new EmailException(e);
586 }
587 }
588
589
590
591
592
593
594 private void checkSessionAlreadyInitialized() {
595 if (session != null) {
596 throw new IllegalStateException("The mail session is already initialized");
597 }
598 }
599
600
601
602
603
604
605
606
607
608 private String createFoldedHeaderValue(final String name, final String value) {
609 if (EmailUtils.isEmpty(name)) {
610 throw new IllegalArgumentException("name can not be null or empty");
611 }
612 if (EmailUtils.isEmpty(value)) {
613 throw new IllegalArgumentException("value can not be null or empty");
614 }
615 try {
616 return MimeUtility.fold(name.length() + 2, MimeUtility.encodeText(value, charset, null));
617 } catch (final UnsupportedEncodingException e) {
618 return value;
619 }
620 }
621
622
623
624
625
626
627
628
629
630
631 private InternetAddress createInternetAddress(final String email, final String name, final String charsetName) throws EmailException {
632 try {
633 final InternetAddress address = new InternetAddress(new IDNEmailAddressConverter().toASCII(email));
634
635 if (EmailUtils.isNotEmpty(name)) {
636
637 if (EmailUtils.isEmpty(charsetName)) {
638 address.setPersonal(name);
639 } else {
640
641
642 final Charset set = Charset.forName(charsetName);
643 address.setPersonal(name, set.name());
644 }
645 }
646
647
648 address.validate();
649 return address;
650 } catch (final AddressException | UnsupportedEncodingException e) {
651 throw new EmailException(e);
652 }
653 }
654
655
656
657
658
659
660
661 protected MimeMessage createMimeMessage(final Session aSession) {
662 return new MimeMessage(aSession);
663 }
664
665
666
667
668
669
670
671 public Authenticator getAuthenticator() {
672 return authenticator;
673 }
674
675
676
677
678
679
680 public List<InternetAddress> getBccAddresses() {
681 return bccList;
682 }
683
684
685
686
687
688
689
690 public String getBounceAddress() {
691 return bounceAddress;
692 }
693
694
695
696
697
698
699 public List<InternetAddress> getCcAddresses() {
700 return ccList;
701 }
702
703
704
705
706
707
708
709 public String getCharsetName() {
710 return charset;
711 }
712
713
714
715
716
717
718
719 public Object getContent() {
720 return content;
721 }
722
723
724
725
726
727
728
729 public String getContentType() {
730 return contentType;
731 }
732
733
734
735
736
737
738
739 public MimeMultipart getEmailBody() {
740 return emailBody;
741 }
742
743
744
745
746
747
748 public InternetAddress getFromAddress() {
749 return fromAddress;
750 }
751
752
753
754
755
756
757
758
759 public String getHeader(final String header) {
760 return headers.get(header);
761 }
762
763
764
765
766
767
768
769 public Map<String, String> getHeaders() {
770 return headers;
771 }
772
773
774
775
776
777
778 public String getHostName() {
779 if (session != null) {
780 return session.getProperty(EmailConstants.MAIL_HOST);
781 }
782 if (EmailUtils.isNotEmpty(hostName)) {
783 return hostName;
784 }
785 return null;
786 }
787
788
789
790
791
792
793
794
795
796 public Session getMailSession() throws EmailException {
797 if (session == null) {
798 final Properties properties = new Properties(System.getProperties());
799 properties.setProperty(EmailConstants.MAIL_TRANSPORT_PROTOCOL, EmailConstants.SMTP);
800
801 if (EmailUtils.isEmpty(hostName)) {
802 hostName = properties.getProperty(EmailConstants.MAIL_HOST);
803 }
804
805 EmailException.checkNonEmpty(hostName, () -> "Cannot find valid hostname for mail session");
806
807 properties.setProperty(EmailConstants.MAIL_PORT, smtpPort);
808 properties.setProperty(EmailConstants.MAIL_HOST, hostName);
809 properties.setProperty(EmailConstants.MAIL_DEBUG, String.valueOf(debug));
810
811 properties.setProperty(EmailConstants.MAIL_TRANSPORT_STARTTLS_ENABLE, Boolean.toString(isStartTLSEnabled()));
812 properties.setProperty(EmailConstants.MAIL_TRANSPORT_STARTTLS_REQUIRED, Boolean.toString(isStartTLSRequired()));
813
814 properties.setProperty(EmailConstants.MAIL_SMTP_SEND_PARTIAL, Boolean.toString(isSendPartial()));
815 properties.setProperty(EmailConstants.MAIL_SMTPS_SEND_PARTIAL, Boolean.toString(isSendPartial()));
816
817 if (authenticator != null) {
818 properties.setProperty(EmailConstants.MAIL_SMTP_AUTH, "true");
819 }
820
821 if (isSSLOnConnect()) {
822 properties.setProperty(EmailConstants.MAIL_PORT, sslSmtpPort);
823 properties.setProperty(EmailConstants.MAIL_SMTP_SOCKET_FACTORY_PORT, sslSmtpPort);
824 properties.setProperty(EmailConstants.MAIL_SMTP_SOCKET_FACTORY_CLASS, "javax.net.ssl.SSLSocketFactory");
825 properties.setProperty(EmailConstants.MAIL_SMTP_SOCKET_FACTORY_FALLBACK, "false");
826 }
827
828 if ((isSSLOnConnect() || isStartTLSEnabled()) && isSSLCheckServerIdentity()) {
829 properties.setProperty(EmailConstants.MAIL_SMTP_SSL_CHECKSERVERIDENTITY, "true");
830 }
831
832 if (bounceAddress != null) {
833 properties.setProperty(EmailConstants.MAIL_SMTP_FROM, bounceAddress);
834 }
835
836 if (socketTimeout > 0) {
837 properties.setProperty(EmailConstants.MAIL_SMTP_TIMEOUT, Integer.toString(socketTimeout));
838 }
839
840 if (socketConnectionTimeout > 0) {
841 properties.setProperty(EmailConstants.MAIL_SMTP_CONNECTIONTIMEOUT, Integer.toString(socketConnectionTimeout));
842 }
843
844
845
846 session = Session.getInstance(properties, authenticator);
847 }
848 return session;
849 }
850
851
852
853
854
855
856
857 public MimeMessage getMessage() {
858 return message;
859 }
860
861
862
863
864
865
866 public MimeMessage getMimeMessage() {
867 return message;
868 }
869
870
871
872
873
874
875
876 public String getPopHost() {
877 return popHost;
878 }
879
880
881
882
883
884
885
886 public String getPopPassword() {
887 return popPassword;
888 }
889
890
891
892
893
894
895
896 public String getPopUserName() {
897 return popUsername;
898 }
899
900
901
902
903
904
905 public List<InternetAddress> getReplyToAddresses() {
906 return replyList;
907 }
908
909
910
911
912
913
914
915 public Date getSentDate() {
916 if (sentDate == null) {
917 return new Date();
918 }
919 return new Date(sentDate.getTime());
920 }
921
922
923
924
925
926
927 public String getSmtpPort() {
928 if (session != null) {
929 return session.getProperty(EmailConstants.MAIL_PORT);
930 }
931 if (EmailUtils.isNotEmpty(smtpPort)) {
932 return smtpPort;
933 }
934 return null;
935 }
936
937
938
939
940
941
942
943 public int getSocketConnectionTimeout() {
944 return socketConnectionTimeout;
945 }
946
947
948
949
950
951
952
953 public int getSocketTimeout() {
954 return socketTimeout;
955 }
956
957
958
959
960
961
962 public String getSslSmtpPort() {
963 if (session != null) {
964 return session.getProperty(EmailConstants.MAIL_SMTP_SOCKET_FACTORY_PORT);
965 }
966 if (EmailUtils.isNotEmpty(sslSmtpPort)) {
967 return sslSmtpPort;
968 }
969 return null;
970 }
971
972
973
974
975
976
977 public String getSubject() {
978 return subject;
979 }
980
981
982
983
984
985
986 public List<InternetAddress> getToAddresses() {
987 return toList;
988 }
989
990
991
992
993
994
995
996 public boolean isDebug() {
997 return debug;
998 }
999
1000
1001
1002
1003
1004
1005
1006 public boolean isPopBeforeSmtp() {
1007 return popBeforeSmtp;
1008 }
1009
1010
1011
1012
1013
1014
1015
1016 public boolean isSendPartial() {
1017 return sendPartial;
1018 }
1019
1020
1021
1022
1023
1024
1025
1026 public boolean isSSLCheckServerIdentity() {
1027 return sslCheckServerIdentity;
1028 }
1029
1030
1031
1032
1033
1034
1035
1036 public boolean isSSLOnConnect() {
1037 return sslOnConnect || ssl;
1038 }
1039
1040
1041
1042
1043
1044
1045
1046 public boolean isStartTLSEnabled() {
1047 return startTlsEnabled || tls;
1048 }
1049
1050
1051
1052
1053
1054
1055
1056 public boolean isStartTLSRequired() {
1057 return startTlsRequired;
1058 }
1059
1060
1061
1062
1063
1064
1065
1066
1067 public String send() throws EmailException {
1068 buildMimeMessage();
1069 return sendMimeMessage();
1070 }
1071
1072
1073
1074
1075
1076
1077
1078
1079 public String sendMimeMessage() throws EmailException {
1080 Objects.requireNonNull(message, "MimeMessage has not been created yet");
1081 try {
1082 Transport.send(message);
1083 return message.getMessageID();
1084 } catch (final Throwable t) {
1085 throw new EmailException("Sending the email to the following server failed : " + this.getHostName() + ":" + getSmtpPort(), t);
1086 }
1087 }
1088
1089
1090
1091
1092
1093
1094
1095
1096
1097
1098
1099
1100
1101 public void setAuthentication(final String userName, final String password) {
1102 this.setAuthenticator(new DefaultAuthenticator(userName, password));
1103 }
1104
1105
1106
1107
1108
1109
1110
1111
1112
1113
1114
1115 public void setAuthenticator(final Authenticator authenticator) {
1116 this.authenticator = authenticator;
1117 }
1118
1119
1120
1121
1122
1123
1124
1125
1126
1127
1128 public Email setBcc(final Collection<InternetAddress> collection) throws EmailException {
1129 EmailException.checkNonEmpty(collection, () -> "BCC list invalid");
1130 bccList = new ArrayList<>(collection);
1131 return this;
1132 }
1133
1134
1135
1136
1137
1138
1139
1140
1141
1142
1143 public Email setBounceAddress(final String email) {
1144 checkSessionAlreadyInitialized();
1145 if (!EmailUtils.isEmpty(email)) {
1146 try {
1147 bounceAddress = createInternetAddress(email, null, charset).getAddress();
1148 } catch (final EmailException e) {
1149
1150 throw new IllegalArgumentException("Failed to set the bounce address : " + email, e);
1151 }
1152 } else {
1153 bounceAddress = email;
1154 }
1155
1156 return this;
1157 }
1158
1159
1160
1161
1162
1163
1164
1165
1166
1167
1168 public Email setCc(final Collection<InternetAddress> collection) throws EmailException {
1169 EmailException.checkNonEmpty(collection, () -> "CC list invalid");
1170 ccList = new ArrayList<>(collection);
1171 return this;
1172 }
1173
1174
1175
1176
1177
1178
1179
1180
1181
1182 public void setCharset(final String charset) {
1183 final Charset set = Charset.forName(charset);
1184 this.charset = set.name();
1185 }
1186
1187
1188
1189
1190
1191
1192
1193 public void setContent(final MimeMultipart mimeMultipart) {
1194 this.emailBody = mimeMultipart;
1195 }
1196
1197
1198
1199
1200
1201
1202
1203
1204 public Email setContent(final Object content) {
1205 this.content = content;
1206 return this;
1207 }
1208
1209
1210
1211
1212
1213
1214
1215
1216 public void setContent(final Object content, final String contentType) {
1217 this.content = content;
1218 updateContentType(contentType);
1219 }
1220
1221
1222
1223
1224
1225
1226
1227
1228 public Email setContentType(final String contentType) {
1229 this.contentType = contentType;
1230 return this;
1231 }
1232
1233
1234
1235
1236
1237
1238
1239 public void setDebug(final boolean debug) {
1240 this.debug = debug;
1241 }
1242
1243
1244
1245
1246
1247
1248
1249
1250
1251
1252
1253 public Email setFrom(final String email) throws EmailException {
1254 return setFrom(email, null);
1255 }
1256
1257
1258
1259
1260
1261
1262
1263
1264
1265
1266
1267
1268 public Email setFrom(final String email, final String name) throws EmailException {
1269 return setFrom(email, name, charset);
1270 }
1271
1272
1273
1274
1275
1276
1277
1278
1279
1280
1281
1282 public Email setFrom(final String email, final String name, final String charset) throws EmailException {
1283 fromAddress = createInternetAddress(email, name, charset);
1284 return this;
1285 }
1286
1287
1288
1289
1290
1291
1292
1293
1294 public Email setFromAddress(final InternetAddress fromAddress) {
1295 this.fromAddress = fromAddress;
1296 return this;
1297
1298 }
1299
1300
1301
1302
1303
1304
1305
1306
1307
1308
1309 public void setHeaders(final Map<String, String> map) {
1310 headers.clear();
1311 for (final Map.Entry<String, String> entry : map.entrySet()) {
1312 addHeader(entry.getKey(), entry.getValue());
1313 }
1314 }
1315
1316
1317
1318
1319
1320
1321
1322
1323 public void setHostName(final String hostName) {
1324 checkSessionAlreadyInitialized();
1325 this.hostName = hostName;
1326 }
1327
1328
1329
1330
1331
1332
1333
1334
1335
1336
1337
1338
1339 public void setMailSession(final Session session) {
1340 Objects.requireNonNull(session, "no mail session supplied");
1341
1342 final Properties sessionProperties = session.getProperties();
1343 final String auth = sessionProperties.getProperty(EmailConstants.MAIL_SMTP_AUTH);
1344
1345 if (Boolean.parseBoolean(auth)) {
1346 final String userName = sessionProperties.getProperty(EmailConstants.MAIL_SMTP_USER);
1347 final String password = sessionProperties.getProperty(EmailConstants.MAIL_SMTP_PASSWORD);
1348
1349 if (EmailUtils.isNotEmpty(userName) && EmailUtils.isNotEmpty(password)) {
1350
1351
1352 authenticator = new DefaultAuthenticator(userName, password);
1353 this.session = Session.getInstance(sessionProperties, authenticator);
1354 } else {
1355
1356 this.session = session;
1357 }
1358 } else {
1359 this.session = session;
1360 }
1361 }
1362
1363
1364
1365
1366
1367
1368
1369
1370
1371 public void setMailSessionFromJNDI(final String jndiName) throws NamingException {
1372 if (EmailUtils.isEmpty(jndiName)) {
1373 throw new IllegalArgumentException("JNDI name missing");
1374 }
1375 Context ctx = null;
1376 if (jndiName.startsWith("java:")) {
1377 ctx = new InitialContext();
1378 } else {
1379 ctx = (Context) new InitialContext().lookup("java:comp/env");
1380
1381 }
1382 setMailSession((Session) ctx.lookup(jndiName));
1383 }
1384
1385
1386
1387
1388
1389
1390 public void setMessage(final MimeMessage message) {
1391 this.message = message;
1392 }
1393
1394
1395
1396
1397
1398
1399
1400
1401
1402 public abstract Email setMsg(String msg) throws EmailException;
1403
1404
1405
1406
1407
1408
1409
1410
1411 public Email setPopBeforeSmtp(final boolean popBeforeSmtp) {
1412 this.popBeforeSmtp = popBeforeSmtp;
1413 return this;
1414
1415 }
1416
1417
1418
1419
1420
1421
1422
1423
1424
1425
1426 public void setPopBeforeSmtp(final boolean popBeforeSmtp, final String popHost, final String popUserName, final String popPassword) {
1427 this.popBeforeSmtp = popBeforeSmtp;
1428 this.popHost = popHost;
1429 this.popUsername = popUserName;
1430 this.popPassword = popPassword;
1431 }
1432
1433
1434
1435
1436
1437
1438
1439
1440 public Email setPopHost(final String popHost) {
1441 this.popHost = popHost;
1442 return this;
1443
1444 }
1445
1446
1447
1448
1449
1450
1451
1452
1453 public Email setPopPassword(final String popPassword) {
1454 this.popPassword = popPassword;
1455 return this;
1456
1457 }
1458
1459
1460
1461
1462
1463
1464
1465
1466 public Email setPopUsername(final String popUserName) {
1467 this.popUsername = popUserName;
1468 return this;
1469
1470 }
1471
1472
1473
1474
1475
1476
1477
1478
1479
1480
1481
1482 public Email setReplyTo(final Collection<InternetAddress> collection) throws EmailException {
1483 EmailException.checkNonEmpty(collection, () -> "Reply to list invalid");
1484 replyList = new ArrayList<>(collection);
1485 return this;
1486 }
1487
1488
1489
1490
1491
1492
1493
1494
1495
1496
1497
1498
1499
1500
1501 public Email setSendPartial(final boolean sendPartial) {
1502 checkSessionAlreadyInitialized();
1503 this.sendPartial = sendPartial;
1504 return this;
1505 }
1506
1507
1508
1509
1510
1511
1512
1513 public void setSentDate(final Date date) {
1514 if (date != null) {
1515
1516 sentDate = new Date(date.getTime());
1517 }
1518 }
1519
1520
1521
1522
1523
1524
1525
1526
1527
1528
1529 public void setSmtpPort(final int portNumber) {
1530 checkSessionAlreadyInitialized();
1531 if (portNumber < 1) {
1532 throw new IllegalArgumentException("Cannot connect to a port number that is less than 1 ( " + portNumber + " )");
1533 }
1534 this.smtpPort = Integer.toString(portNumber);
1535 }
1536
1537
1538
1539
1540
1541
1542
1543
1544 public void setSocketConnectionTimeout(final Duration socketConnectionTimeout) {
1545 checkSessionAlreadyInitialized();
1546 this.socketConnectionTimeout = Math.toIntExact(socketConnectionTimeout.toMillis());
1547 }
1548
1549
1550
1551
1552
1553
1554
1555
1556 public void setSocketTimeout(final Duration socketTimeout) {
1557 checkSessionAlreadyInitialized();
1558 this.socketTimeout = Math.toIntExact(socketTimeout.toMillis());
1559 }
1560
1561
1562
1563
1564
1565
1566
1567
1568
1569 public Email setSSLCheckServerIdentity(final boolean sslCheckServerIdentity) {
1570 checkSessionAlreadyInitialized();
1571 this.sslCheckServerIdentity = sslCheckServerIdentity;
1572 return this;
1573 }
1574
1575
1576
1577
1578
1579
1580
1581
1582
1583
1584
1585
1586
1587 public Email setSSLOnConnect(final boolean ssl) {
1588 checkSessionAlreadyInitialized();
1589 this.sslOnConnect = ssl;
1590 this.ssl = ssl;
1591 return this;
1592 }
1593
1594
1595
1596
1597
1598
1599
1600
1601 public void setSslSmtpPort(final String sslSmtpPort) {
1602 checkSessionAlreadyInitialized();
1603 this.sslSmtpPort = sslSmtpPort;
1604 }
1605
1606
1607
1608
1609
1610
1611
1612
1613
1614 public Email setStartTLSEnabled(final boolean startTlsEnabled) {
1615 checkSessionAlreadyInitialized();
1616 this.startTlsEnabled = startTlsEnabled;
1617 this.tls = startTlsEnabled;
1618 return this;
1619 }
1620
1621
1622
1623
1624
1625
1626
1627
1628
1629
1630
1631
1632 public Email setStartTLSRequired(final boolean startTlsRequired) {
1633 checkSessionAlreadyInitialized();
1634 this.startTlsRequired = startTlsRequired;
1635 return this;
1636 }
1637
1638
1639
1640
1641
1642
1643
1644
1645 public Email setSubject(final String aSubject) {
1646 this.subject = EmailUtils.replaceEndOfLineCharactersWithSpaces(aSubject);
1647 return this;
1648 }
1649
1650
1651
1652
1653
1654
1655
1656
1657
1658
1659 public Email setTo(final Collection<InternetAddress> collection) throws EmailException {
1660 EmailException.checkNonEmpty(collection, () -> "To list invalid");
1661 this.toList = new ArrayList<>(collection);
1662 return this;
1663 }
1664
1665
1666
1667
1668
1669
1670
1671
1672 protected InternetAddress[] toInternetAddressArray(final List<InternetAddress> list) {
1673 return list.toArray(EMPTY_INTERNET_ADDRESS_ARRAY);
1674 }
1675
1676
1677
1678
1679
1680
1681
1682 public void updateContentType(final String contentType) {
1683 if (EmailUtils.isEmpty(contentType)) {
1684 this.contentType = null;
1685 } else {
1686
1687 this.contentType = contentType;
1688
1689 final String strMarker = "; charset=";
1690 int charsetPos = EmailUtils.toLower(contentType).indexOf(strMarker);
1691 if (charsetPos != -1) {
1692
1693 charsetPos += strMarker.length();
1694 final int intCharsetEnd = EmailUtils.toLower(contentType).indexOf(" ", charsetPos);
1695 if (intCharsetEnd != -1) {
1696 this.charset = contentType.substring(charsetPos, intCharsetEnd);
1697 } else {
1698 this.charset = contentType.substring(charsetPos);
1699 }
1700 } else if (this.contentType.startsWith("text/") && EmailUtils.isNotEmpty(this.charset)) {
1701
1702
1703 final StringBuilder contentTypeBuf = new StringBuilder(this.contentType);
1704 contentTypeBuf.append(strMarker);
1705 contentTypeBuf.append(this.charset);
1706 this.contentType = contentTypeBuf.toString();
1707 }
1708 }
1709 }
1710 }