Commit 4fb8a6fc authored by Matija Obreza's avatar Matija Obreza
Browse files

Merge branch '23-providing-permissions-to-frontend' into 'master'

Resolve "Providing permissions to frontend"

Closes #23

See merge request genesys-pgr/application-blocks!23
parents 6e829eb5 3f57a18a
......@@ -136,7 +136,7 @@
<groupId>org.springframework</groupId>
<artifactId>spring-core</artifactId>
<version>${spring.version}</version>
<scope>test</scope>
<scope>provided</scope>
</dependency>
<dependency>
......
......@@ -17,10 +17,15 @@ package org.genesys.blocks.security.model;
import java.io.Serializable;
import com.fasterxml.jackson.databind.annotation.JsonAppend;
import org.genesys.blocks.model.EntityId;
import org.genesys.blocks.security.serialization.CurrentPermissions;
import org.genesys.blocks.security.serialization.CurrentPermissionsWriter;
/**
* Interface label for entities that require ACL security.
*/
@JsonAppend(props = { @JsonAppend.Prop(name="_permissions", value = CurrentPermissionsWriter.class, type=CurrentPermissions.class) })
public interface AclAwareModel extends Serializable, EntityId {
}
/*
* Copyright 2017 Global Crop Diversity Trust
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package org.genesys.blocks.security.serialization;
/**
* The Class CurrentPermissions.
*/
public class CurrentPermissions {
/** The create. */
public boolean create;
/** The read. */
public boolean read;
/** The write. */
public boolean write;
/** The delete. */
public boolean delete;
/** The manage. */
public boolean manage;
}
/*
* Copyright 2017 Global Crop Diversity Trust
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package org.genesys.blocks.security.serialization;
import com.fasterxml.jackson.core.JsonGenerator;
import com.fasterxml.jackson.databind.JavaType;
import com.fasterxml.jackson.databind.SerializerProvider;
import com.fasterxml.jackson.databind.cfg.MapperConfig;
import com.fasterxml.jackson.databind.introspect.AnnotatedClass;
import com.fasterxml.jackson.databind.introspect.BeanPropertyDefinition;
import com.fasterxml.jackson.databind.ser.VirtualBeanPropertyWriter;
import com.fasterxml.jackson.databind.util.Annotations;
import org.genesys.blocks.security.SecurityContextUtil;
import org.genesys.blocks.util.CurrentApplicationContext;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.BeansException;
import org.springframework.context.ApplicationContext;
import org.springframework.security.access.PermissionEvaluator;
import org.springframework.security.acls.domain.BasePermission;
import org.springframework.security.core.Authentication;
/**
* The Class CurrentPermissionsWriter.
*/
public class CurrentPermissionsWriter extends VirtualBeanPropertyWriter {
/** The Constant LOG. */
private static final Logger LOG = LoggerFactory.getLogger(CurrentPermissionsWriter.class);
/** The Constant serialVersionUID. */
private static final long serialVersionUID = 1L;
/** The permission evaluator. */
private static PermissionEvaluator permissionEvaluator;
// Context initialization
static {
ApplicationContext context = CurrentApplicationContext.getContext();
if (context != null) {
try {
permissionEvaluator = context.getBean(PermissionEvaluator.class);
} catch (BeansException e) {
LOG.warn("Could not find PermissionEvaluator instance in your context");
}
} else {
LOG.warn("You should initialize a bean instance of org.genesys.blocks.util.CurrentApplicationContext in your context");
}
}
/**
* Instantiates a new current permissions writer.
*/
public CurrentPermissionsWriter() {
LOG.trace("CurrentPermissionsWriter");
}
/**
* Instantiates a new current permissions writer.
*
* @param propDef the prop def
* @param annotations the annotations
* @param type the type
*/
public CurrentPermissionsWriter(BeanPropertyDefinition propDef, Annotations annotations, JavaType type) {
super(propDef, annotations, type);
LOG.trace("CurrentPermissionsWriter");
}
/* (non-Javadoc)
* @see com.fasterxml.jackson.databind.ser.VirtualBeanPropertyWriter#value(java.lang.Object, com.fasterxml.jackson.core.JsonGenerator, com.fasterxml.jackson.databind.SerializerProvider)
*/
@Override
protected Object value(Object bean, JsonGenerator gen, SerializerProvider prov) throws Exception {
if (permissionEvaluator != null) {
Authentication authentication = SecurityContextUtil.getCurrentUser();
if (authentication != null) {
CurrentPermissions perms = new CurrentPermissions();
perms.create = permissionEvaluator.hasPermission(authentication, bean, BasePermission.CREATE);
perms.read = permissionEvaluator.hasPermission(authentication, bean, BasePermission.READ);
perms.write = permissionEvaluator.hasPermission(authentication, bean, BasePermission.WRITE);
perms.delete = permissionEvaluator.hasPermission(authentication, bean, BasePermission.DELETE);
perms.manage = permissionEvaluator.hasPermission(authentication, bean, BasePermission.ADMINISTRATION);
return perms;
}
}
return null;
}
/* (non-Javadoc)
* @see com.fasterxml.jackson.databind.ser.VirtualBeanPropertyWriter#withConfig(com.fasterxml.jackson.databind.cfg.MapperConfig, com.fasterxml.jackson.databind.introspect.AnnotatedClass, com.fasterxml.jackson.databind.introspect.BeanPropertyDefinition, com.fasterxml.jackson.databind.JavaType)
*/
@Override
public VirtualBeanPropertyWriter withConfig(MapperConfig<?> config, AnnotatedClass declaringClass, BeanPropertyDefinition propDef, JavaType type) {
return new CurrentPermissionsWriter(propDef, declaringClass.getAnnotations(), type);
}
}
/*
* Copyright 2017 Global Crop Diversity Trust
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package org.genesys.blocks.util;
import org.springframework.beans.BeansException;
import org.springframework.context.ApplicationContext;
import org.springframework.context.ApplicationContextAware;
/**
* https://stackoverflow.com/questions/28005761/how-to-access-a-method-a-spring-bean-from-a-class-not-in-the-spring-container/28005923#28005923
*/
public class CurrentApplicationContext implements ApplicationContextAware {
static ApplicationContext applicationContext = null;
public void setApplicationContext(ApplicationContext context) throws BeansException {
applicationContext = context;
}
/**
* Note that this is a static method which expose ApplicationContext
**/
public static ApplicationContext getContext() {
return applicationContext;
}
}
\ No newline at end of file
Markdown is supported
0% or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment