0
votes

I am trying to add Spring Integration to a REST MVC Spring app I have been writing. I am using the latest Spring 4.2.x for core, integration and mvc. The idea is to create separate application contexts as on the Dynamic FTP example. The reason why is because I can send emails from 2 separated accounts as well as listen from 2 separated accounts hence having separate application contexts as well as environment variables to aid on bean creation for each context helps a bunch.

I apologize for the newbie questions, but I am having a hard time with the manual as well as trying to figure out how to setup SMTP email configuration class without XML.

I want to have both receive and send integration channels. All email settings will be configured from enviroment variables so I have injected the enviroment: @Autowired Environment env;

I can define:

  1. A MailSender bean
  2. A MailSendingMessageHandler bean
  3. A MessageChannel for the SMTP (outbound)

Now, on XML configurations you have an outbound-channel-adapter where you wire the mail-sender bean as well as the MessageChannel

My goal is to have configurations for:

  1. Send emails.
  2. Listen to IMAP emails and process them.

For sending emails, the idea is to get from a rest endpoint, calling a service and that service is what will put a message to Integration SMTP outbound channel to send an email. Looks like, by using the MailSendingMessageHandler it will get the Integration Message and convert to a Mail Message for the MailSender. I have no idea on how to wire the MailSendingMessageHandler to the outbound channel so that an email can be send. Also I do not know how to, from my @Service class that is called by the rest endpoint how to create the messages and send them through the outbound SMTP channel so emails can be send. On one rest call I send all email recipients I want to reach. Before, each email message body is properly formatted so that I can create each Integration Message (as an email) that will be handled and converted by MailSendingMessageHandler. I have tried to find examples online without success on how to accomplish this.

Any examples you could redirect me? Thanks in advance!

So far I have for the configuration:

import java.util.Properties;

import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.context.support.PropertySourcesPlaceholderConfigurer;
import org.springframework.integration.annotation.InboundChannelAdapter;
import org.springframework.integration.config.EnableIntegration;
import org.springframework.integration.annotation.Poller;
import org.springframework.integration.channel.DirectChannel;
import org.springframework.integration.channel.QueueChannel;
import org.springframework.integration.core.MessageSource;
import org.springframework.integration.mail.MailReceiver;
import org.springframework.integration.mail.MailReceivingMessageSource;
import org.springframework.integration.mail.MailSendingMessageHandler;
import org.springframework.mail.MailMessage;
import org.springframework.mail.MailSender;
import org.springframework.mail.javamail.JavaMailSenderImpl;
import org.springframework.messaging.MessageChannel;
import org.springframework.messaging.MessagingException;


import org.springframework.core.env.Environment;

@Configuration
@EnableIntegration
public class IntegrationEmailConfig {

@Autowired 
Environment env;

@Bean
public static PropertySourcesPlaceholderConfigurer pspc() {
    return new PropertySourcesPlaceholderConfigurer();
}

@Bean
@InboundChannelAdapter(value = "emailInboundChannel", poller = @Poller(fixedDelay = "5000") )
public MailReceivingMessageSource mailMessageSource(MailReceiver imapMailReceiver) {
    return new MailReceivingMessageSource(imapMailReceiver);
}

private Properties additionalMailProperties() { 
    Properties properties = new Properties();
    if (env.containsProperty("mail.smtp.auth")) {
        properties.setProperty("mail.smtp.auth",env.getProperty("mail.smtp.auth"));
    }
    if (env.containsProperty("mail.smtp.starttls.enable")) {
        properties.setProperty("mail.smtp.starttls.enable",env.getProperty("mail.smtp.starttls.enable"));
    }
    return properties; 
} 


@Bean
public MailSender mailSender() throws Exception {
    JavaMailSenderImpl mailSender = new JavaMailSenderImpl();
    if (env.containsProperty("mail.server.host")) {
        mailSender.setHost(env.getProperty("mail.server.host"));
    } else {
        throw new Exception("Missing mail.server.host property");
    }
    if (env.containsProperty("mail.server.port")) {
        mailSender.setPort(Integer.parseInt(env.getProperty("mail.server.port")));
    } else {
        throw new Exception("Missing mail.server.port property");
    }
    if (env.containsProperty("mail.server.username")) {
        mailSender.setUsername(env.getProperty("mail.server.username"));
    } else {
        throw new Exception("Missing mail.server.username property");
    }
    if (env.containsProperty("mail.server.password")) {
        mailSender.setPassword(env.getProperty("mail.server.password"));
    } else {
        throw new Exception("Missing mail.server.password property");
    }
    mailSender.setJavaMailProperties(additionalMailProperties());
    return mailSender;
}

@Bean
public MailSendingMessageHandler mailSendingMessageHandler() throws Exception {
    MailSendingMessageHandler mailSendingMessageHandler = new MailSendingMessageHandler(mailSender());
    //mailSendingMessageHandler.setChannelResolver(channelResolver);
    return mailSendingMessageHandler;
}

/*    @Bean
public DirectChannel outboundMail() {
    DirectChannel outboundChannel = new DirectChannel();
    return outboundChannel;
}
*/    
@Bean
public MessageChannel smtpChannel() {
    return new DirectChannel();
}


/*    @Bean
@Value("${imap.url}")
public MailReceiver imapMailReceiver(String imapUrl) {
//      ImapMailReceiver imapMailReceiver = new ImapMailReceiver(imapUrl);
//      imapMailReceiver.setShouldMarkMessagesAsRead(true);
//      imapMailReceiver.setShouldDeleteMessages(false);
//      // other setters here
//      return imapMailReceiver;
    MailReceiver receiver = mock(MailReceiver.class);
    MailMessage message = mock(Message.class);
    when(message.toString()).thenReturn("Message from " + imapUrl);
    Message[] messages = new Message[] {message};
    try {
        when(receiver.receive()).thenReturn(messages);
    }
    catch (MessagingException e) {
        e.printStackTrace();
    }
    return receiver;
}*/

}

1
I have found where the XML annotations are defined by looking at the source code MailNamespaceHandler. So "outbound-channel-adapter", new MailOutboundChannelAdapterParser(). That starts to make much more sense. I will add some more code changes as I try to figure this out before getting further help here.Carlos Antunes

1 Answers

0
votes

Simply annotate the MailSendingMessageHandler bean with @ServiceActivator, the framework will register a ConsumerEndpointFactoryBean to wrap the handler. See the documentation about "Annotations on @Beans".