your programing

어노테이션 만 사용하여 (web.xml 없음) JAX-RS 애플리케이션을 설정하는 방법은 무엇입니까?

lovepro 2020. 10. 15. 08:22
반응형

어노테이션 만 사용하여 (web.xml 없음) JAX-RS 애플리케이션을 설정하는 방법은 무엇입니까?


어노테이션 만 사용하여 JAX-RS 애플리케이션을 설정할 수 있습니까? (Servlet 3.0 및 JAX-RS Jersey 1.1.0 사용)

나는 시도했지만 운이 없었습니다. 일부 사용 web.xml이 필요한 것 같습니다.


구성 A (작동하지만 web.xml 구성이 있음)

web.xml

   ...
   <servlet>
      <servlet-name>org.foo.rest.MyApplication</servlet-name>
   </servlet>
   <servlet-mapping>
       <servlet-name>org.foo.rest.MyApplication</servlet-name>
       <url-pattern>/*</url-pattern>
   </servlet-mapping>
   ...

자바

@ApplicationPath("/")
public class MyApplication extends Application {
    ...
}

구성 B (작동하지 않음, 예외 발생)

@ApplicationPath("/")
@WebServlet("/*") // <-- 
public class MyApplication extends Application {
    ...
}

후자는 응용 프로그램이 Servlet의 하위 클래스가 될 것이라고 주장하는 것 같습니다 (예외가 추측을 남기지 않음).

java.lang.ClassCastException: org.foo.rest.MyApplication cannot be cast to javax.servlet.Servlet

질문

  1. web.xml 정의가 작동했지만 주석이 작동하지 않은 이유는 무엇입니까? 차이점이 뭐야?

  2. 예를 들어 web.xml이없는 JAX-RS 애플리케이션을 사용하는 것과 같이 작동하도록하는 방법이 있습니까?


** TOMCAT 또는 JETTY를 사용하는 경우 읽으십시오! **

허용되는 답변 작동하지만 Webapp이 Glassfish 또는 Wildfly와 같은 앱 서버 및 TomEE와 같은 EE 확장이있는 서블릿 컨테이너에 배포 된 경우에만 작동합니다. 그것은 하지 않습니다 내가 여기 사용 하시겠습니까 솔루션을 찾고 대부분의 사람들이야 톰캣 같은 표준 서블릿 컨테이너에서 작동합니다.

표준 Tomcat 설치 (또는 다른 서블릿 컨테이너)를 사용하는 경우 Tomcat에 REST 구현이 포함되어 있지 않으므로 REST 구현을 포함해야합니다. Maven을 사용하는 경우 dependencies섹션에 다음 을 추가 하십시오.

<dependencies>
  <dependency>
    <groupId>org.glassfish.jersey.bundles</groupId>
    <artifactId>jaxrs-ri</artifactId>
    <version>2.13</version>
  </dependency>
  ...
</dependencies>

그런 다음 프로젝트에 애플리케이션 구성 클래스를 추가하기 만하면됩니다. 나머지 서비스에 대한 컨텍스트 경로를 설정하는 것 외에 특별한 구성이 필요하지 않은 경우 클래스가 비어있을 수 있습니다. 이 클래스가 추가되면 다음에서 아무것도 구성 할 필요가 없습니다 web.xml.

package com.domain.mypackage;
import javax.ws.rs.ApplicationPath;
import javax.ws.rs.core.Application;

@ApplicationPath("rest") // set the path to REST web services
public class ApplicationConfig extends Application {}

그런 다음 Java 클래스에서 표준 JAX-RS 어노테이션을 사용하여 웹 서비스 선언이 간단합니다.

package com.domain.mypackage;
import javax.ws.rs.Consumes;
import javax.ws.rs.Produces;
import javax.ws.rs.GET;
import javax.ws.rs.MatrixParam;
import javax.ws.rs.Path;

// It's good practice to include a version number in the path so you can have
// multiple versions deployed at once. That way consumers don't need to upgrade
// right away if things are working for them.
@Path("calc/1.0")
public class CalculatorV1_0 {
  @GET
  @Consumes("text/plain")
  @Produces("text/plain")
  @Path("addTwoNumbers")
  public String add(@MatrixParam("firstNumber") int n1, @MatrixParam("secondNumber") int n2) {
    return String.valueOf(n1 + n2);
  }
}

이것 만 있으면됩니다. Tomcat 설치가 포트 8080에서 로컬로 실행되고 WAR 파일을 컨텍스트에 배포하는 경우 다음으로 myContext이동합니다.

http://localhost:8080/myContext/rest/calc/1.0/addTwoNumbers;firstNumber=2;secondNumber=3

... 예상 된 결과를 생성해야합니다 (5).


내가해야 할 일은 이것 뿐인 것 같습니다 (서블릿 3.0 이상)

@ApplicationPath("/*")
public class MyApplication extends Application {
    ...
}

그리고 web.xml 구성이 분명히 필요하지 않았습니다 (Tomcat 7에서 시도)


Chapter 2 of the JAX-RS: Java™ API for RESTful Web Services specification describes the publication process of a JAX-RS application in Servlet environment (section 2.3.2 Servlet in the specification).

Please note that Servlet 3 environment is recommended only (section 2.3.2 Servlet, page 6):

It is RECOMMENDED that implementations support the Servlet 3 framework pluggability mechanism to enable portability between containers and to avail themselves of container-supplied class scanning facilities.

In short, if you want to use a no-web.xml approach, it's possible with a custom implementation of javax.ws.rs.core.Application that registers RESTful service resources with the javax.ws.rs.ApplicationPath annotation.

@ApplicationPath("/rest")

Although you asked specifically about Jersey you may also like to read the article Implementing RESTful services with JAX-RS and WebSphere 8.5 Liberty Profile in which I described the no-web.xml publication process for WebSphere Liberty Profile (with Apache Wink as the implementation of JAX-RS).


You need to setup the right dependencies in pom.xml

<dependency>
        <groupId>javax.servlet</groupId>
        <artifactId>javax.servlet-api</artifactId>
        <version>3.0.1</version>
        <scope>provided</scope>
    </dependency>
    <dependency>
        <groupId>org.glassfish.jersey.containers</groupId>
        <artifactId>jersey-container-servlet</artifactId>
    </dependency>

More details here: Starter example for jax-rs


As @Eran-Medan pointed out, JBoss EAP 7.1 (note without a Web Application so no servlet, I was doing it in a EJB 3.2 project) I had to add the "value" attribute as such as I was getting an exception that the value attribute was required.

This worked for me

    @ApplicationPath(value="/*")
        public class MyApplication extends Application {

            private Set singletons = new HashSet();

            public MyApplication() {
                singletons.add(new MyService());
            }

            ...
    }

Stack Trace

    Caused by: java.lang.annotation.IncompleteAnnotationException: javax.ws.rs.ApplicationPath missing element value
        at sun.reflect.annotation.AnnotationInvocationHandler.invoke(AnnotationInvocationHandler.java:80)
        at com.sun.proxy.$Proxy141.value(Unknown Source)
        ... 21 more

The previously mentioned dependencies did not work for me. From the Jersey User guide:

Jersey provides two Servlet modules. The first module is the Jersey core Servlet module that provides the core Servlet integration support and is required in any Servlet 2.5 or higher container:

<dependency>
 <groupId>org.glassfish.jersey.containers</groupId>
 <artifactId>jersey-container-servlet-core</artifactId>
</dependency>

To support additional Servlet 3.x deployment modes and asynchronous JAX-RS resource programming model, an additional Jersey module is required:

<dependency>
 <groupId>org.glassfish.jersey.containers</groupId>
 <artifactId>jersey-container-servlet</artifactId>
</dependency>

The jersey-container-servlet module depends on jersey-container-servlet-core module, therefore when it is used, it is not necessary to explicitly declare the jersey-container-servlet-core dependency.

https://jersey.github.io/documentation/latest/deployment.html#deployment.servlet.3

참고URL : https://stackoverflow.com/questions/9373081/how-to-set-up-jax-rs-application-using-annotations-only-no-web-xml

반응형