2010-07-29 10 views
9

Me gustaría configurar un bean de primavera (ya sea a través de la interfaz o la clase de frijoles). que puedo llamar para "comenzar" una ruta.¿Es posible iniciar una ruta en camello usando una interfaz java o un frijol?

En este sencillo ejemplo cuando llamo sayHello ("mundo") desde el código me gustaría enrutar el valor de retorno del método sayHello al punto final que lo escribirá en un archivo.

¿Alguien sabe si esto es posible o cómo hacerlo? Sé que puedo exponer esa misma interfaz a través de CXF y hacer que esto funcione, pero realmente solo quiero llamar a un método, no tener la molestia de enviar un mensaje jms o llamar a un servicio web.

public interface Hello{ 
    public String sayHello(String value); 
} 

from("bean:helloBean").to("file:/data/outbox?fileName=hello.txt"); 

Respuesta

11

Sí, puede usar el proxy/remoto en Camel para hacer esto.

Luego cuando invocas sayHello (valor) el valor se enruta a la ruta elegida. Y la respuesta de la ruta se devuelve del método sayHello.

Consulte estos enlaces
- http://camel.apache.org/spring-remoting.html
- http://camel.apache.org/hiding-middleware.html
- http://camel.apache.org/using-camelproxy.html

Capítulo 14 del camello en Acción libro cubre esto en mucho más detalle: http://www.manning.com/ibsen

+0

, gracias por responder a mi pregunta. Creo que necesito obtener una actualización de mi libro MEAP. Para el Capítulo 14 dice TBD. ¡El libro ha sido muy útil! – ScArcher2

1

tengo que mirar en Noel 'respuestas, pero para una interfaz de usuario rápida y sucia fui con un enfoque diferente.

Estaba usando Spring MVC 3.1.X y tengo una consola de administración para varios elementos en mi aplicación. Escribí un Controlador para mostrar las rutas y sus estados, así como los enlaces provistos para iniciar y detener las rutas según sea necesario. Aquí está una parte del código:

@Controller 
public class CamelController { 
    private static final Log LOG = LogFactory.getLog(CamelController.class); 

    @Autowired 
    @Qualifier("myCamelContextID") 
    private CamelContext camelContext; 

    @RequestMapping(value = "/dashboard", method = RequestMethod.GET) 
    public String dashboard(Model model) { 
     if (LOG.isDebugEnabled()) { 
      LOG.debug("camel context is suspended : " + camelContext.isSuspended()); 
     } 

     List<Route> routes = camelContext.getRoutes(); 
     List<RouteStatus> routeStatuses = new ArrayList<RouteStatus>(); 
     for (Route r : routes) { 
      RouteStatus rs = new RouteStatus(); 
      rs.setId(r.getId()); 
      rs.setServiceStatus(camelContext.getRouteStatus(r.getId())); 
      routeStatuses.add(rs); 
     } 

     model.addAttribute("routeStatuses", routeStatuses); 

     return "dashboard"; 
    } 

    @RequestMapping(value = "/dashboard/{routeId}/start", method = RequestMethod.GET) 
    public String startRoute(@PathVariable String routeId) { 
     try { 
      camelContext.startRoute(routeId); 
      if (LOG.isDebugEnabled()) { 
       LOG.debug("camel context is starting route [" + routeId + "]"); 
      } 
     } catch (Exception e) { 
      LOG.error("failed to start camel context [" + camelContext + "]"); 
     } 

     return "redirect:/dashboard"; 
    } 

    @RequestMapping(value = "/dashboard/{routeId}/stop", method = RequestMethod.GET) 
    public String stopRoute(@PathVariable String routeId) { 
     try { 
      camelContext.stopRoute(routeId); 
      if (LOG.isDebugEnabled()) { 
       LOG.debug("camel context is stopping route [" + routeId + "]"); 
      } 
     } catch (Exception e) { 
      LOG.error("failed to stop camel context [" + camelContext + "]"); 
     } 
     return "redirect:/dashboard"; 
     } 
    } 
} 

Hay un pequeño POJO hice para ir con ella:

public class RouteStatus { 
    private String id; 
    private ServiceStatus serviceStatus; 

    public String getId() { 
     return id; 
    } 

    public void setId(String id) { 
     this.id = id; 
    } 

    public ServiceStatus getServiceStatus() { 
     return serviceStatus; 
    } 

    public void setServiceStatus(ServiceStatus serviceStatus) { 
     this.serviceStatus = serviceStatus; 
    } 
} 
9

Puede utilizar ProducerTemplate:

import org.apache.camel.Produce; 
import org.apache.camel.ProducerTemplate; 
import org.springframework.stereotype.Component; 

import java.util.concurrent.ExecutionException; 
import java.util.concurrent.Future; 

@Component 
public class HelloImpl implements Hello { 

    @Produce(uri = "direct:start") 
    private ProducerTemplate template; 

    @Override 
    public Object sayHello(String value) throws ExecutionException, InterruptedException { 
     Future future = template.asyncSendBody(template.getDefaultEndpoint(), value); 
     return future.get(); 
    } 
} 

y su ruta de camellos debería parecerse :

<beans xmlns="http://www.springframework.org/schema/beans" 
     xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" 
     xmlns:camel="http://camel.apache.org/schema/spring" 
     xmlns:context="http://www.springframework.org/schema/context" 
     xsi:schemaLocation=" 
     http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd 
     http://camel.apache.org/schema/spring http://camel.apache.org/schema/spring/camel-spring.xsd 
     http://www.springframework.org/schema/context http://www.springframework.org/schema/context/spring-context.xsd"> 

    <context:component-scan base-package="com.mycompany.camel"/> 

    <camelContext xmlns="http://camel.apache.org/schema/spring"> 
     <route> 
      <from uri="direct:start"/> 
      <to uri="log:com.mycompany.camel?level=DEBUG"/> 
     </route> 
    </camelContext> 

</beans> 
0

Desde mis rutas fueron componentes de muelles usando CamelConfiguration. Lo seguí para usar mi interfaz en las rutas de camellos.

@Component 
public class SomeRoute extends RouteBuilder { 

    @Autowired 
    private ApplicationContext applicationContext; 

    @Override 
    public void configure() throws Exception { 
     from("direct:someroute") 
     .bean(applicationContext.getBean(SomeInterface.class).getClass(), "someAbstractMethod") 
     .to("direct:otherroute"); 
    } 
} 

Este fue el caso muy sencillo, si tiene varios granos utilizando misma interfaz o clase abstracta es probable que tenga que hacer un poco de lógica antes de usar .getClass() de frijol.

0

Ninguna de las otras respuestas funcionó para mí, todas fueron construidas y fueron válidas, pero las rutas no se activaron.

Esta es la solución que terminé usando:

import org.apache.camel.Handler; 

public class Hello{ 

    @Produce(uri = "direct:start") 
    private ProducerTemplate producer; 

    @Handler 
    public void sayHello() { 
     producer.sendBody("hello") 
    } 
} 

from("timer:hubspotContacts?repeatCount=1").bean(Hello.class); 
from("direct:start").to("log:hello"); 
  • timer El componente de la primera ruta fue la parte que falta clave para mí. Con repeatCount=1, se dispara exactamente una vez, al iniciarse y hace que se llame al método Bean. También es compatible con una tasa de llamadas o un retraso si necesita que se llame al método varias veces.
  • las anotaciones @Handler sirve como marcador por lo que el nombre del método no tiene que ser explícita en la configuración de rutas
  • el componente direct conecta el productor con sus consumidores
Cuestiones relacionadas