Разбираюсь со Спрингом, и некоторые вещи мне не до конца ясны. К примеру, прочитанная недавно статья:
https://habr.com/ru/post/352954/
В тексте приводится пример создания сервисов:
1. Создаётся интерфейс EmailService:
public interface EmailService {
void send(String to, String title, String body);
}
2. Реализуя его, создаётся сервис, в котором переопределяется метод:
@Service
@RequiredArgsConstructor(onConstructor = @__(@Autowired))
public class EmailServiceImpl implements EmailService {
private final JavaMailSender emailSender;
@Override
public void send(String to, String subject, String text) {
MimeMessage message = this.emailSender.createMimeMessage();
MimeMessageHelper helper = new MimeMessageHelper(message);
try {
helper.setTo(to);
helper.setSubject(subject);
helper.setText(text);
this.emailSender.send(message);
} catch (MessagingException messageException) {
throw new RuntimeException(messageException);
}
}
}
А дальше в SchedulerService инжектится не EmailServiceImpl, а "исходный" EmailService:
@Slf4j
@Service
@RequiredArgsConstructor(onConstructor = @__(@Autowired))
public class SchedulerService {
private final UserRepositoryService userService;
private final EmailService emailService;
}
Вопросы, которые мне не ясны:
1. Это нормально?
2. Почему инжектится "исходный" интерфейс?
3. Зачем создаётся EmailServiceImpl, если он не используется? Он ведь не используется?
4. Тут какая-то хитрая магия Spring? Он видит, что есть
ИмяИнтерфейсаImpl и учитывает это в процессе? Как это работает?
5. Как правильно в Spring создавать интерфейсы и правильно их инжектить?