Author: shawkins
Date: 2012-05-09 11:08:01 -0400 (Wed, 09 May 2012)
New Revision: 4078
Modified:
branches/7.7.x/build/kits/jboss-container/deploy/teiid/teiid-jboss-beans.xml
branches/7.7.x/engine/src/main/java/org/teiid/dqp/internal/process/AuthorizationValidator.java
branches/7.7.x/engine/src/main/java/org/teiid/dqp/internal/process/DefaultAuthorizationValidator.java
branches/7.7.x/engine/src/main/java/org/teiid/dqp/internal/process/PreparedStatementRequest.java
branches/7.7.x/engine/src/main/java/org/teiid/dqp/internal/process/Request.java
branches/7.7.x/engine/src/main/java/org/teiid/dqp/internal/process/RequestWorkItem.java
branches/7.7.x/engine/src/test/java/org/teiid/dqp/internal/process/TestRequest.java
Log:
TEIID-2009 allowing authorizationvalidator command modification
Modified: branches/7.7.x/build/kits/jboss-container/deploy/teiid/teiid-jboss-beans.xml
===================================================================
---
branches/7.7.x/build/kits/jboss-container/deploy/teiid/teiid-jboss-beans.xml 2012-05-09
14:36:12 UTC (rev 4077)
+++
branches/7.7.x/build/kits/jboss-container/deploy/teiid/teiid-jboss-beans.xml 2012-05-09
15:08:01 UTC (rev 4078)
@@ -154,7 +154,7 @@
<bean name="AuthorizationValidator"
class="org.teiid.dqp.internal.process.DefaultAuthorizationValidator">
<!-- Turn on authorization checking (default true) -->
<property name="enabled">true</property>
- <!-- The policy decider to use. (default AuthorizationValidator).
+ <!-- The policy decider to use. (default
org.teiid.dqp.internal.process.DataRolePolicyDecider).
This instance may be changed to another org.teiid.PolicyDecider if needed.
-->
<property name="policyDecider"><inject
bean="PolicyDecider"/></property>
Modified:
branches/7.7.x/engine/src/main/java/org/teiid/dqp/internal/process/AuthorizationValidator.java
===================================================================
---
branches/7.7.x/engine/src/main/java/org/teiid/dqp/internal/process/AuthorizationValidator.java 2012-05-09
14:36:12 UTC (rev 4077)
+++
branches/7.7.x/engine/src/main/java/org/teiid/dqp/internal/process/AuthorizationValidator.java 2012-05-09
15:08:01 UTC (rev 4078)
@@ -33,8 +33,34 @@
*/
public interface AuthorizationValidator {
- void validate(Command command, QueryMetadataInterface metadata, CommandContext
commandContext) throws QueryValidatorException, TeiidComponentException;
+ enum CommandType {
+ USER,
+ PREPARED,
+ CACHED
+ }
+ /**
+ * Validates the given command. If the command is not a {@link CommandType#USER}
command, the command object should not be modified.
+ * Any modification must be fully resolved using the associated {@link
QueryMetadataInterface}. Returning true for a
+ * {@link CommandType#PREPARED} or {@link CommandType#CACHED} commands means that the
matching prepared plan or cache entry
+ * will not be used.
+ * @param originalSql array of commands will typically contain only a single string, but
may have multiple for batched updates.
+ * @param command the parsed and resolved command.
+ * @param metadata
+ * @param commandContext
+ * @param commandType
+ * @return true if the USER command was modified, or if the non-USER command should be
modified.
+ * @throws QueryValidatorException
+ * @throws TeiidComponentException
+ */
+ boolean validate(String[] originalSql, Command command, QueryMetadataInterface metadata,
CommandContext commandContext, CommandType commandType) throws QueryValidatorException,
TeiidComponentException;
+
+ /**
+ *
+ * @param roleName
+ * @param commandContext
+ * @return true if the current user has the given role
+ */
boolean hasRole(String roleName, CommandContext commandContext);
boolean isEnabled();
Modified:
branches/7.7.x/engine/src/main/java/org/teiid/dqp/internal/process/DefaultAuthorizationValidator.java
===================================================================
---
branches/7.7.x/engine/src/main/java/org/teiid/dqp/internal/process/DefaultAuthorizationValidator.java 2012-05-09
14:36:12 UTC (rev 4077)
+++
branches/7.7.x/engine/src/main/java/org/teiid/dqp/internal/process/DefaultAuthorizationValidator.java 2012-05-09
15:08:01 UTC (rev 4078)
@@ -41,11 +41,15 @@
}
@Override
- public void validate(Command command, QueryMetadataInterface metadata, CommandContext
commandContext) throws QueryValidatorException, TeiidComponentException {
+ public boolean validate(String[] originalSql, Command command,
+ QueryMetadataInterface metadata, CommandContext commandContext,
+ CommandType commandType) throws QueryValidatorException,
+ TeiidComponentException {
if (enabled && policyDecider.validateCommand(commandContext)) {
AuthorizationValidationVisitor visitor = new
AuthorizationValidationVisitor(this.policyDecider, commandContext);
Request.validateWithVisitor(visitor, metadata, command);
}
+ return false;
}
@Override
Modified:
branches/7.7.x/engine/src/main/java/org/teiid/dqp/internal/process/PreparedStatementRequest.java
===================================================================
---
branches/7.7.x/engine/src/main/java/org/teiid/dqp/internal/process/PreparedStatementRequest.java 2012-05-09
14:36:12 UTC (rev 4077)
+++
branches/7.7.x/engine/src/main/java/org/teiid/dqp/internal/process/PreparedStatementRequest.java 2012-05-09
15:08:01 UTC (rev 4078)
@@ -35,6 +35,7 @@
import org.teiid.core.TeiidComponentException;
import org.teiid.core.TeiidProcessingException;
import org.teiid.core.types.DataTypeManager;
+import org.teiid.dqp.internal.process.AuthorizationValidator.CommandType;
import org.teiid.dqp.internal.process.SessionAwareCache.CacheID;
import org.teiid.logging.LogConstants;
import org.teiid.logging.LogManager;
@@ -131,6 +132,21 @@
String sqlQuery = requestMsg.getCommands()[0];
CacheID id = new CacheID(this.workContext, Request.createParseInfo(this.requestMsg),
sqlQuery);
prepPlan = prepPlanCache.get(id);
+
+ if (prepPlan != null) {
+ ProcessorPlan cachedPlan = prepPlan.getPlan();
+ this.userCommand = prepPlan.getCommand();
+ if (validateAccess(requestMsg.getCommands(), userCommand, CommandType.PREPARED))
{
+ LogManager.logDetail(LogConstants.CTX_DQP, requestId,
"AuthorizationValidator indicates that the prepared plan for command will not be
used"); //$NON-NLS-1$
+ prepPlan = null;
+ } else {
+ LogManager.logTrace(LogConstants.CTX_DQP, new Object[] { "Query exist in
cache: ", sqlQuery }); //$NON-NLS-1$
+ processPlan = cachedPlan.clone();
+ //already in cache. obtain the values from cache
+ analysisRecord = prepPlan.getAnalysisRecord();
+ }
+ }
+
if (prepPlan == null) {
//if prepared plan does not exist, create one
prepPlan = new PreparedPlan();
@@ -149,15 +165,7 @@
}
this.prepPlanCache.put(id, determinismLevel, prepPlan,
userCommand.getCacheHint() != null?userCommand.getCacheHint().getTtl():null);
- }
- } else {
- ProcessorPlan cachedPlan = prepPlan.getPlan();
- this.userCommand = prepPlan.getCommand();
- validateAccess(userCommand);
- LogManager.logTrace(LogConstants.CTX_DQP, new Object[] { "Query exist in
cache: ", sqlQuery }); //$NON-NLS-1$
- processPlan = cachedPlan.clone();
- //already in cache. obtain the values from cache
- analysisRecord = prepPlan.getAnalysisRecord();
+ }
}
if (requestMsg.isBatchedUpdate()) {
Modified: branches/7.7.x/engine/src/main/java/org/teiid/dqp/internal/process/Request.java
===================================================================
---
branches/7.7.x/engine/src/main/java/org/teiid/dqp/internal/process/Request.java 2012-05-09
14:36:12 UTC (rev 4077)
+++
branches/7.7.x/engine/src/main/java/org/teiid/dqp/internal/process/Request.java 2012-05-09
15:08:01 UTC (rev 4078)
@@ -47,6 +47,7 @@
import org.teiid.core.types.DataTypeManager;
import org.teiid.core.util.Assertion;
import org.teiid.dqp.internal.datamgr.ConnectorManagerRepository;
+import org.teiid.dqp.internal.process.AuthorizationValidator.CommandType;
import org.teiid.dqp.internal.process.multisource.MultiSourceCapabilitiesFinder;
import org.teiid.dqp.internal.process.multisource.MultiSourceMetadataWrapper;
import org.teiid.dqp.internal.process.multisource.MultiSourcePlanToProcessConverter;
@@ -289,8 +290,6 @@
//ensure that the user command is distinct from the processing command
//rewrite and planning may alter options, symbols, etc.
QueryResolver.resolveCommand(command, metadata);
-
- this.userCommand = (Command)command.clone();
}
private void validateQuery(Command command)
@@ -391,8 +390,10 @@
resolveCommand(command);
- validateAccess(userCommand);
+ validateAccess(requestMsg.getCommands(), command, CommandType.USER);
+ this.userCommand = (Command) command.clone();
+
Collection<GroupSymbol> groups = GroupCollectorVisitor.getGroups(command,
true);
for (GroupSymbol groupSymbol : groups) {
if (groupSymbol.isTempTable()) {
@@ -470,11 +471,14 @@
this.context.setValidateXML(requestMsg.getValidationMode());
}
- protected void validateAccess(Command command) throws QueryValidatorException,
TeiidComponentException {
- createCommandContext(command);
+ protected boolean validateAccess(String[] commandStr, Command command, CommandType type)
throws QueryValidatorException, TeiidComponentException {
+ if (context == null) {
+ createCommandContext(command);
+ }
if (this.authorizationValidator != null) {
- this.authorizationValidator.validate(command, metadata, context);
+ return this.authorizationValidator.validate(commandStr, command, metadata, context,
type);
}
+ return false;
}
public void setExecutor(Executor executor) {
Modified:
branches/7.7.x/engine/src/main/java/org/teiid/dqp/internal/process/RequestWorkItem.java
===================================================================
---
branches/7.7.x/engine/src/main/java/org/teiid/dqp/internal/process/RequestWorkItem.java 2012-05-09
14:36:12 UTC (rev 4077)
+++
branches/7.7.x/engine/src/main/java/org/teiid/dqp/internal/process/RequestWorkItem.java 2012-05-09
15:08:01 UTC (rev 4078)
@@ -50,6 +50,7 @@
import org.teiid.core.TeiidProcessingException;
import org.teiid.core.TeiidRuntimeException;
import org.teiid.core.types.DataTypeManager;
+import org.teiid.dqp.internal.process.AuthorizationValidator.CommandType;
import org.teiid.dqp.internal.process.DQPCore.CompletionListener;
import org.teiid.dqp.internal.process.DQPCore.FutureWork;
import org.teiid.dqp.internal.process.DQPWorkContext.Version;
@@ -504,9 +505,11 @@
this.resultsBuffer = cr.getResults();
request.initMetadata();
this.originalCommand = cr.getCommand(requestMsg.getCommandString(),
request.metadata, pi);
- request.validateAccess(this.originalCommand);
- this.doneProducingBatches();
- return;
+ if (!request.validateAccess(requestMsg.getCommands(), this.originalCommand,
CommandType.CACHED)) {
+ this.doneProducingBatches();
+ return;
+ }
+ LogManager.logDetail(LogConstants.CTX_DQP, requestID, "Cached result command
to be modified, will not use the cached results", cacheId); //$NON-NLS-1$
}
} else {
LogManager.logDetail(LogConstants.CTX_DQP, requestID, "Parameters are not
serializable - cache cannot be used for", cacheId); //$NON-NLS-1$
Modified:
branches/7.7.x/engine/src/test/java/org/teiid/dqp/internal/process/TestRequest.java
===================================================================
---
branches/7.7.x/engine/src/test/java/org/teiid/dqp/internal/process/TestRequest.java 2012-05-09
14:36:12 UTC (rev 4077)
+++
branches/7.7.x/engine/src/test/java/org/teiid/dqp/internal/process/TestRequest.java 2012-05-09
15:08:01 UTC (rev 4078)
@@ -35,6 +35,7 @@
import org.teiid.core.TeiidProcessingException;
import org.teiid.dqp.internal.datamgr.ConnectorManagerRepository;
import org.teiid.dqp.internal.datamgr.FakeTransactionService;
+import org.teiid.dqp.internal.process.AuthorizationValidator.CommandType;
import org.teiid.dqp.service.AutoGenDataService;
import org.teiid.query.metadata.QueryMetadataInterface;
import org.teiid.query.parser.QueryParser;
@@ -89,10 +90,9 @@
drpd.setAllowFunctionCallsByDefault(true);
drav.setPolicyDecider(drpd);
request.setAuthorizationValidator(drav);
- request.validateAccess(command);
+ request.validateAccess(new String[] {QUERY}, command, CommandType.USER);
}
-
/**
* Test Request.processRequest().
* Test processing the same query twice, and make sure that doesn't cause
problems.
@@ -166,7 +166,7 @@
DQPWorkContext workContext = RealMetadataFactory.buildWorkContext(metadata,
RealMetadataFactory.example1VDB());
message.setStatementType(StatementType.PREPARED);
- message.setParameterValues(new ArrayList());
+ message.setParameterValues(new ArrayList<Object>());
helpProcessMessage(message, cache, workContext);
@@ -174,7 +174,7 @@
//If this doesn't throw an exception, assume it was successful.
message = new RequestMessage(QUERY);
message.setStatementType(StatementType.PREPARED);
- message.setParameterValues(new ArrayList());
+ message.setParameterValues(new ArrayList<Object>());
helpProcessMessage(message, cache, workContext);
}