我是Spring Data REST项目的新手,我正在尝试创建我的第一个RESTful服务。任务很简单,但我被卡住了。
我想使用RESTful API对存储在嵌入式数据库中的用户数据执行CRUD操作。
但是我不知道如何让Spring框架将birthData处理为“1999-12-15”并将其存储为LocalDate。@JsonFormat注解没有帮助。
目前我得到的错误:
HTTP/1.1 400
Content-Type: application/hal+json;charset=UTF-8
Transfer-Encoding: chunked
Date: Thu, 24 Aug 2017 13:36:51 GMT
Connection: close
{"cause":{"cause":null,"message":"Can not construct instance of java.time.LocalDate:
no String-argument constructor/factory method to deserialize from String value ('1999-10-10')\n
at [Source: org.apache.catalina.connector.CoyoteInputStream@4ee2a60e;
line: 1, column: 65] (through reference chain: ru.zavanton.entities.User[\"birthDate\"])"},
"message":"JSON parse error: Can not construct instance of java.time.LocalDate:
no String-argument constructor/factory method to deserialize from String value ('1999-10-10'); nested exception is com.fasterxml.jackson.databind.JsonMappingException:
Can not construct instance of java.time.LocalDate: no String-argument constructor/factory method to deserialize from String value ('1999-10-10')\n
at [Source: org.apache.catalina.connector.CoyoteInputStream@4ee2a60e; line: 1, column: 65] (through reference chain: ru.zavanton.entities.User[\"birthDate\"])"}
如何使它工作,使客户端调用像:
curl -i -X POST -H "Content-Type:application/json" -d "{ \"firstName\" : \"John\", \"lastName\" : \"Johnson\", \"birthDate\" : \"1999-10-10\", \"email\" : \"[email protected]\" }" http://localhost:8080/users
将实体存储到数据库中。
下面是关于班级的信息。
用户类:
package ru.zavanton.entities;
import com.fasterxml.jackson.annotation.JsonFormat;
import javax.persistence.Entity;
import javax.persistence.GeneratedValue;
import javax.persistence.GenerationType;
import javax.persistence.Id;
import java.time.LocalDate;
@Entity
public class User {
@Id
@GeneratedValue(strategy = GenerationType.AUTO)
private long id;
private String firstName;
private String lastName;
@JsonFormat(shape = JsonFormat.Shape.STRING, pattern = "yyyy-MM-dd")
private LocalDate birthDate;
private String email;
private String password;
public long getId() {
return id;
}
public void setId(long id) {
this.id = id;
}
public String getFirstName() {
return firstName;
}
public void setFirstName(String firstName) {
this.firstName = firstName;
}
public String getLastName() {
return lastName;
}
public void setLastName(String lastName) {
this.lastName = lastName;
}
public LocalDate getBirthDate() {
return birthDate;
}
public void setBirthDate(LocalDate birthDate) {
this.birthDate = birthDate;
}
public String getEmail() {
return email;
}
public void setEmail(String email) {
this.email = email;
}
public String getPassword() {
return password;
}
public void setPassword(String password) {
this.password = password;
}
}
UserRepository类:
package ru.zavanton.repositories;
import org.springframework.data.repository.PagingAndSortingRepository;
import org.springframework.data.repository.query.Param;
import org.springframework.data.rest.core.annotation.RepositoryRestResource;
import ru.zavanton.entities.User;
@RepositoryRestResource(collectionResourceRel = "users", path = "users")
public interface UserRepository extends PagingAndSortingRepository<User, Long> {
User findByEmail(@Param("email") String email);
}
应用类别:
package ru.zavanton;
import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;
@SpringBootApplication
public class Application {
public static void main(String[] args) {
SpringApplication.run(Application.class, args);
}
}
7条答案
按热度按时间ttisahbt1#
你需要Jackson依赖来实现这个序列化和非序列化。
添加此依赖项:
Gradle:
梅芬:
之后,您需要告诉JacksonObjectMapper使用JavaTimeModule。为此,在主类中自动连接ObjectMapper并将JavaTimeModule注册到它。
之后,您的LocalDate和LocalDateTime应该被正确地序列化和重新序列化。
hzbexzde2#
Sping Boot 2.2.2 / Gradle:
Gradle(build.gradle):
Entity(User.class):
验证码:
rjzwgtxy3#
我有一个类似的问题,我通过做两个改变来解决
1.在
application.yaml
文件中添加以下条目1.将下面两个注解添加到POJO的
LocalDate
字段例如
请求格式示例:
示例请求格式为数组
nbewdwxp4#
事实证明,不应该忘记在pom文件中包含jacson依赖。这为我解决了这个问题:
iqjalb3h5#
好吧,我在每个项目上所做的都是上述选项的组合。
首先,添加jsr310依赖项:
重要信息:把这个依赖项放在依赖项列表的顶部。我已经看到一个项目,其中Localdate错误仍然存在,即使对pom.xml有此依赖关系。但是改变了独立的顺序,错误就消失了。
在
/src/main/resources/application.yml
文件上,设置write-dates-as-timestamps
属性:创建一个
ObjectMapper
bean,如下所示:遵循此配置,转换始终在Sping Boot 1.5.x上工作,没有任何错误。
Bonus:Spring AMQP队列配置
使用Spring AMQP时,注意是否有
Jackson2JsonMessageConverter
的新示例(创建SimpleRabbitListenerContainerFactory
时常见的情况)。您需要将ObjectMapper
bean传递给它,如:否则,您将收到相同的错误。
z3yyvxxp6#
我已经纠结了三个小时了。我相信Dherik的回答(关于AMQP的额外材料)使我离我的答案YMMV很近。
我在SpringBootApplication的对象Map器中注册了JavaTimeModule,如下所示:
然而,我的Instants是通过STOMP连接来仍然没有实现。然后我意识到我已经创建了一个MappingJackson2MessageConverter,它创建了第二个ObjectMapper。所以我想这个故事的寓意是:您确定您已经调整了所有的ObjectMapper吗?在我的例子中,我用注册了JavaTimeModule的外部版本替换了MappingJackson2MessageConverter.objectMapper,一切正常:
rlcwz9us7#
您需要将以下代码添加到pom.xml modules-java8中