Spring 5 MVC JSON ser/deser 不尊重属性(但适用于 XML)
Spring 5 MVC JSON ser/deser not respecting properties (but works for XML)
我在使用 vanilla Spring Boot 2/Spring 5/Java 10/Jigsaw 的新设置中遇到了一个奇怪的情况,无论我做什么,拉一个object 通过 Spring MVC 给我一个空的 {} JSON object 而不是我的 object 属性。
但是...如果我使用 application/xml 的 Accept header 而不是 application/json,我将获得所有正确的属性。也许我失去了理智,但我似乎记得在以前的版本中,如果它在一侧工作 (xml),它应该在另一侧 (json) 和 vice/versa 上工作。
我在内部将其追溯到为我的模型 class 创建的没有属性的 BeanSerializer。我只是不确定这是为什么。我追踪了整个执行过程,发现 Jackson 在 http 转换过程中是 运行 ...它只是忽略了 object.
中的所有属性
这是我的设置:
专家:
<parent>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-parent</artifactId>
<version>2.0.4.RELEASE</version>
<relativePath /> <!-- lookup parent from repository -->
</parent>
<properties>
<project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
<project.reporting.outputEncoding>UTF-8</project.reporting.outputEncoding>
<java.version>10</java.version>
</properties>
<dependencies>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-amqp</artifactId>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-data-jpa</artifactId>
</dependency>
<dependency>
<groupId>org.postgresql</groupId>
<artifactId>postgresql</artifactId>
<version>42.2.4</version>
<scope>runtime</scope>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-integration</artifactId>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-web</artifactId>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-webflux</artifactId>
</dependency>
<dependency>
<groupId>javax.xml.bind</groupId>
<artifactId>jaxb-api</artifactId>
<version>2.3.0</version>
</dependency>
<dependency>
<groupId>org.glassfish.jaxb</groupId>
<artifactId>jaxb-runtime</artifactId>
<version>2.3.0</version>
<scope>runtime</scope>
</dependency>
<dependency>
<groupId>javax.activation</groupId>
<artifactId>javax.activation-api</artifactId>
<version>1.2.0</version>
</dependency>
<dependency>
<groupId>com.fasterxml.jackson.module</groupId>
<artifactId>jackson-module-jaxb-annotations</artifactId>
<version>2.9.6</version>
<scope>runtime</scope>
</dependency>
module-info:
module stupid.example {
opens com.example.microservice.datasynchronizer;
opens com.example.microservice.datasynchronizer.model;
opens com.example.microservice.datasynchronizer.webflux to spring.beans, spring.core, spring.web ;
opens com.example.microservice.datasynchronizer.dao to spring.core ;
requires java.base ;
requires java.xml.bind ;
requires spring.boot;
requires spring.boot.autoconfigure;
requires spring.beans ;
requires spring.context ;
requires spring.core ;
requires spring.data.commons ;
requires spring.web ;
requires spring.webmvc ;
requires java.persistence ;
requires org.junit.jupiter.api;
requires spring.test;
requires spring.boot.test ;
}
型号class(最新,带有jaxb注解以防万一):
@Entity
@XmlRootElement
public class Thingamajig {
@Id
@GeneratedValue(strategy = GenerationType.AUTO)
@XmlElement
private Long id;
@XmlElement
private String firstName;
@XmlElement
private String lastName;
public Thingamajig ( ) { ; }
public Thingamajig(String firstName, String lastName) {
this.firstName = firstName;
this.lastName = lastName;
}
@Override
public String toString() {
return String.format("Thingamajig [id=%d, firstName='%s', lastName='%s']", id, firstName, lastName);
}
}
控制器:
@RestController
public class ThingamajigController {
@Autowired
private ThingamajigDao _dao ;
@GetMapping("/thing/{id}")
public Thingamajig getPerson(@PathVariable Long id) {
Optional<Thingamajig> found = _dao.findById(id) ;
return found.get() ;
}
@PostMapping ( "/thing" )
@ResponseStatus(HttpStatus.CREATED)
public void add(@RequestBody Thingamajig person) {
_dao.save(person) ;
}
}
配置:
@EnableWebMvc
@SpringBootApplication
public class DataSynchronizerApplication {
public static void main(String[] args) throws Throwable {
SpringApplication.run(DataSynchronizerApplication.class, args);
}
}
我到底错过了什么?任何帮助表示赞赏。
您只是忘记了在 Thingamajig 中定义 getter 和 setter class。
XML 有效,因为您已经在属性上定义了注释,但 JSON 序列化程序正在寻找吸气剂。
我在使用 vanilla Spring Boot 2/Spring 5/Java 10/Jigsaw 的新设置中遇到了一个奇怪的情况,无论我做什么,拉一个object 通过 Spring MVC 给我一个空的 {} JSON object 而不是我的 object 属性。
但是...如果我使用 application/xml 的 Accept header 而不是 application/json,我将获得所有正确的属性。也许我失去了理智,但我似乎记得在以前的版本中,如果它在一侧工作 (xml),它应该在另一侧 (json) 和 vice/versa 上工作。
我在内部将其追溯到为我的模型 class 创建的没有属性的 BeanSerializer。我只是不确定这是为什么。我追踪了整个执行过程,发现 Jackson 在 http 转换过程中是 运行 ...它只是忽略了 object.
中的所有属性这是我的设置:
专家:
<parent>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-parent</artifactId>
<version>2.0.4.RELEASE</version>
<relativePath /> <!-- lookup parent from repository -->
</parent>
<properties>
<project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
<project.reporting.outputEncoding>UTF-8</project.reporting.outputEncoding>
<java.version>10</java.version>
</properties>
<dependencies>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-amqp</artifactId>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-data-jpa</artifactId>
</dependency>
<dependency>
<groupId>org.postgresql</groupId>
<artifactId>postgresql</artifactId>
<version>42.2.4</version>
<scope>runtime</scope>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-integration</artifactId>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-web</artifactId>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-webflux</artifactId>
</dependency>
<dependency>
<groupId>javax.xml.bind</groupId>
<artifactId>jaxb-api</artifactId>
<version>2.3.0</version>
</dependency>
<dependency>
<groupId>org.glassfish.jaxb</groupId>
<artifactId>jaxb-runtime</artifactId>
<version>2.3.0</version>
<scope>runtime</scope>
</dependency>
<dependency>
<groupId>javax.activation</groupId>
<artifactId>javax.activation-api</artifactId>
<version>1.2.0</version>
</dependency>
<dependency>
<groupId>com.fasterxml.jackson.module</groupId>
<artifactId>jackson-module-jaxb-annotations</artifactId>
<version>2.9.6</version>
<scope>runtime</scope>
</dependency>
module-info:
module stupid.example {
opens com.example.microservice.datasynchronizer;
opens com.example.microservice.datasynchronizer.model;
opens com.example.microservice.datasynchronizer.webflux to spring.beans, spring.core, spring.web ;
opens com.example.microservice.datasynchronizer.dao to spring.core ;
requires java.base ;
requires java.xml.bind ;
requires spring.boot;
requires spring.boot.autoconfigure;
requires spring.beans ;
requires spring.context ;
requires spring.core ;
requires spring.data.commons ;
requires spring.web ;
requires spring.webmvc ;
requires java.persistence ;
requires org.junit.jupiter.api;
requires spring.test;
requires spring.boot.test ;
}
型号class(最新,带有jaxb注解以防万一):
@Entity
@XmlRootElement
public class Thingamajig {
@Id
@GeneratedValue(strategy = GenerationType.AUTO)
@XmlElement
private Long id;
@XmlElement
private String firstName;
@XmlElement
private String lastName;
public Thingamajig ( ) { ; }
public Thingamajig(String firstName, String lastName) {
this.firstName = firstName;
this.lastName = lastName;
}
@Override
public String toString() {
return String.format("Thingamajig [id=%d, firstName='%s', lastName='%s']", id, firstName, lastName);
}
}
控制器:
@RestController
public class ThingamajigController {
@Autowired
private ThingamajigDao _dao ;
@GetMapping("/thing/{id}")
public Thingamajig getPerson(@PathVariable Long id) {
Optional<Thingamajig> found = _dao.findById(id) ;
return found.get() ;
}
@PostMapping ( "/thing" )
@ResponseStatus(HttpStatus.CREATED)
public void add(@RequestBody Thingamajig person) {
_dao.save(person) ;
}
}
配置:
@EnableWebMvc
@SpringBootApplication
public class DataSynchronizerApplication {
public static void main(String[] args) throws Throwable {
SpringApplication.run(DataSynchronizerApplication.class, args);
}
}
我到底错过了什么?任何帮助表示赞赏。
您只是忘记了在 Thingamajig 中定义 getter 和 setter class。
XML 有效,因为您已经在属性上定义了注释,但 JSON 序列化程序正在寻找吸气剂。