【发布时间】:2016-02-28 09:02:40
【问题描述】:
给定一个映射了以下属性的用户实体:
@Entity
@Table(name = "user")
public class User {
//...
@Id
@GeneratedValue
@Column(name = "user_id")
private Long id;
@Column(name = "user_email")
private String email;
@Column(name = "user_password")
private String password;
@Column(name = "user_type")
@Enumerated(EnumType.STRING)
private UserType type;
@Column(name = "user_registered_date")
private Timestamp registeredDate;
@Column(name = "user_dob")
@Temporal(TemporalType.DATE)
private Date dateOfBirth;
//...getters and setters
}
我创建了一个通过 ID 返回用户的控制器方法。
@RestController
public class UserController {
//...
@RequestMapping(
value = "/api/users/{id}",
method = RequestMethod.GET,
produces = MediaType.APPLICATION_JSON_VALUE)
public ResponseEntity<User> getUser(@PathVariable("id") Long id) {
User user = userService.findOne(id);
if (user != null) {
return new ResponseEntity<User>(user, HttpStatus.OK);
}
return new ResponseEntity<User>(HttpStatus.NOT_FOUND);
}
//...
}
我的业务逻辑层中的一个服务。
public class UserServiceBean implements UserService {
//...
public User findOne(Long id) {
User user = userRepository.findOne(id);
return user;
}
//...
}
我的数据层中有一个存储库。
public interface UserRepository extends JpaRepository<User, Long> {
}
这很好用,它返回有关用户的所有信息,但我在应用程序的几个不同部分使用它,并且在某些情况下我只需要用户的特定字段。
我正在学习 spring-boot 来创建 web 服务,并且想知道:鉴于当前的实现,有没有办法选择我想在 web 服务中发布的属性?
如果不是,我应该在实现中进行哪些更改才能做到这一点?
谢谢。
【问题讨论】:
-
您已经有一个安全漏洞,因为您当前的设置会将密码转储到外部世界。这基本上就是为什么我从来没有在任何暴露给外界的接口中暴露 JPA 实体的海报示例。在你知道数据库和 JPA 实体的更改之前,要么破坏你的 API,要么你暴露了外部世界真的不知道的数据。
-
您可以将 DTO 用于不同的表示形式(参见 martinfowler.com/eaaCatalog/dataTransferObject.html)
-
你可能想看看Jackson wiki.fasterxml.com/JacksonJsonViews 的@JsonView 注释,尤其是这个问题stackoverflow.com/questions/29838960/…
标签: java spring rest jpa spring-boot