Можно ли начать маршрут верблюда, используя интерфейс Java или боб? - PullRequest
13 голосов
/ 29 июля 2010

Я бы хотел настроить бин пружины (либо через интерфейс, либо через класс бина). что я могу позвонить, чтобы «запустить» маршрут.

В этом простом примере, когда я вызываю sayHello ("мир") из кода, я бы хотел, чтобы он направлял возвращаемое значение метода sayHello конечной точке, которая запишет его в файл.

Кто-нибудь знает, возможно ли это или как это сделать? Я знаю, что могу использовать тот же интерфейс через CXF и заставить это работать, но я действительно просто хочу вызвать метод, а не пытаться отправить сообщение jms или вызвать веб-сервис.

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

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

Ответы [ 5 ]

12 голосов
/ 28 февраля 2013

Вы можете использовать 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();
    }
}

и ваш верблюжий маршрут должен выглядеть так:

<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>
10 голосов
/ 30 июля 2010

Да, вы можете использовать прокси / удаленное взаимодействие в Camel для этого.

Затем, когда вы вызываете sayHello (значение), значение направляется на выбранный маршрут.А ответ от маршрута возвращается из метода sayHello.

Смотрите эти ссылки- http://camel.apache.org/spring-remoting.html- http://camel.apache.org/hiding-middleware.html- http://camel.apache.org/using-camelproxy.html

Глава 14 книги «Верблюд в действии» описывает это гораздо подробнее: http://www.manning.com/ibsen

2 голосов
/ 24 февраля 2017

Ни один из других ответов не работал для меня, все они построены и были действительны, но маршруты не сработали.

Это решение, которое я использовал в итоге:

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 с первого маршрута был для меня ключевой недостающей частью. С repeatCount=1 он запускается ровно один раз при запуске и вызывает метод bean. Он также поддерживает скорость вызова или задержку, если необходимо, чтобы метод вызывался несколько раз.
  • аннотации @Handler служат маркером, поэтому нет необходимости указывать имя метода в конфигурации маршрута
  • компонент direct связывает производителя с потребителями
1 голос
/ 08 января 2013

Мне нужно посмотреть ответы Клауса, но для быстрого и грязного интерфейса я выбрал другой подход.

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

@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";
        }
    }
}

Я сделал несколько POJO для этого:

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;
    }
}
0 голосов
/ 16 октября 2016

Так как мои маршруты были компонентами пружины с использованием CamelConfiguration . Я сделал следующее, чтобы использовать мой интерфейс на верблюжьих маршрутах.

@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");
    }
}

Это был очень простой случай, если у вас есть несколько бинов, использующих один и тот же интерфейс или абстрактный класс, вам, вероятно, придется сделать некоторую логику, прежде чем использовать .getClass() в бине.

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