2015-11-09 9 views
5

Nel mio progetto creato da SpringBoot,multipla annotazione @SpringBootApplication in un progetto

Ho aggiunto 2 classi principali con @SpringBootApplication.

Perché se utilizzo STS posso scegliere un'applicazione principale quando si avvia il debug.

Ma ho scoperto che mentre SpringDemoApplication è attivo, anche RabbitMQApplication è in esecuzione.

È questa specifica? lavorare in modo appropriato?

Ecco questo è di esempio per riprodurre https://github.com/MariMurotani/SpringDemo/tree/6_rabbitMQ

enter image description here

SpringDemoApplication

package demo; 

import org.springframework.boot.SpringApplication; 
import org.springframework.boot.autoconfigure.SpringBootApplication; 
import org.springframework.context.ApplicationContext; 

@SpringBootApplication 
public class SpringDemoApplication { 

public static void main(String[] args) { 

     SpringApplication application = new SpringApplication(SpringDemoApplication.class); 
     ApplicationContext context = application.run(args); 

    } 
} 

RabbitMQApplication

package demo; 

import java.util.Date; 

import org.codehaus.jackson.map.ObjectMapper; 
import org.springframework.amqp.core.Binding; 
import org.springframework.amqp.core.BindingBuilder; 
import org.springframework.amqp.core.Queue; 
import org.springframework.amqp.core.TopicExchange; 
import org.springframework.amqp.rabbit.connection.ConnectionFactory; 
import org.springframework.amqp.rabbit.core.RabbitTemplate; 
import org.springframework.amqp.rabbit.listener.SimpleMessageListenerContainer; 
import org.springframework.beans.factory.annotation.Autowired; 
import org.springframework.boot.CommandLineRunner; 
import org.springframework.boot.SpringApplication; 
import org.springframework.boot.autoconfigure.SpringBootApplication; 
import org.springframework.context.ApplicationContext; 
import org.springframework.context.annotation.Bean; 

import demo.configs.Const; 
import demo.dto.Mail; 

@SpringBootApplication 
public class RabbitMQApplication implements CommandLineRunner { 

@Autowired 
ApplicationContext context; 


@Autowired 
RabbitTemplate rabbitTemplate; 

@Bean 
Queue queue() { 
    return new Queue(Const.RabbitMQMessageQue, false); 
} 

@Bean 
TopicExchange exchange() { 
    return new TopicExchange("spring-boot-exchange"); 
} 

@Bean 
Binding binding(Queue queue, TopicExchange exchange) { 
    return BindingBuilder.bind(queue).to(exchange).with(Const.RabbitMQMessageQue); 
} 

@Bean 
SimpleMessageListenerContainer container(ConnectionFactory connectionFactory) { 
    SimpleMessageListenerContainer container = new SimpleMessageListenerContainer(); 
    container.setConnectionFactory(connectionFactory); 
    container.setQueueNames(Const.RabbitMQMessageQue); 
    //container.setMessageListener(listenerAdapter); 
    return container; 
} 

/* 
For asyncronized receiving 

@Bean 
Receiver receiver() { 
    return new Receiver(); 
} 

@Bean 
MessageListenerAdapter listenerAdapter(Receiver receiver) { 
    return new MessageListenerAdapter(receiver, "receiveMessage"); 
}*/ 

public static void main(String[] args) throws InterruptedException { 
    SpringApplication.run(RabbitMQApplication.class, args); 
} 

@Override 
public void run(String... args) throws Exception { 
    System.out.println("Waiting five seconds..."); 

    while(0 < 1){ 
     for(int i = 0 ; i < 5 ; i++){ 
      String object = (String)rabbitTemplate.receiveAndConvert(Const.RabbitMQMessageQue); 
      if(object != null){ 
       try{ 
        System.out.println(new Date().toGMTString() + ": " + object); 
        ObjectMapper mapper = new ObjectMapper(); 
        Mail mail = mapper.readValue(object, Mail.class); 
        System.out.println(mail.getToAddress() + " , " + mail.getStrContent()); 
       }catch(Exception e){ 
        System.out.println(e.getMessage()); 
       } 
      } 
     } 
     Thread.sleep(10000); 
    } 
} 
} 

risposta

9

L'annotazione @SpringBootApplication è un'annotazione di scelta rapida per @Configuration, @EnableAutoConfiguration e @ComponentScan.

http://docs.spring.io/spring-boot/docs/current/reference/html/using-boot-using-springbootapplication-annotation.html

Il comportamento predefinito di @ComponentScan è quello di cercare @Configuration e @Component classi all'interno dello stesso package e tutte le sotto-pacchetti della classe annotata. Dal momento che tutte le tue classi sono nello stesso pacchetto, quando inizi una di esse Spring troverà le altre e le tratterà come classi @Configuration e registreranno i loro bean, ecc.

Quindi sì, questo è il comportamento previsto dato il tuo progetto impostare. Metti ogni classe @SpringBootApplication in un sotto pacchetto separato se non vuoi che ciò accada per il test locale. Se questo si sposta oltre una demo a un certo punto, probabilmente vorrai creare una configurazione migliore (sottoprogetti per ogni @SpringBootApplication).