标题翻译
Cannot save an object with GrantedAuthority field (no Creators, like default construct, exist)
问题
我一直在尝试在我的项目中启用基于表单的用户注册。
只是注册一个没有角色的用户运行良好,但是添加一些角色会给我一个错误:
com.fasterxml.jackson.databind.exc.InvalidDefinitionException: 无法构造org.springframework.security.core.GrantedAuthority
的实例(不存在默认构造函数等创建者):抽象类型需要映射到具体类型,具有自定义反序列化器或包含附加类型信息
在[源:(PushbackInputStream); 行:9,列:21]处(通过引用链:com.warehousing.model.User ["authorities"] - > java.util.HashSet [0])
我怀疑问题是由于Spring不知道如何将我的权限表示从一些扩展GrantedAuthority
的内容转换过来。话虽如此,我尝试将GrantedAuthority
切换到SimpleGrantedAuthority
,但问题仍然存在。
我的User类如下所示:
public class User implements UserDetails {
@Id
@GeneratedValue(strategy=GenerationType.AUTO)
private Long id;
private String fName;
private String lName;
private String phone;
private String email;
// Spring认证属性
@ElementCollection(targetClass=SimpleGrantedAuthority.class, fetch = FetchType.EAGER)
@JsonDeserialize(as = SimpleGrantedAuthority.class)
private Set<? extends GrantedAuthority> grantedAuthorities;
@NotNull
private String password;
@NotNull
private String username;
private boolean isAccountNonExpired;
private boolean isAccountNonLocked;
private boolean isCredentialsNonExpired;
private boolean isEnabled;
public User(String fName, String lName, String phone, String email,
Set<SimpleGrantedAuthority> grantedAuthorities, String password, String username,
boolean isAccountNonExpired, boolean isAccountNonLocked,
boolean isCredentialsNonExpired, boolean isEnabled) {
this.fName = fName;
this.lName = lName;
this.phone = phone;
this.email = email;
this.grantedAuthorities = grantedAuthorities;
this.password = password;
this.username = username;
this.isAccountNonExpired = isAccountNonExpired;
this.isAccountNonLocked = isAccountNonLocked;
this.isCredentialsNonExpired = isCredentialsNonExpired;
this.isEnabled = isEnabled;
}
// 获取器、设置器和构造函数
}
我的UserController中用于创建新用户的方法:
@RestController
public class UserController {
@Autowired
UserService userService;
@PostMapping("/users")
public User createNew(@Valid @RequestBody User user) {
return userService.addUser(user);
}
}
该方法调用了UserService:
public class UserService implements UserDetailsService {
@Autowired
UserRepository userRepo;
public User addUser(User user) {
Set<SimpleGrantedAuthority> userRoles = user.getGrantedAuthorities()
.stream()
.map(p -> new SimpleGrantedAuthority(p.getAuthority()))
.collect(Collectors.toSet());
User newUser = new User(user.getfName(), user.getlName(),
user.getPhone(), user.getEmail(),
userRoles,
user.getPassword(), user.getUsername(),
user.isAccountNonExpired(),
user.isAccountNonLocked(),
user.isCredentialsNonExpired(),
user.isEnabled());
return userRepo.save(newUser);
}
}
现在,像这样发布一个JSON可以正常工作:
{
"fName": "First",
"lName": "Last",
"phone": "+3111111111",
"email": "test@mail.com",
"password": "password",
"username": "user",
"enabled": true,
"authorities": [],
"accountNonLocked": true,
"accountNonExpired": true,
"credentialsNonExpired": true
}
然而,添加某种权限会导致上述错误:
{
"fName": "First",
"lName": "Last",
"phone": "+3111111111",
"email": "test@mail.com",
"password": "password",
"username": "user",
"enabled": true,
"authorities": [{
"authority": "inventory:read"
}],
"accountNonLocked": true,
"accountNonExpired": true,
"credentialsNonExpired": true
}
欢迎提供任何帮助!
英文翻译
I have been trying to enable a form-based user registration in my project.
Just registering a user with no roles works fine, however adding some roles gives me an error:
>
com.fasterxml.jackson.databind.exc.InvalidDefinitionException: Cannot construct instance of org.springframework.security.core.GrantedAuthority
(no Creators, like default construct, exist): abstract types either need to be mapped to concrete types, have custom deserializer, or contain additional type information
at [Source: (PushbackInputStream); line: 9, column: 21] (through reference chain: com.warehousing.model.User["authorities"]->java.util.HashSet[0])
I suspect that the problem is coming from the fact that Spring has no idea how to convert from my authority representation to something that extends GrantedAuthority
. That being said, I tried switching from GrantedAuthority
to SimpleGrantedAuthority
, but the problem remained.
My User class looks like follows:
public class User implements UserDetails {
@Id
@GeneratedValue(strategy=GenerationType.AUTO)
private Long id;
private String fName;
private String lName;
private String phone;
private String email;
// Properties for Spring authentication
@ElementCollection(targetClass=SimpleGrantedAuthority.class, fetch = FetchType.EAGER)
@JsonDeserialize(as = SimpleGrantedAuthority.class)
private Set<? extends GrantedAuthority> grantedAuthorities;
@NotNull
private String password;
@NotNull
private String username;
private boolean isAccountNonExpired;
private boolean isAccountNonLocked;
private boolean isCredentialsNonExpired;
private boolean isEnabled;
public User(String fName, String lName, String phone, String email,
Set<SimpleGrantedAuthority> grantedAuthorities, String password, String username,
boolean isAccountNonExpired, boolean isAccountNonLocked,
boolean isCredentialsNonExpired, boolean isEnabled) {
this.fName = fName;
this.lName = lName;
this.phone = phone;
this.email = email;
this.grantedAuthorities = grantedAuthorities;
this.password = password;
this.username = username;
this.isAccountNonExpired = isAccountNonExpired;
this.isAccountNonLocked = isAccountNonLocked;
this.isCredentialsNonExpired = isCredentialsNonExpired;
this.isEnabled = isEnabled;
}
// Getters, setters & constructors
}
My UserController`s method to create a new user:
@RestController
public class UserController {
@Autowired
UserService userService;
@PostMapping("/users")
public User createNew(@Valid @RequestBody User user) {
return userService.addUser(user);
}
}
Which calls the UserService:
public class UserService implements UserDetailsService {
@Autowired
UserRepository userRepo;
public User addUser(User user) {
Set<SimpleGrantedAuthority> userRoles = user.getGrantedAuthorities()
.stream()
.map(p -> new SimpleGrantedAuthority(p.getAuthority()))
.collect(Collectors.toSet());
User newUser = new User(user.getfName(), user.getlName(),
user.getPhone(), user.getEmail(),
userRoles,
user.getPassword(), user.getUsername(),
user.isAccountNonExpired(),
user.isAccountNonLocked(),
user.isCredentialsNonExpired(),
user.isEnabled());
return userRepo.save(newUser);
}
}
Now, posting a JSON like this works fine:
{
"fName": "First",
"lName": "Last",
"phone": "+3111111111",
"email": "test@mail.com",
"password": "password",
"username": "user",
"enabled": true,
"authorities": [],
"accountNonLocked": true,
"accountNonExpired": true,
"credentialsNonExpired": true
}
However, adding some kind of authority will cause the error mentioned above:
{
"fName": "First",
"lName": "Last",
"phone": "+3111111111",
"email": "test@mail.com",
"password": "password",
"username": "user",
"enabled": true,
"authorities": [{
"authority": "inventory:read"
}],
"accountNonLocked": true,
"accountNonExpired": true,
"credentialsNonExpired": true
}
Any kind of help is appreciated!
专注分享java语言的经验与见解,让所有开发者获益!
评论