fra*_*cis 11 java spring spring-security spring-data spring-data-rest
我正在尝试实现细粒度访问控制,同时仍然利用Spring数据休息.
我正在努力确保安全,CrudRepository因此用户只能修改或插入属于他们的数据.我正在使用@PreAuthorize/ @PostAuthorize和@PreFilter/ @PostFilter将访问锁定到当前主体.
到目前为止我的存储库看起来像这样
public interface MyRepository extends CrudRepository<MyObject, Integer> {
@PreAuthorize("#entity.userId == principal.id")
@Override
<S extends MyObject> S save(S entity);
@PreFilter("filterObject.userId === principal.id")
@Override
<S extends MyObject> Iterable<S> save(Iterable<S> entities);
@PostAuthorize("returnObject.userId == principal.id")
@Override
MyObject findOne(Integer integer);
@PostFilter("filterObject.userId == principal.id")
@Override
Iterable<MyObject> findAll();
}
Run Code Online (Sandbox Code Playgroud)
虽然这有点单调乏味,但它似乎完成了我所追求的目标.(如果有人知道更好的方式,请随时告诉我!)
我遇到问题的地方是delete(),count()和exists()
@Override
long count();
@Override
void delete(Integer integer);
@Override
void delete(MyObject entity);
@Override
void deleteAll();
@Override
boolean exists(Integer integer);
Run Code Online (Sandbox Code Playgroud)
这些方法要么采用IntegerID参数,要么根本不采用.看来我必须首先选择具有输入ID的实体,然后执行auth检查.
存储库中是否可以进行此类授权?
谢谢
编辑:
感谢ksokol,这似乎现在正在运作.
我在@Configuration课堂上添加了一个新的bean
@Bean
public EvaluationContextExtension securityExtension() {
return new SecurityEvaluationContextExtensionImpl();
}
Run Code Online (Sandbox Code Playgroud)
此bean扩展EvaluationContextExtensionSupport并覆盖getRootObject以返回SecurityExpressionRoot保存我的自定义主体的bean .
public class SecurityEvaluationContextExtensionImpl extends EvaluationContextExtensionSupport {
@Override
public String getExtensionId() {
return "security";
}
@Override
public Object getRootObject() {
Authentication authentication = SecurityContextHolder.getContext().getAuthentication();
return new SecurityExpressionRoot(authentication){};
}
}
Run Code Online (Sandbox Code Playgroud)
Kam*_*kol 18
从Spring Security 4.0开始,您可以访问Spring Data JPA查询中的安全上下文.
将SecurityEvaluationContextExtensionbean 添加到bean上下文中:
@Bean
public SecurityEvaluationContextExtension securityEvaluationContextExtension() {
return new SecurityEvaluationContextExtension();
}
Run Code Online (Sandbox Code Playgroud)
现在您应该能够访问PrincipalSpring Data查询:
@Query("select count(m) from MyObject as m where m.user.id = ?#{ principal?.id }")
@Override
long count();
@Modifying
@Query("delete from MyObject as m where m.id = ?1 and m.user.id = ?#{ principal?.id }")
@Override
void delete(Integer integer);
@Modifying
@Query("delete from MyObject as m where m.id = ?1 and m.user.id = ?#{ principal?.id }")
@Override
void delete(MyObject entity);
@Modifying
@Query("delete from MyObject as m where m.user.id = ?#{ principal?.id }")
@Override
void deleteAll();
@Query("select 1 from MyObject as m where m.id = ?1 and m.user.id = ?#{ principal?.id }")
@Override
boolean exists(Integer integer);
Run Code Online (Sandbox Code Playgroud)
警告.查询可能有错误.我没时间测试它.
| 归档时间: |
|
| 查看次数: |
4824 次 |
| 最近记录: |