Package org.geoserver.xacml.role

Source Code of org.geoserver.xacml.role.XACMLDefaultRoleAuthority

/* Copyright (c) 2001 - 2007 TOPP - www.openplans.org. All rights reserved.
* This code is licensed under the GPL 2.0 license, available at the root
* application directory.
*/
package org.geoserver.xacml.role;

import java.beans.BeanInfo;
import java.beans.IntrospectionException;
import java.beans.Introspector;
import java.beans.PropertyDescriptor;
import java.io.Serializable;
import java.net.URI;
import java.net.URISyntaxException;
import java.util.ArrayList;
import java.util.Date;
import java.util.HashSet;
import java.util.List;
import java.util.Set;

import org.acegisecurity.Authentication;
import org.acegisecurity.GrantedAuthority;
import org.acegisecurity.userdetails.UserDetails;
import org.geoserver.xacml.geoxacml.GeoXACMLConfig;
import org.geoserver.xacml.geoxacml.XACMLConstants;
import org.geoserver.xacml.geoxacml.XACMLUtil;
import org.geotools.xacml.geoxacml.attr.GMLVersion;
import org.geotools.xacml.geoxacml.attr.GeometryAttribute;

import com.sun.xacml.Obligation;
import com.sun.xacml.attr.AnyURIAttribute;
import com.sun.xacml.attr.AttributeValue;
import com.sun.xacml.attr.BooleanAttribute;
import com.sun.xacml.attr.DateTimeAttribute;
import com.sun.xacml.attr.DoubleAttribute;
import com.sun.xacml.attr.IntegerAttribute;
import com.sun.xacml.attr.StringAttribute;
import com.sun.xacml.ctx.Attribute;
import com.sun.xacml.ctx.RequestCtx;
import com.sun.xacml.ctx.ResponseCtx;
import com.sun.xacml.ctx.Result;
import com.vividsolutions.jts.geom.Geometry;

/**
* Acegi implementation for {@link XACMLRoleAuthority}
*
*
* @author Christian Mueller
*
*/
public class XACMLDefaultRoleAuthority implements XACMLRoleAuthority {

    private static InheritableThreadLocal<Set<Authentication>> AlreadyPrepared = new InheritableThreadLocal<Set<Authentication>>();

    public <T extends UserDetails> void transformUserDetails(T details) {
        for (int i = 0; i < details.getAuthorities().length; i++) {
            details.getAuthorities()[i] = new XACMLRole(details.getAuthorities()[i].getAuthority());
        }
    }

    public void prepareRoles(Authentication auth) {

        // Trying to avoid multiple processing within one thread, result cannot change
        if (AlreadyPrepared.get() == null) {
            AlreadyPrepared.set(new HashSet<Authentication>());
        }

        if (AlreadyPrepared.get().contains(auth)) {
            return; // nothing todo
        }
        List<RequestCtx> requests = new ArrayList<RequestCtx>(auth.getAuthorities().length);
        String userName = null;
        if (auth.getPrincipal() instanceof UserDetails)
            userName = ((UserDetails) auth.getPrincipal()).getUsername();
        if (auth.getPrincipal() instanceof String) {
            userName = auth.getPrincipal().toString();
        }

        for (GrantedAuthority ga : auth.getAuthorities()) {
            requests.add(GeoXACMLConfig.getRequestCtxBuilderFactory()
                    .getXACMLRoleRequestCtxBuilder((XACMLRole) ga, userName).createRequestCtx());
        }

        List<ResponseCtx> responses = GeoXACMLConfig.getXACMLTransport().evaluateRequestCtxList(
                requests);

        outer: for (int i = 0; i < responses.size(); i++) {
            ResponseCtx response = responses.get(i);
            XACMLRole role = (XACMLRole) auth.getAuthorities()[i];
            for (Result result : response.getResults()) {
                if (result.getDecision() != Result.DECISION_PERMIT) {
                    role.setEnabled(false);
                    continue outer;
                }
                role.setEnabled(true);
                setUserProperties(auth, result, role);
            }

        }
        AlreadyPrepared.get().add(auth); // avoid further processing within one thread
    }

