Files
no-copy/src/main/java/ru/soune/nocopy/service/mail/EmailService.java
T

134 lines
4.9 KiB
Java
Raw Normal View History

2026-01-20 03:47:51 +07:00
package ru.soune.nocopy.service.mail;
2026-01-23 16:09:51 +07:00
import jakarta.mail.MessagingException;
import jakarta.mail.internet.MimeMessage;
import lombok.RequiredArgsConstructor;
import lombok.extern.slf4j.Slf4j;
2026-01-19 19:26:59 +07:00
import org.springframework.beans.factory.annotation.Value;
import org.springframework.core.io.ClassPathResource;
import org.springframework.mail.javamail.JavaMailSender;
import org.springframework.mail.javamail.MimeMessageHelper;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;
import ru.soune.nocopy.entity.user.AuthToken;
import ru.soune.nocopy.entity.user.EmailVerificationToken;
import ru.soune.nocopy.entity.user.User;
import ru.soune.nocopy.repository.EmailVerificationTokenRepository;
import java.io.IOException;
import java.nio.charset.StandardCharsets;
import java.security.SecureRandom;
import java.time.LocalDateTime;
@Service
@RequiredArgsConstructor
@Slf4j
public class EmailService {
private final JavaMailSender mailSender;
private final EmailVerificationTokenRepository emailVerificationTokenRepository;
2026-01-20 03:47:51 +07:00
@Value("${app.email.verification.standart-subject}")
private String standartSubject;
@Value("${app.email.verification.standart-address-from}")
private String standartAdressFrom;
@Value("${app.email.verification.user}")
private String user;
2026-02-17 20:17:34 +07:00
@Value("${app.email.verification.drop-password-subject}")
private String dropPasswordSubject;
2026-02-20 10:50:44 +07:00
@Value("${server.baseurl}")
private String baseUrl;
@Value("${server.front.port}")
private String frontPort;
2026-01-23 16:09:51 +07:00
public void sendVerificationEmail(User user, String code) throws MessagingException, IOException {
MimeMessage message = mailSender.createMimeMessage();
MimeMessageHelper helper = new MimeMessageHelper(message, true, "UTF-8");
2026-02-17 18:11:32 +07:00
helper.setFrom("noreply@no-copy.ru");
2026-01-23 16:09:51 +07:00
helper.setTo(user.getEmail());
helper.setSubject(standartSubject);
2026-02-17 20:17:34 +07:00
String htmlContent = loadAndProcessTemplate(user.getFullName(), code,
"templates/email-verification.html");
2026-01-23 16:09:51 +07:00
helper.setText(htmlContent, true);
2026-01-23 16:09:51 +07:00
mailSender.send(message);
}
@Transactional
public EmailVerificationToken createEmailVerificationToken(AuthToken authToken) {
2026-02-20 11:11:24 +07:00
EmailVerificationToken existingToken = emailVerificationTokenRepository
.findByUserId(authToken.getUser().getId());
if (existingToken != null) {
emailVerificationTokenRepository.deleteById(existingToken.getId());
}
EmailVerificationToken emailToken = new EmailVerificationToken();
emailToken.setUser(authToken.getUser());
emailToken.setToken(generateVerificationCode());
emailToken.setCreatedAt(LocalDateTime.now());
return emailVerificationTokenRepository.save(emailToken);
}
private String generateVerificationCode() {
SecureRandom random = new SecureRandom();
int code = 100000 + random.nextInt(900000);
return String.valueOf(code);
}
2026-02-17 20:17:34 +07:00
private String loadAndProcessTemplate(String username, String code, String templatePath) throws IOException {
ClassPathResource resource = new ClassPathResource(templatePath);
String template = new String(resource.getInputStream().readAllBytes(), StandardCharsets.UTF_8);
2026-01-20 03:47:51 +07:00
String safeUsername = escapeHtml(username != null ? username : user);
String safeCode = escapeHtml(code);
return template
.replace("{{username}}", safeUsername)
.replace("{{code}}", safeCode);
}
private String escapeHtml(String text) {
if (text == null) return "";
return text
.replace("&", "&")
.replace("<", "&lt;")
.replace(">", "&gt;")
.replace("\"", "&quot;")
.replace("'", "&#39;");
}
2026-02-17 20:17:34 +07:00
public void sendResetPasswordEmail(User user, String code) {
try {
MimeMessage message = mailSender.createMimeMessage();
MimeMessageHelper helper = new MimeMessageHelper(message, true, "UTF-8");
helper.setFrom(standartAdressFrom);
helper.setTo(user.getEmail());
helper.setSubject(dropPasswordSubject);
String htmlContent = loadAndProcessTemplate(user.getFullName(), code,
"templates/reset-password.html");
2026-02-20 11:19:54 +07:00
//TODO frontPort убрать после настройки редиректа nginx
String resetLink = escapeHtml(baseUrl + frontPort + "/reset-password?email=" + user.getEmail());
2026-02-20 10:50:44 +07:00
htmlContent = htmlContent.replace("{{resetLink}}", resetLink);
2026-02-17 20:17:34 +07:00
helper.setText(htmlContent, true);
mailSender.send(message);
log.info("Email sent to: {}", user.getEmail());
} catch (Exception e) {
log.error("Failed to send email: {}", e.getMessage());
}
}
}