我在模型中有一些字段,我只希望在登录用户具有角色 function Person(){}
Person.prototype.name = "Nicholas";
Person.prototype.age = 29;
Person.prototype.job = "Software Engineer";
Person.prototype.sayName = function(){
};
var person1 = new Person();
person1.hasOwnProperty("name") // false ?
时返回该字段。我可以使用person1.hasOwnProperty("name") // is true
但是它会为每个人隐藏它。如何让它动态隐藏?
答案 0 :(得分:2)
您应该使用Jackson Json Views技术来实现它 - 它允许选择以编程方式序列化的不同字段集。它也受Spring
支持考虑您有一个类Model
,其中包含两个属性:commonField
应该适用于所有人,secretField
应该只适用于某些用户。您应该创建一个视图层次结构(任何类都可以工作)并使用@JsonView
注释指定哪个视图在哪个视图中可用
package com.stackoverflow.jsonview;
import com.fasterxml.jackson.annotation.JsonView;
public class Model {
public static class Public {}
public static class Secret extends Public {}
@JsonView(Public.class)
private String commonField;
@JsonView(Secret.class)
private String secretField;
public Model() {
}
public Model(String commonField, String secretField) {
this.commonField = commonField;
this.secretField = secretField;
}
public String getCommonField() {
return commonField;
}
public void setCommonField(String commonField) {
this.commonField = commonField;
}
public String getSecretField() {
return secretField;
}
public void setSecretField(String secretField) {
this.secretField = secretField;
}
}
现在,您可以在具体的ObjectMapper
package com.stackoverflow.jsonview;
import com.fasterxml.jackson.core.JsonProcessingException;
import com.fasterxml.jackson.databind.ObjectMapper;
import org.junit.Test;
import static org.junit.Assert.*;
/**
*/
public class ModelTest {
@Test
public void testSecretField() throws JsonProcessingException {
Model model = new Model("commonField","secretField");
assertEquals("{\"commonField\":\"commonField\",\"secretField\":\"secretField\"}", new ObjectMapper().writerWithView(Model.Secret.class).writeValueAsString(model));
assertEquals("{\"commonField\":\"commonField\"}", new ObjectMapper().writerWithView(Model.Public.class).writeValueAsString(model));
}
}
我不确定你是否可以使用declaratie方法让spring根据开箱即用的用户角色选择正确的视图,所以你可能需要写一些这样的代码:
@RequestMapping("/data")
public String getData(HttpServletRequest request) {
Model model = service.getModel();
ObjectMapper objectMapper = new ObjectMapper();
objectMapper = request.isUserInRole("ROLE_ADMIN") ? objectMapper.writerWithView(Model.Secret.class) : objectMapper.writerWithView(Model.Public.class);
return objectMapper.writeValueAsString(model);
}
答案 1 :(得分:1)
经过整整一个月的尝试,我解决了这个问题。我正在使用Spring 4.3.1并启动,使用pagedrepository在Hal中返回数据。
将RepositoryRestMvcConfiguration
扩展为MyRepositoryRestMvcConfiguration
并将@Configuration
添加到班级,确保您的入门班级有@EnableWebMvc
将此内容添加到MyRepositoryRestMvcConfiguration
- 将TypeConstrainedMappingJackson2HttpMessageConverter
扩展为MyResourceSupportHttpMessageConverter
将此内容添加到MyRepositoryRestMvcConfiguration
@Override
@Bean
public TypeConstrainedMappingJackson2HttpMessageConverter halJacksonHttpMessageConverter() {
ArrayList<MediaType> mediaTypes = new ArrayList<MediaType>();
mediaTypes.add(MediaTypes.HAL_JSON);
if (config().useHalAsDefaultJsonMediaType()) {
mediaTypes.add(MediaType.APPLICATION_JSON);
}
int order = config().useHalAsDefaultJsonMediaType() ? Ordered.LOWEST_PRECEDENCE - 10
: Ordered.LOWEST_PRECEDENCE - 1;
TypeConstrainedMappingJackson2HttpMessageConverter converter = new MyResourceSupportHttpMessageConverter(
order);
converter.setObjectMapper(halObjectMapper());
converter.setSupportedMediaTypes(mediaTypes);
converter.getObjectMapper().addMixIn(Object.class, MyFilteringMixin.class);
final FilterProvider myRestrictionFilterProvider = new SimpleFilterProvider()
.addFilter("MyFilteringMixin", new MyPropertyFilter()).setFailOnUnknownId(false);
converter.getObjectMapper().setFilterProvider(myRestrictionFilterProvider);
return converter;
}
创建一个空的Mixin
package filters;
import com.fasterxml.jackson.annotation.JsonFilter;
@JsonFilter("MyFilteringMixin")
public class MyFilteringMixin {}
创建一个空的Mixin
创建扩展MyPropertyFilter
的类SimpleBeanPropertyFilter
并覆盖适应此方法
serializeAsField(Object, JsonGenerator, SerializerProvider, PropertyWriter)
您需要调用super.serializeAsField(pPojo, pJgen, pProvider, pWriter)
或pWriter.serializeAsOmittedField(pPojo, pJgen, pProvider)
,具体取决于您是希望包含还是放弃此特定字段。
我在我想要改变的特定字段中添加了一个注释,并在决定调用这两个中的哪一个时查询该注释。我在注释中注入了安全角色并存储了允许的角色。
这改变了Hal与调用者共享的内容,而不是Hal在其存储库中持有的内容。因此,您可以根据呼叫者的身份对其进行变形。