300.7. sample
Camel 2.7 부터 Spring 웹 애플리케이션에서 Servlet 을 사용하는 것이 더 쉽습니다. 자세한 내용은 Servlet Tomcat 예제 를 참조하십시오.
이 샘플에서는 http://localhost:8080/camel/services/hello 에서 HTTP 서비스를 노출하는 경로를 정의합니다.
먼저 일반 웹 컨테이너 또는 OSGi 서비스를 통해 CamelHttpTransportServlet 을 게시해야 합니다. Web.xml
파일을 사용하여 CamelHttpTransportServlet 을 다음과 같이 게시합니다.
<web-app> <servlet> <servlet-name>CamelServlet</servlet-name> <display-name>Camel Http Transport Servlet</display-name> <servlet-class>org.apache.camel.component.servlet.CamelHttpTransportServlet</servlet-class> </servlet> <servlet-mapping> <servlet-name>CamelServlet</servlet-name> <url-pattern>/services/*</url-pattern> </servlet-mapping> </web-app>
그런 다음 다음과 같이 경로를 정의할 수 있습니다.
from("servlet:hello?matchOnUriPrefix=true").process(new Processor() { public void process(Exchange exchange) throws Exception { String contentType = exchange.getIn().getHeader(Exchange.CONTENT_TYPE, String.class); String path = exchange.getIn().getHeader(Exchange.HTTP_URI, String.class); path = path.substring(path.lastIndexOf("/")); assertEquals("Get a wrong content type", CONTENT_TYPE, contentType); // assert camel http header String charsetEncoding = exchange.getIn().getHeader(Exchange.HTTP_CHARACTER_ENCODING, String.class); assertEquals("Get a wrong charset name from the message heaer", "UTF-8", charsetEncoding); // assert exchange charset assertEquals("Get a wrong charset naem from the exchange property", "UTF-8", exchange.getProperty(Exchange.CHARSET_NAME)); exchange.getOut().setHeader(Exchange.CONTENT_TYPE, contentType + "; charset=UTF-8"); exchange.getOut().setHeader("PATH", path); exchange.getOut().setBody("<b>Hello World</b>"); } });
camel-servlet 끝점의 상대 경로 지정
HTTP 전송에 게시된 서블릿과 바인딩하고 서블릿의 애플리케이션 컨텍스트 경로를 모르는 경우 camel-servlet
끝점은 상대 경로를 사용하여 끝점의 URL을 지정합니다. 클라이언트는 서블릿 게시 주소( ("http://localhost:8080/camel/services") + RELATIVE_PATH("/hello")
를 통해 camel-servlet
엔드포인트에 액세스할 수 있습니다.
300.7.1. Spring 3.x를 사용할 때 샘플
Servlet Tomcat 예제 를 참조하십시오.
300.7.2. Spring 2.x를 사용할 때 샘플
Camel/Spring 애플리케이션에서 Servlet 구성 요소를 사용하는 경우 서블릿 구성 요소가 시작된 후 Spring ApplicationContext를 로드해야 하는 경우가 많습니다. 이 작업은 ContextLoaderListener
대신 Spring의 ContextLoaderServlet
을 사용하여 수행할 수 있습니다. 이 경우 다음과 같은 CamelHttpTransportServlet 후 ContextLoaderServlet
을 시작해야 합니다.
<web-app> <servlet> <servlet-name>CamelServlet</servlet-name> <servlet-class> org.apache.camel.component.servlet.CamelHttpTransportServlet </servlet-class> <load-on-startup>1</load-on-startup> </servlet> <servlet> <servlet-name>SpringApplicationContext</servlet-name> <servlet-class> org.springframework.web.context.ContextLoaderServlet </servlet-class> <load-on-startup>2</load-on-startup> </servlet> <web-app>
300.7.3. OSGi를 사용할 때 샘플
Camel 2.6.0 에서 다음과 같이 CamelHttpTransportServlet 을 OSGi 서비스로 게시할 수 있습니다.
<blueprint xmlns="http://www.osgi.org/xmlns/blueprint/v1.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation=" http://www.osgi.org/xmlns/blueprint/v1.0.0 https://www.osgi.org/xmlns/blueprint/v1.0.0/blueprint.xsd"> <bean id="camelServlet" class="org.apache.camel.component.servlet.CamelHttpTransportServlet" /> <!-- Enlist it in OSGi service registry. This will cause two things: 1) As the pax web whiteboard extender is running the CamelServlet will be registered with the OSGi HTTP Service 2) It will trigger the HttpRegistry in other bundles so the servlet is made known there too --> <service ref="camelServlet"> <interfaces> <value>javax.servlet.Servlet</value> <value>org.apache.camel.http.common.CamelServlet</value> </interfaces> <service-properties> <entry key="alias" value="/camel/services" /> <entry key="matchOnUriPrefix" value="true" /> <entry key="servlet-name" value="CamelServlet" /> </service-properties> </service> </blueprint>
그런 다음 Camel 경로에서 이 서비스를 다음과 같이 사용합니다.
<blueprint xmlns="http://www.osgi.org/xmlns/blueprint/v1.0.0" xmlns:ext="http://aries.apache.org/blueprint/xmlns/blueprint-ext/v1.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation=" http://www.osgi.org/xmlns/blueprint/v1.0.0 https://www.osgi.org/xmlns/blueprint/v1.0.0/blueprint.xsd"> <reference id="servletref" ext:proxy-method="classes" interface="org.apache.camel.http.common.CamelServlet"> <reference-listener ref="httpRegistry" bind-method="register" unbind-method="unregister" /> </reference> <bean id="httpRegistry" class="org.apache.camel.component.servlet.DefaultHttpRegistry" /> <bean id="servlet" class="org.apache.camel.component.servlet.ServletComponent"> <property name="httpRegistry" ref="httpRegistry" /> </bean> <bean id="servletProcessor" class="org.apache.camel.example.servlet.ServletProcessor" /> <camelContext xmlns="http://camel.apache.org/schema/blueprint"> <route> <!-- Notice how we can use the servlet scheme which is that reference above --> <from uri="servlet://hello" /> <process ref="servletProcessor" /> </route> </camelContext> </blueprint>
Camel 2.6 이전 버전의 경우 활성화
기를 사용하여 OSGi 플랫폼에 CamelHttpTransportServlet 을 게시할 수 있습니다.
import java.util.Dictionary; import java.util.Hashtable; import org.apache.camel.component.servlet.CamelHttpTransportServlet; import org.osgi.framework.BundleActivator; import org.osgi.framework.BundleContext; import org.osgi.framework.ServiceReference; import org.osgi.service.http.HttpContext; import org.osgi.service.http.HttpService; import org.slf4j.Logger; import org.slf4j.LoggerFactory; import org.springframework.osgi.context.BundleContextAware; public final class ServletActivator implements BundleActivator, BundleContextAware { private static final Logger LOG = LoggerFactory.getLogger(ServletActivator.class); private static boolean registerService; /** * HttpService reference. */ private ServiceReference<?> httpServiceRef; /** * Called when the OSGi framework starts our bundle */ public void start(BundleContext bc) throws Exception { registerServlet(bc); } /** * Called when the OSGi framework stops our bundle */ public void stop(BundleContext bc) throws Exception { if (httpServiceRef != null) { bc.ungetService(httpServiceRef); httpServiceRef = null; } } protected void registerServlet(BundleContext bundleContext) throws Exception { httpServiceRef = bundleContext.getServiceReference(HttpService.class.getName()); if (httpServiceRef != null && !registerService) { LOG.info("Register the servlet service"); final HttpService httpService = (HttpService)bundleContext.getService(httpServiceRef); if (httpService != null) { // create a default context to share between registrations final HttpContext httpContext = httpService.createDefaultHttpContext(); // register the hello world servlet final Dictionary<String, String> initParams = new Hashtable<String, String>(); initParams.put("matchOnUriPrefix", "false"); initParams.put("servlet-name", "CamelServlet"); httpService.registerServlet("/camel/services", // alias new CamelHttpTransportServlet(), // register servlet initParams, // init params httpContext // http context ); registerService = true; } } } public void setBundleContext(BundleContext bc) { try { registerServlet(bc); } catch (Exception e) { LOG.error("Cannot register the servlet, the reason is " + e); } } }
300.7.4. Spring-Boot 사용
Camel 2.19.0 이후부터 camel-servlet-starter 라이브러리는 /camel/*
컨텍스트 경로에 있는 나머지 모든 엔드포인트를 자동으로 바인딩합니다. 다음 표에는 camel-servlet-starter 라이브러리에서 사용할 수 있는 추가 구성 속성이 요약되어 있습니다. Camel 서블릿의 자동 매핑도 비활성화할 수 있습니다.
Spring-Boot 속성 | Default | 설명 |
---|---|---|
camel.component.servlet.mapping.enabled |
| 서블릿 구성 요소를 Spring 웹 컨텍스트에 자동 매핑 가능 |
camel.component.servlet.mapping.context-path |
| 자동 매핑을 위해 서블릿 구성 요소에서 사용하는 컨텍스트 경로 |
camel.component.servlet.mapping.servlet-name |
| Camel 서블릿의 이름 |