0

I'm experimenting RESTful Web Services with Spring, my starting project is Spring's gs-rest-service. The project works fine, when I hit http://localhost:8080/greeting I get {"id":1,"content":"Hello, World!"}.

The problem is when I added dependencies to spring-data-rest-core and spring-data-rest-webmvc in my pom.xml the application does not work any more. When I hit http://localhost:8080/greeting I get the following error:

Whitelabel Error Page
This application has no explicit mapping for /error, so you are seeing this as a fallback.
Tue Aug 12 12:27:28 CEST 2014
There was an unexpected error (type=Not Acceptable, status=406).
Could not find acceptable representation

When I remove the depndencies the application works fine again, what is causing this problem? Here is my pom.xml:

<project xmlns="http://maven.apache.org/POM/4.0.0"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/maven-v4_0_0.xsd">
<modelVersion>4.0.0</modelVersion>

<groupId>org.springframework</groupId>
<artifactId>gs-rest-service</artifactId>
<version>0.1.0</version>
<parent>
    <groupId>org.springframework.boot</groupId>
    <artifactId>spring-boot-starter-parent</artifactId>
    <version>1.1.5.RELEASE</version>
</parent>

<packaging>war</packaging>

<properties>
    <spring.version>4.0.5.RELEASE</spring.version>
    <spring.boot.version>1.1.4.RELEASE</spring.boot.version>
    <jdk.version>1.7</jdk.version>
    <jetty.version>8.1.8.v20121106</jetty.version>
    <spring.data.rest.version>2.1.2.RELEASE</spring.data.rest.version>
</properties>

<dependencies>
    <dependency>
        <groupId>org.springframework.boot</groupId>
        <artifactId>spring-boot-starter-web</artifactId>
        <version>${spring.boot.version}</version>
    </dependency>
    <dependency>
        <groupId>org.springframework.data</groupId>
        <artifactId>spring-data-rest-core</artifactId>
        <version>${spring.data.rest.version}</version>
    </dependency>

    <dependency>
        <groupId>org.springframework.data</groupId>
        <artifactId>spring-data-rest-webmvc</artifactId>
        <version>${spring.data.rest.version}</version>
    </dependency>

    <dependency>
        <groupId>junit</groupId>
        <artifactId>junit</artifactId>
        <version>3.8.1</version>
        <scope>test</scope>
    </dependency>
</dependencies>

<build>

    <plugins>
        <plugin>
            <groupId>org.apache.maven.plugins</groupId>
            <artifactId>maven-compiler-plugin</artifactId>
            <version>3.0</version>
            <configuration>
                <source>${jdk.version}</source>
                <target>${jdk.version}</target>
            </configuration>
        </plugin>

        <plugin>                
            <groupId>org.mortbay.jetty</groupId>                
            <artifactId>jetty-maven-plugin</artifactId>             
            <version>${jetty.version}</version>             
        </plugin>
    </plugins>
</build>
</project>
bachr
  • 5,780
  • 12
  • 57
  • 92

3 Answers3

2

Spring Boot ships a dedicated starter for Spring Data REST:

<dependency>
  <groupId>org.springframework.boot</groupId>
  <artifactId>spring-boot-starter-data-rest</artifactId>
</dependency>
Oliver Drotbohm
  • 80,157
  • 18
  • 225
  • 211
  • When I add this dependency I have a `Could not autowire field: private final java.util.List org.springframework.boot.autoconfigure.web.HttpMessageConvertersAutoConfiguration.converters; nested exception is java.lang.NoClassDefFoundError: org/codehaus/jackson/JsonProcessingException`. It sounds I still have to add dependencies to Jackson as below! – bachr Aug 13 '14 at 09:04
  • Looks like you have some mismatching versions as the class you mention only has a dependency on `com.jackson`. Can you post the whole stacktrace? (And also see my answer). – M. Deinum Aug 13 '14 at 10:35
2

You are making things to complex in your dependencies and your configuration. As @OliverGierke already mentioned use the following starter instead of individual dependencies.

