如何在Spring Boot中配置多个(未知数量)不同的smtp服务器?

问题描述 投票:0回答:2

我的问题看起来类似于如何在 springboot 中配置两个不同的电子邮件?

而且这个答案非常酷 但与我的需求不同。我不知道要配置多少个smtp服务器。我希望能够仅通过在配置中添加几行来添加电子邮件服务器。

在代码中我想@Autowire 他们像:

@Autowire
private List<JavaMailSenderImpl> javaMailSenders

我想要这样的配置

spring.mail.first.host=host1
spring.mail.first.port=port1
spring.mail.first.username=username1
spring.mail.first.password=password1
spring.mail.first.properties.mail.smtp.auth=true
...
spring.mail.second.host=host2
spring.mail.second.port=port2
spring.mail.second.username=username2
spring.mail.second.password=password2
spring.mail.second.properties.mail.smtp.auth=true
...
spring.mail.fifth.host=host5
spring.mail.fifth.port=port5
spring.mail.fifth.username=username5
spring.mail.fifth.password=password5
spring.mail.fifth.properties.mail.smtp.auth=true

你能帮忙吗?

java spring spring-boot email smtp
2个回答
2
投票

您可以将原始答案有关动态创建bean的答案结合起来。

例如,假设您创建自己的

MailListProperties

@ConfigurationProperties(prefix = "mail")
public record MailListProperties(Map<String, MailProperties> list) { }

然后您可以创建自己的

BeanDefinitionRegistryPostProcessor
类来创建
JavaMailSenderImpl
beans:

public class DynamicMailsenderBeanDefinitionRegistrar implements BeanDefinitionRegistryPostProcessor {
    private final MailListProperties properties;

    public DynamicMailsenderBeanDefinitionRegistrar(Environment environment) {
        this.properties = Binder
            .get(environment)
            .bind("mail", MailListProperties.class)
            .orElseThrow(IllegalStateException::new);
    }

    @Override
    public void postProcessBeanDefinitionRegistry(BeanDefinitionRegistry registry) throws BeansException {
        properties.list().forEach((beanName, mailProperties) -> {
            GenericBeanDefinition definition = new GenericBeanDefinition();
            definition.setBeanClass(JavaMailSenderImpl.class);
            definition.setInstanceSupplier(() -> {
                 JavaMailSenderImpl sender = new JavaMailSenderImpl();
                 sender.setHost(mailProperties.getHost());
                 // TODO: Here you put the logic to create a JavaMailSenderImpl
                 // You can read the properties defined in MailProperties
                 return sender;
            });
            registry.registerBeanDefinition(beanName, definition);
        });
    }

    @Override
    public void postProcessBeanFactory(ConfigurableListableBeanFactory beanFactory) throws BeansException {

    }
}

要注册

DynamicMailsenderBeanDefinitionRegistrar
bean,您可以使用以下代码:

@Bean
public DynamicMailsenderBeanDefinitionRegistrar registrar(Environment environment) {
    return new DynamicMailsenderBeanDefinitionRegistrar(environment);
}

要配置属性,您可以使用以下属性文件:

mail.list.first.host=...
mail.list.first.username=...
mail.list.first.password=...
mail.list.second.host=...
mail.list.second.username=...
mail.list.second.password=...
mail.list.third.host=...
mail.list.third.username=...
mail.list.third.password=...

在此示例中,属性文件中的键(

first
second
third
)将成为 bean 名称。您可以选择自动装配特定的 JavaMailSenderImpl bean,如下所示:

@Autowired
@Qualifier("first")
private JavaMailSenderImpl firstMailSender;

或者,您可以使用集合自动装配特定类型的所有 bean:

@Autowired
private List<JavaMailSenderImpl> mailSenders;

0
投票

为什么不将电子邮件配置保存到数据库中?

如果你必须将配置放在属性中,你可以这样做

spring.mail.host=host1,host2
spring.mail.port=port1,port2
spring.mail.username=username1,username2
spring.mail.password=password1,password2
spring.mail.properties.mail.smtp.auth=true,true

这样你可以避免在更改属性时更改Java代码,但是你需要定义一个分隔符来分隔不同的主机,例如

,
或其他东西,然后在代码中编写。

我认为第二种方法很难维护配置。

© www.soinside.com 2019 - 2024. All rights reserved.