    private void setUserProperties(Authentication auth, Result result, XACMLRole role) {

        if (role.isRoleAttributesProcessed())
            return; // already done

        if (auth.getPrincipal() == null || auth.getPrincipal() instanceof String) {
            role.setRoleAttributesProcessed(true);
            return;
        }

        for (Obligation obligation : result.getObligations()) {
            if (XACMLConstants.UserPropertyObligationId.equals(obligation.getId().toString()))
                setRoleParamsFromUserDetails(auth, obligation, role);
            if (XACMLConstants.RoleConstantObligationId.equals(obligation.getId().toString()))
                setRoleParamsFromConstants(obligation, role);

        }
        role.setRoleAttributesProcessed(true);
    }

    private void setRoleParamsFromConstants(Obligation obligation, XACMLRole role) {
        for (Attribute attr : obligation.getAssignments()) {
            role.getAttributes().add(attr);
        }
    }

    private void setRoleParamsFromUserDetails(Authentication auth, Obligation obligation,
            XACMLRole role) {

        BeanInfo bi = null;
        try {
            bi = Introspector.getBeanInfo(auth.getPrincipal().getClass());
        } catch (IntrospectionException e) {
            throw new RuntimeException(e);
        }

        for (Attribute attr : obligation.getAssignments()) {
            String propertyName = ((StringAttribute) attr.getValue()).getValue();
            for (PropertyDescriptor pd : bi.getPropertyDescriptors()) {
                if (pd.getName().equals(propertyName)) {
                    Serializable value = null;
                    try {
                        Object tmp = pd.getReadMethod().invoke(auth.getPrincipal(), new Object[0]);
                        if (tmp == null)
                            continue;
                        if (tmp instanceof Serializable == false) {
                            throw new RuntimeException("Role params must be serializable, "
                                    + tmp.getClass() + " is not");
                        }
                        value = (Serializable) tmp;
                    } catch (Exception e) {
                        throw new RuntimeException(e);
                    }
                    // special check for geometries
                    if (value instanceof Geometry) {
                        if (((Geometry) value).getUserData() == null)
                            throw new RuntimeException("Property: " + propertyName
                                    + " : Geometry must have srs name as userdata");
                    }
                    AttributeValue attrValue = createAttributeValueFromObject(value);
                    Attribute xacmlAttr = new Attribute(attr.getId(), null, null, attrValue);
                    role.getAttributes().add(xacmlAttr);
                }
            }
        }

    }

    protected AttributeValue createAttributeValueFromObject(Serializable object) {
        AttributeValue retVal = null;

        if (object instanceof String)
            retVal = new StringAttribute((String) object);
        if (object instanceof URI)
            retVal = new AnyURIAttribute((URI) object);
        if (object instanceof Boolean)
            retVal = ((Boolean) object) ? BooleanAttribute.getTrueInstance() : BooleanAttribute
                    .getFalseInstance();
        if (object instanceof Double)
            retVal = new DoubleAttribute((Double) object);
        if (object instanceof Float)
            retVal = new DoubleAttribute((Float) object);
        if (object instanceof Integer)
            retVal = new IntegerAttribute((Integer) object);
        if (object instanceof Date)
            retVal = new DateTimeAttribute((Date) object);
        if (object instanceof Geometry) {
            Geometry g = (Geometry) object;
            String gmlType = XACMLUtil.getGMLTypeFor(g);
            try {
                retVal = new GeometryAttribute(g, g.getUserData().toString(), null,
                        GMLVersion.Version3, gmlType);
            } catch (URISyntaxException e) {
                throw new RuntimeException(e);
            }
        }

        return retVal;
    }

}
TOP

Related Classes of org.geoserver.xacml.role.XACMLDefaultRoleAuthority

TOP
Copyright © 2018 www.massapi.com. All rights reserved.
All source code are property of their respective owners. Java is a trademark of Sun Microsystems, Inc and owned by ORACLE Inc. Contact coftware#gmail.com.