/* The contents of this file are subject to the license and copyright terms
* detailed in the license directory at the root of the source tree (also
* available online at http://fedora-commons.org/license/).
*/
package org.fcrepo.server.security.xacml.pdp.decorator;
import java.io.InputStream;
import java.lang.reflect.InvocationTargetException;
import java.lang.reflect.Method;
import java.util.Date;
import javax.ws.rs.core.StreamingOutput;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.fcrepo.server.Context;
import org.fcrepo.server.errors.ServerException;
import org.fcrepo.server.management.Management;
import org.fcrepo.server.storage.types.Datastream;
import org.fcrepo.server.storage.types.RelationshipTuple;
import org.fcrepo.server.storage.types.Validation;
/**
* Used to provide an explicitly paramterised view of API-M methods that affect the policy cache
*
* Note: this is not strictly an implementation of Management, but using this interface ensures
* a build error will be generated if Management changes and any new or modified methods are not
* catered for by the decorator.
*
* Constructor locates the equivalent API-M method in this class, and invokes it.
*
* Invoking the method pulls out the relevant method parameters, and determines what
* kind of operation it is.
*
* Methods that do not affect the policy cache should set action to NA
*
* @author Stephen Bayliss
* @version $Id$
*/
public class ManagementMethodInvocation
implements Management {
/** Logger for this class. */
private static Logger LOG =
LoggerFactory.getLogger(ManagementMethodInvocation.class.getName());
// represents the type of operation
public static enum Action {
CREATE,
READ,
UPDATE,
DELETE,
NA
}
public Action action = null;
// represents the overall target of the operation
public static enum Target {
DIGITALOBJECT,
DATASTREAM,
OTHER
}
public Target target = null;
// represents the component of the Target
public static enum Component {
CONTENT,
STATE,
OTHER
}
public Component component = null;
// parameters of the method (only the ones relevant to operations on policy objects are included)
public class Parameters {
public Context context = null;
public String pid = null;
public String dsID = null;
public String dsState = null;
public String objectState = null;
}
public Parameters parameters = new Parameters();
@SuppressWarnings("unused")
private ManagementMethodInvocation() {
}
/**
* Given an API-M method and arguments, locate the same method in this class and invoke it,
* populating the method parameters and classifying the method in terms of the kind of action
* and the kind of resource it is operating on.
*
* @param method
* @param args
* @throws InvocationTargetException
*/
public ManagementMethodInvocation(Method method, Object[] args) throws InvocationTargetException {
// get methods of this class
Method methods[] = this.getClass().getMethods();
// find the equivalent method in this class to method given in constructor
Method targetMethod = null;
for (int i = 0; i < methods.length; i++ ) {
if (methods[i].getName().equals(method.getName())) {
targetMethod = method;
break;
}
}
if (targetMethod == null) {
LOG.warn("Method " + method.getName() + " not found");
throw new InvocationTargetException(new Exception("Method not found"));
}
// invoke the method
try {
targetMethod.invoke(this, args);
// or can we just do
// method.invoke(this, args)?
} catch (Exception e) {
LOG.warn("Execution failed for method " + method.getName());
throw new InvocationTargetException(e);
}
}
@Override
public String addDatastream(Context context,
String pid,
String dsID,
String[] altIDs,
String dsLabel,
boolean versionable,
String mimeType,
String formatURI,
String dsLocation,
String controlGroup,
String dsState,
String checksumType,
String checksum,
String logMessage) throws ServerException {
action = Action.CREATE;
target = Target.DATASTREAM;
component = Component.CONTENT;
parameters.context = context;
parameters.pid = pid;
parameters.dsID = dsID;
parameters.dsState = dsState;
return null;
}
@Override
public boolean addRelationship(Context context,
String subject,
String relationship,
String object,
boolean isLiteral,
String datatype) throws ServerException {
action = Action.NA;
return false;
}
@Override
public String compareDatastreamChecksum(Context context,
String pid,
String dsID,
Date asOfDateTime)
throws ServerException {
action = Action.NA;
return null;
}
@Override
public InputStream export(Context context,
String pid,
String format,
String exportContext,
String encoding) throws ServerException {
action = Action.NA;
return null;
}
@Override
public StreamingOutput stream(Context context,
String pid,
String format,
String exportContext,
String encoding) throws ServerException {
action = Action.NA;
return null;
}
@Override
public Datastream getDatastream(Context context,
String pid,
String dsID,
Date asOfDateTime) throws ServerException {
action = Action.NA;
return null;
}
@Override
public Datastream[] getDatastreamHistory(Context context,
String pid,
String dsID)
throws ServerException {
action = Action.NA;
return null;
}
@Override
public Datastream[] getDatastreams(Context context,
String pid,
Date asOfDateTime,
String dsState) throws ServerException {
action = Action.NA;
return null;
}
@Override
public String[] getNextPID(Context context, int numPIDs, String namespace)
throws ServerException {
action = Action.NA;
return null;
}
@Override
public InputStream getObjectXML(Context context, String pid, String encoding)
throws ServerException {
action = Action.NA;
return null;
}
@Override
public RelationshipTuple[] getRelationships(Context context,
String subject,
String relationship)
throws ServerException {
action = Action.NA;
return null;
}
@Override
public InputStream getTempStream(String id) throws ServerException {
action = Action.NA;
return null;
}
@Override
public String ingest(Context context,
InputStream serialization,
String logMessage,
String format,
String encoding,
String newPid) throws ServerException {
action = Action.CREATE;
target = Target.DIGITALOBJECT;
component = Component.CONTENT;
parameters.context = context;
return null;
}
@Override
public Date modifyDatastreamByReference(Context context,
String pid,
String dsID,
String[] altIDs,
String dsLabel,
String mimeType,
String formatURI,
String dsLocation,
String checksumType,
String checksum,
String logMessage,
Date lastModifiedDate)
throws ServerException {
action = Action.UPDATE;
target = Target.DATASTREAM;
component = Component.CONTENT;
parameters.context = context;
parameters.pid = pid;
parameters.dsID = dsID;
return null;
}
@Override
public Date modifyDatastreamByValue(Context context,
String pid,
String dsID,
String[] altIDs,
String dsLabel,
String mimeType,
String formatURI,
InputStream dsContent,
String checksumType,
String checksum,
String logMessage,
Date lastModifiedDate) throws ServerException {
action = Action.UPDATE;
target = Target.DATASTREAM;
component = Component.CONTENT;
parameters.context = context;
parameters.pid = pid;
parameters.dsID = dsID;
return null;
}
@Override
public Date modifyObject(Context context,
String pid,
String state,
String label,
String ownerID,
String logMessage,
Date lastModifiedDate) throws ServerException {
action = Action.UPDATE;
target = Target.DIGITALOBJECT;
component = Component.STATE;
parameters.context = context;
parameters.pid = pid;
parameters.objectState = state;
return null;
}
@Override
public Date[] purgeDatastream(Context context,
String pid,
String dsID,
Date startDT,
Date endDT,
String logMessage) throws ServerException {
action = Action.DELETE;
target = Target.DATASTREAM;
component = Component.CONTENT;
parameters.context = context;
parameters.pid = pid;
parameters.dsID = dsID;
return null;
}
@Override
public Date purgeObject(Context context,
String pid,
String logMessage) throws ServerException {
action = Action.DELETE;
target = Target.DIGITALOBJECT;
component = Component.CONTENT;
parameters.context = context;
parameters.pid = pid;
return null;
}
@Override
public boolean purgeRelationship(Context context,
String subject,
String relationship,
String object,
boolean isLiteral,
String datatype) throws ServerException {
action = Action.NA;
return false;
}
@Override
public String putTempStream(Context context, InputStream in)
throws ServerException {
action = Action.NA;
return null;
}
@Override
public Date setDatastreamState(Context context,
String pid,
String dsID,
String dsState,
String logMessage) throws ServerException {
action = Action.UPDATE;
target = Target.DATASTREAM;
component = Component.STATE;
parameters.context = context;
parameters.pid = pid;
parameters.dsID = dsID;
parameters.dsState = dsState;
return null;
}
@Override
public Date setDatastreamVersionable(Context context,
String pid,
String dsID,
boolean versionable,
String logMessage)
throws ServerException {
action = Action.NA;
return null;
}
@Override
public Validation validate(Context context, String pid, Date asOfDateTime)
throws ServerException {
action = Action.NA;
return null;
}
}