<dependency>
    <groupId>org.springframework.boot</groupId>
    <artifactId>spring-boot-starter-data-rest</artifactId>
</dependency>

Also you are already using the spring-boot-starter-parent so yuo don't need spring boot versions are some of the additional properties you configured. Instead of jdk.version use java.version and that is all. Leaving you with the following pom. (Which also adds the spring-boot plugin).

<project xmlns="http://maven.apache.org/POM/4.0.0"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/maven-v4_0_0.xsd">
    <modelVersion>4.0.0</modelVersion>

    <groupId>org.springframework</groupId>
    <artifactId>gs-rest-service</artifactId>
    <version>0.1.0</version>

    <parent>
        <groupId>org.springframework.boot</groupId>
        <artifactId>spring-boot-starter-parent</artifactId>
        <version>1.1.5.RELEASE</version>
    </parent>

    <packaging>jar</packaging>

    <properties>
        <java.version>1.7</java.version>
    </properties>

    <dependencies>
        <dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-starter-web</artifactId>
        </dependency>
        <dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-starter-data-rest</artifactId>
        </dependency>
        <dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-starter-test</artifactId>
            <scope>test</scope>
        </dependency>
    </dependencies>

    <build>
        <plugins>
            <plugin>
                <groupId>org.springframework.boot</groupId>
                <artifactId>spring-boot-maven-plugin</artifactId>
            </plugin>
        </plugins>
    </build>
</project>

This wil create an executable jar which you can run with java -jar <your-jar-name-here>.jar. This should also have all the dependencies you need including jackson for your JSON (un)marshalling, this is a dependency of spring-boot-starter-web.

Spring Boot with @EnableAutoConfiguration will detect Spring MVC and Jackson and do the proper configuration for it. The same for Spring Data REST. YOu shouldn't need to mess around with xml (or a war archive) yourself.

I removed Jetty if you want to use it check the Spring Boot reference guide on how to do this.

M. Deinum
  • 115,695
  • 22
  • 220
  • 224
0

It turns out that I have to add dependencies to Jackson:

<dependency>
    <groupId>org.codehaus.jackson</groupId>
    <artifactId>jackson-core-asl</artifactId>
    <version>1.9.13</version>
</dependency>
<dependency>
    <groupId>org.codehaus.jackson</groupId>
    <artifactId>jackson-mapper-asl</artifactId>
    <version>1.9.13</version>
</dependency>

And declare a the following beans as described here Spring MVC - HttpMediaTypeNotAcceptableException:

<context:annotation-config/>

<bean id="jacksonMessageConverter" class="org.springframework.http.converter.json.MappingJacksonHttpMessageConverter">
</bean>
<bean class="org.springframework.web.servlet.mvc.annotation.AnnotationMethodHandlerAdapter">
    <property name="messageConverters">
        <list>
            <ref bean="jacksonMessageConverter"/>
        </list>
    </property>
</bean>

Then, add the beans.xml to the Application.java with @ImportResource("beans.xml").

Community
  • 1
  • 1
bachr
  • 5,780
  • 12
  • 57
  • 92
  • I suggest following the suggestion made by the first answer. Add the starter and use spring boots autoconfigure features to detect Spring Data REST and let it configure itself. – M. Deinum Aug 13 '14 at 06:27
  • `@EnableAutoConfiguration` is already added as in the original [gs-rest-service](https://github.com/spring-guides/gs-rest-service) project. – bachr Aug 13 '14 at 09:08
  • 1
    Then you don't need the `AnnotationMethodHandlerAdapter` which is also kind of deprecated and replaced by `RequestMethodHandlerAdapter` which is registered automatically by `@EnableWebMvc` which is enabled by default if spring boot detects Sprnig MVC. Jackson is autconfigured if that is detected to, so basically all you have done isn't needed. (Also you probably want to use jackson2 for which Spring Boot already has the dependencies configured). – M. Deinum Aug 13 '14 at 09:11