@RequestBody没有处理Rest服务

时间:2016-03-03 17:12:36

标签: java angularjs json spring rest

我正在使用Spring开发一个使用AngularJS和WildFly的Web应用程序。

我的问题是我疯了,因为注释@requestBody似乎工作不对。

这是我的服务:

@ResponseBody
@RequestMapping(value = "/keyuser", method = RequestMethod.POST,
  consumes = "application/json")
public KeyProfileUserSummary updateEmployee(@RequestBody KeyProfileUserSummary keyUser) {
return null;
}

这是我的对象KeyProfileUserSummary:

的成员
private Integer id;
private String login;
private String password;
private String firstname;
private String lastname;
private UserRole userRole;

我不知道发生了什么,但我已经用其他类型的对象测试了这个服务,它运行得很好,但是当定义KeyProfileUserSummary它不能正常工作时,我得到ERROR 400 BAD REQUEST。我已经测试过将@RequestBody设置为“Object”,所以至少我可以看到即将发生的事情,从我的前端,我得到以下内容:

{id=3, login=aa, password=a, firstname=Martin, lastname=Müller, userRole=ROLE_USER} 

UserRole是一个枚举。重要的是要清楚KeyProfileUserSummary只是KeyProfileUser的摘要版本,但是由于我得到了响应的所有链接元素,我决定发送这个更轻的类。使用KeyProfileUser进行测试工作得很好,我在Angular端获得JSON对象并可以将其发回。

在Angular方面,我没有对该对象做任何事情。只需在列表中接收它,当按下编辑按钮时,只需返回列表中的元素即可。这就是我发送它的方式:

res = $http.post("url.../keyuser", user);

问题是我的一切都与KeyProfileUser完美配合,但由于数据库可以变得非常庞大并且引用相当多,我决定切换到这个更轻的类,但现在我只得到这个ERROR 400 BAD REQUEST ......我正要挂起自己:P

感谢您的帮助!

4 个答案:

答案 0 :(得分:2)

好的,最后我找到了解决方案。

在我的KeyProfileUserSummary中,我只有一个构造函数正在使用KeyProfileUser并将属性设置为摘要版本:

public KeyProfileUserSummary(KeyProfileUser keyProfileUser) {
  this.id = keyProfileUser.getId();
  this.login = keyProfileUser.getLogin();
  this.password = keyProfileUser.getPassword();
  this.firstname = keyProfileUser.getPerson().getFirstname();
  this.lastname = keyProfileUser.getPerson().getLastname();
  this.userRole = keyProfileUser.getUserRole();
}

显然,在调度程序servlet的第993行设置断点(感谢@Clemens Eberwein的提示)我意识到从JSON对象解析时,Jackson解析器需要一个空的构造函数!所以添加它解决了它并且完美地工作。

注意:对于KeyProfileUser,它完全正常,因为我们有hibernate的注释@Entity,因此自动创建了空构造函数。

答案 1 :(得分:1)

尝试一下..可能对你有用..

$http({
    method: 'POST',
    url: 'http://localhost:8080/keyuser',
    data: user,
    headers: {
        'Content-Type': 'application/json',
        'Accept': 'application/json'
    }}).then(function(result) {
           console.log(result);
       }, function(error) {
           console.log(error);
       });

答案 2 :(得分:0)

如果我猜测,杰克逊无法反序列化/序列化您的对象。这是我制作的一个工具:

import java.io.IOException;
import java.nio.charset.Charset;

import org.springframework.http.MediaType;

import com.fasterxml.jackson.annotation.JsonInclude.Include;
import com.fasterxml.jackson.core.JsonParseException;
import com.fasterxml.jackson.databind.JsonMappingException;
import com.fasterxml.jackson.databind.JsonSerializer;
import com.fasterxml.jackson.databind.ObjectMapper;
import com.fasterxml.jackson.databind.module.SimpleModule;

public class SerializeDeserializeUtil {

    public static final MediaType APPLICATION_JSON_UTF8 = new MediaType(
            MediaType.APPLICATION_JSON.getType(),
            MediaType.APPLICATION_JSON.getSubtype(), Charset.forName("utf8"));

    public static byte[] convertObjectToJsonBytes(Object object)
            throws IOException {
        ObjectMapper mapper = new ObjectMapper();
        mapper.setSerializationInclusion(Include.NON_NULL);

        return mapper.writeValueAsBytes(object);

    }

    public static <T> T deserializeObject(String jsonRepresentation,
            Class<T> clazz) throws JsonParseException, JsonMappingException,
            IOException {

        ObjectMapper mapper = new ObjectMapper();

        Object obj = mapper.readValue(jsonRepresentation.getBytes(), clazz);

        return clazz.cast(obj);
    }


    @SuppressWarnings({ "unchecked", "rawtypes" })
    public static byte[] convertObjectToJsonBytesWithCustomSerializer(
            Object object, JsonSerializer serializer, Class clazz)
            throws IOException {

        ObjectMapper mapper = new ObjectMapper();

        SimpleModule sm = new SimpleModule();
        sm.addSerializer(clazz, serializer);

        mapper.registerModule(sm);
        mapper.setSerializationInclusion(Include.NON_NULL);

        return mapper.writeValueAsBytes(object);

    }

}

尝试创建测试只是为了序列化和反序列化目标。创建一个KeyProfileUserSummary对象并尝试反序列化/序列化,看看杰克逊是否抱怨。

更简单的方法是启用DEBUG日志记录并检查日志文件,默认情况下您不会看到此类错误

希望它有所帮助。

答案 3 :(得分:0)

如果为“org.springframework.web”添加DEBUG日志记录org.springframework.web.servlet.DispatcherServlet应该为您提供导致“400 Bad Request”错误的详细信息。

可以找到有关Wildfly日志记录配置的详细信息here

基于你的KeyProfileUserSummary类,我猜问题是UserRole对象,在上面的例子中只是userRole=ROLE_USER。由于它是一个对象,它应该用花括号括起来,并且必须设置属性名称。例如

之类的东西
userRole = { name = "ROLE_USER"}

如果是enum,this答案可能会有帮助