小编典典

Spring 3.2:基于Spring Security角色过滤Jackson JSON输出

spring

有什么好的方法可以根据Spring Security角色过滤JSON输出吗?我正在寻找类似@JsonIgnore的东西,但要寻找角色,例如@HasRole(“ ROLE_ADMIN”)。我应该如何实施呢?


阅读 391

收藏
2020-04-21

共1个答案

小编典典

有什么好的方法可以根据Spring Security角色过滤JSON输出吗?我正在寻找类似@JsonIgnore的东西,但要寻找角色,例如@HasRole(“ ROLE_ADMIN”)。我应该如何实施呢?对于那些从Google登陆的人来说,这里是Spring Boot 1.4的类似解决方案。

为每个角色定义接口,例如

public class View {
    public interface Anonymous {}

    public interface Guest extends Anonymous {}

    public interface Organizer extends Guest {}

    public interface BusinessAdmin extends Organizer {}

    public interface TechnicalAdmin extends BusinessAdmin {}
}

声明@JsonView你的实体,例如

@Entity
public class SomeEntity {
    @JsonView(View.Anonymous.class)
    String anonymousField;

    @JsonView(View.BusinessAdmin.class)
    String adminField;
}

并定义一个根据角色@ControllerAdvice选择合适的权利JsonView:

@ControllerAdvice
public class JsonViewConfiguration extends AbstractMappingJacksonResponseBodyAdvice {

    @Override
    public boolean supports(MethodParameter returnType, Class<? extends HttpMessageConverter<?>> converterType) {
        return super.supports(returnType, converterType);
    }

    @Override
    protected void beforeBodyWriteInternal(MappingJacksonValue bodyContainer, MediaType contentType,
                                           MethodParameter returnType, ServerHttpRequest request, ServerHttpResponse response) {

        Class<?> viewClass = View.Anonymous.class;

        if (SecurityContextHolder.getContext().getAuthentication() != null && SecurityContextHolder.getContext().getAuthentication().getAuthorities() != null) {
            Collection<? extends GrantedAuthority> authorities = SecurityContextHolder.getContext().getAuthentication().getAuthorities();

            if (authorities.stream().anyMatch(o -> o.getAuthority().equals(Role.GUEST.getValue()))) {
                viewClass = View.Guest.class;
            }
            if (authorities.stream().anyMatch(o -> o.getAuthority().equals(Role.ORGANIZER.getValue()))) {
                viewClass = View.Organizer.class;
            }
            if (authorities.stream().anyMatch(o -> o.getAuthority().equals(Role.BUSINESS_ADMIN.getValue()))) {
                viewClass = View.BusinessAdmin.class;
            }
            if (authorities.stream().anyMatch(o -> o.getAuthority().equals(Role.TECHNICAL_ADMIN.getValue()))) {
                viewClass = View.TechnicalAdmin.class;
            }
        }
        bodyContainer.setSerializationView(viewClass);
    }
}
2020-04-21