Изменение настроек электронной почты Spring в зависимости от режима разработки / тестирования / разработки - PullRequest
5 голосов
/ 24 января 2010

Я часто тестирую свое приложение с копией действующей базы данных, но нужно быть осторожным, чтобы не выполнять никаких действий, которые вызывают отправку пользователю электронного письма. Я хотел бы иметь возможность настроить Spring так, чтобы, когда я нахожусь в режиме разработки или тестирования, чтобы никакие электронные письма не отправлялись реальным пользователям. В идеале я хотел бы, чтобы все электронные письма, которые должны были быть отправлены пользователю, вместо этого отправлялись в почтовый ящик, который я могу проверить. И я не хочу изменять какой-либо код, чтобы это произошло, просто файлы конфигурации xml.

Я уже использую PropertyPlaceholderConfigurer и читаю в разных файлах свойств в зависимости от того, работаю ли я в рабочем, тестовом или dev-режимах. Я настраиваю JavaMailSenderImpl на основе значений в файле свойств. Я также использую SimpleMailMessage для создания шаблона с адресом From.

В идеале был бы способ переписать на адрес TO всех исходящих электронных писем тестовую учетную запись, если я работаю в режиме разработки или в тестовом режиме.

Моей первой мыслью было использование другого SMTP-сервера для разработки и тестирования. Но тогда мне пришлось бы также управлять другим почтовым сервером, и ему нужно было бы настроить его так, чтобы он не отправлял почту куда-либо, а вместо этого доставлял ее в один почтовый ящик. Я не хочу добавлять дополнительные требования к управлению, если это возможно.

Возможно, это лучшее решение, но, похоже, должен быть способ перехватить электронные письма и изменить получателя.

Кто-нибудь имел дело с этой проблемой раньше? Какие решения вы придумали?

Ответы [ 6 ]

4 голосов
/ 29 октября 2010

Примечание: мой ответ основан на использовании Maven, так что это больше о сборке, чем о чем-либо, но использование Spring позволяет мне удобно вводить значения.

Я использую свойство-заполнитель в и создаю бины, такие как:

jdbc.properties:

db.url=hostname:1521/test
db.username=awesome
db.password=password

applicationContext.xml (с использованием пространства имен контекста)

<context:property-placeholder location="classpath:jdbc.properties"/>
<bean id="yo" class="some.DataSource">
    <property name="url" value="${db.url}"/>
    <property name="username" value="${db.username}"/>
    <property name="password" value="${db.password}"/>
</bean>

Затем я храню среды в отдельных папках со значениями, специфичными для домена, например:

src/main/environments
 ++ prod
 +++++ jdbc.properties
 ++ dev
 +++++ jdbc.properties
 ++ cert
 +++++ jdbc.properties

Использование профилей Maven (из pom.xml):

<profile>
    <id>environment</id>
    <activation>
        <property>
            <name>environment</name>
        </property>
    </activation>
    <build>
        <resources>
            <resource>
                <directory>src/main/environments/${environment}</directory>
            </resource>
        </resources>

Вы можете запустить любую команду maven со свойством -Denviroment, чтобы согнуть свойства:

mvn clean -Denvironment=dev test
mvn clean -Denvironment=cert package
mvn clean -Denvironment=prod deploy

и т.д.. и любые файлы из этой папки среды копируются в целевой объект или артефакт вместе с любыми файлами src / main / resources.

2 голосов
/ 25 января 2010

В прошлом у меня было подобное требование, и я решил написать то, что я назвал EnvironmentSelectingFactoryBean (Spring, кажется, поощряет длинные имена классов ...). Это была реализация FactoryBean, которая "выбирала" один из диапазона доступных компонентов на основе текущей среды приложения.

Если я покажу вам пример XML, думаю, вы поймете идею:

<bean id="mailSender" class="com.kizoom.spring.config.EnvironmentSelectingFactoryBean">
   <property name="beanMap">
      <map>
         <entry key="test">
            <bean class="org.springframework.mail.javamail.JavaMailSenderImpl">
               <property name="host" value="${mailhost.test}"/>
            </bean>
         </entry>
         <entry key="production">
            <bean class="org.springframework.mail.javamail.JavaMailSenderImpl">
               <property name="host" value="${mailhost.production}"/>
            </bean>
         </entry>
      </map>
   </property>
</bean>

Итак, EnvironmentSelectingFactoryBean знает, работаете ли вы в «тестовом» или «производственном» режиме, выбирает соответствующий компонент из beanMap и выплевывает наш метод из FactoryBean.getObject(). Оба bean-компонента в beanMap являются реальными отправителями почты, а не заглушками, каждый с разными значениями заполнителей, но вы никогда не рискуете получить неправильный.

Код клиента будет видеть только один компонент JavaMailSender.

1 голос
/ 03 марта 2014

Лучшее решение - создать javax.mail.Session в качестве ресурса JNDI. Чем вы можете установить его по-разному для prod / test и dev . И вам не нужно беспокоиться об изменении настроек в вашем приложении, потому что только разница управляется сервером.

Для dev * и ** test Я могу порекомендовать вам хороший макет javax.mail.Session.

Проект github расширение javaMail добавляет файловый транспорт , что позволяет:

  • сохранять письма в файлы в формате text вместо их отправки
  • сохранять письма в файлы в формате mbox вместо их отправки
  • добавить информацию журнала вместо отправки электронной почты
1 голос
/ 04 декабря 2010

Другой вариант с помощью Property Placeholder - динамически загружать файл свойств в зависимости от свойства System во время выполнения.

/WEB-INF/config/myapp.${myapp.env}.properties

WEB-INF / conf будет иметь myapp.prod.properties myapp.stag.properties myapp.test.properties

Добавьте -Dmyapp.env = prod в tomcat или скрипт запуска серверов приложений.

1 голос
/ 24 января 2010

Взгляните на mock-javamail (делает то, что предлагает предыдущий ответ) или, возможно, даже более быстрое решение - поддельный SMTP-сервер, такой как Fakemail .

1 голос
/ 24 января 2010

Я вижу, что вы заявляете конкретное требование, что вы не хотите изменять какой-либо код Я все еще хотел бы предложить создать заглушку реализации JavaMailSender. Таким образом, вы можете внедрить объект-заглушку в ваш dev и тестовые сборки.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...