A newsletter website allows users to subscribe and receive daily emails with useful content. In this tutorial, we will build a Spring Boot newsletter website that sends a random LeetCode question to users every day at 7:30 PM.
1. Project Setup
Step 1: Create a Spring Boot Project
Use Spring Initializr to create a Spring Boot project with the following dependencies:
- Spring Web (for REST API)
- Spring Boot Mail (for email service)
- Spring Data JPA (for database operations)
- Spring Scheduler (for scheduling jobs)
- H2 Database (or MySQL for persistence)
Download the generated project and extract it.
2. Configure Dependencies
Step 2: Add Dependencies in pom.xml
<dependencies>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-web</artifactId>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-data-jpa</artifactId>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-mail</artifactId>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-thymeleaf</artifactId>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter</artifactId>
</dependency>
</dependencies>
3. Configure Database and Email
Step 3: Update application.properties
# H2 Database Configuration (for development)
spring.datasource.url=jdbc:h2:mem:testdb
spring.datasource.driverClassName=org.h2.Driver
spring.datasource.username=sa
spring.datasource.password=
spring.jpa.database-platform=org.hibernate.dialect.H2Dialect
# Email Configuration
spring.mail.host=smtp.gmail.com
spring.mail.port=587
spring.mail.username=your-email@gmail.com
spring.mail.password=your-email-password
spring.mail.properties.mail.smtp.auth=true
spring.mail.properties.mail.smtp.starttls.enable=true
Note: Use environment variables or a secrets manager for email credentials in production.
4. Create Entity Model
Step 4: Create User
Entity
@Entity
public class User {
@Id
@GeneratedValue(strategy = GenerationType.IDENTITY)
private Long id;
private String email;
private boolean subscribed;
// Constructors, Getters, and Setters
}
Step 5: Create Question
Entity
@Entity
public class Question {
@Id
@GeneratedValue(strategy = GenerationType.IDENTITY)
private Long id;
private String title;
private String url;
private String difficulty;
}
5. Create Services
Step 6: Implement Email Service
@Service
public class EmailService {
@Autowired
private JavaMailSender mailSender;
public void sendEmail(String to, String subject, String text) {
SimpleMailMessage message = new SimpleMailMessage();
message.setTo(to);
message.setSubject(subject);
message.setText(text);
mailSender.send(message);
}
}
Step 7: Implement Question Service
@Service
public class QuestionService {
@Autowired
private QuestionRepository questionRepository;
public Question getRandomQuestion() {
List<Question> questions = questionRepository.findAll();
return questions.isEmpty() ? null : questions.get(new Random().nextInt(questions.size()));
}
}
6. Implement Subscription System
Step 8: Create User Repository
@Repository
public interface UserRepository extends JpaRepository<User, Long> {
Optional<User> findByEmail(String email);
}
Step 9: Create Subscription Controller
@RestController
@RequestMapping("/api/subscription")
public class SubscriptionController {
@Autowired
private UserRepository userRepository;
@PostMapping("/subscribe")
public String subscribe(@RequestParam String email) {
if (userRepository.findByEmail(email).isPresent()) {
return "You are already subscribed!";
}
userRepository.save(new User(email, true));
return "Subscription successful!";
}
@PostMapping("/unsubscribe")
public String unsubscribe(@RequestParam String email) {
userRepository.findByEmail(email).ifPresent(user -> {
user.setSubscribed(false);
userRepository.save(user);
});
return "Unsubscribed successfully!";
}
}
7. Implement Email Scheduler
Step 10: Schedule Daily Emails
@Component
public class EmailScheduler {
@Autowired
private QuestionService questionService;
@Autowired
private EmailService emailService;
@Autowired
private UserRepository userRepository;
@Scheduled(cron = "0 30 19 * * ?") // Runs daily at 7:30 PM
public void sendDailyQuestion() {
Question question = questionService.getRandomQuestion();
if (question != null) {
String subject = "Daily LeetCode Question - " + question.getDifficulty();
String body = "Today's question: " + question.getTitle() + "\n"
+ "Solve it here: " + question.getUrl();
List<User> subscribers = userRepository.findAll();
for (User user : subscribers) {
if (user.isSubscribed()) {
emailService.sendEmail(user.getEmail(), subject, body);
}
}
}
}
}
8. Test and Run the Application
- Run Spring Boot Application
mvn spring-boot:run
- Subscribe to the newsletter
curl -X POST "http://localhost:8080/api/subscription/subscribe?email=user@example.com"
- Unsubscribe from the newsletter
curl -X POST "http://localhost:8080/api/subscription/unsubscribe?email=user@example.com"
- Check email inbox at 7:30 PM 🚀
🎯 Congratulations! You have successfully built a newsletter website that sends daily LeetCode questions via email.
Let me know if you have any questions! 🚀
Top comments (0)