Search in sources :

Example 1 with ReflectionHelper

use of org.teiid.core.util.ReflectionHelper in project teiid by teiid.

the class MongoDBDirectQueryExecution method execute.

@Override
public void execute() throws TranslatorException {
    StringBuilder buffer = new StringBuilder();
    SQLStringVisitor.parseNativeQueryParts(query, arguments, buffer, new SQLStringVisitor.Substitutor() {

        @Override
        public void substitute(Argument arg, StringBuilder builder, int index) {
            Literal argumentValue = arg.getArgumentValue();
            builder.append(argumentValue.getValue());
        }
    });
    // $NON-NLS-1$
    StringTokenizer st = new StringTokenizer(buffer.toString(), ";");
    String collectionName = st.nextToken();
    // $NON-NLS-1$
    boolean shellOperation = collectionName.equalsIgnoreCase("$ShellCmd");
    String shellOperationName = null;
    if (shellOperation) {
        collectionName = st.nextToken();
        shellOperationName = st.nextToken();
    }
    DBCollection collection = this.mongoDB.getCollection(collectionName);
    if (collection == null) {
        throw new TranslatorException(MongoDBPlugin.Event.TEIID18020, MongoDBPlugin.Util.gs(MongoDBPlugin.Event.TEIID18020, collectionName));
    }
    if (shellOperation) {
        ArrayList<Object> operations = new ArrayList<Object>();
        while (st.hasMoreTokens()) {
            String token = st.nextToken();
            if (token.startsWith("{")) {
                // $NON-NLS-1$
                operations.add(JSON.parse(token));
            } else {
                operations.add(token);
            }
        }
        try {
            ReflectionHelper helper = new ReflectionHelper(DBCollection.class);
            Method method = helper.findBestMethodOnTarget(shellOperationName, operations.toArray(new Object[operations.size()]));
            Object result = method.invoke(collection, operations.toArray(new Object[operations.size()]));
            if (result instanceof Cursor) {
                this.results = (Cursor) result;
            } else if (result instanceof WriteResult) {
                WriteResult wr = (WriteResult) result;
                if (!wr.wasAcknowledged()) {
                    // throw error for unacknowledged write
                    throw new TranslatorException(wr.toString());
                }
            }
        } catch (NoSuchMethodException e) {
            throw new TranslatorException(MongoDBPlugin.Event.TEIID18034, e, MongoDBPlugin.Util.gs(MongoDBPlugin.Event.TEIID18034, buffer.toString()));
        } catch (SecurityException e) {
            throw new TranslatorException(MongoDBPlugin.Event.TEIID18034, e, MongoDBPlugin.Util.gs(MongoDBPlugin.Event.TEIID18034, buffer.toString()));
        } catch (IllegalAccessException e) {
            throw new TranslatorException(MongoDBPlugin.Event.TEIID18034, e, MongoDBPlugin.Util.gs(MongoDBPlugin.Event.TEIID18034, buffer.toString()));
        } catch (IllegalArgumentException e) {
            throw new TranslatorException(MongoDBPlugin.Event.TEIID18034, e, MongoDBPlugin.Util.gs(MongoDBPlugin.Event.TEIID18034, buffer.toString()));
        } catch (InvocationTargetException e) {
            throw new TranslatorException(MongoDBPlugin.Event.TEIID18034, e.getTargetException(), MongoDBPlugin.Util.gs(MongoDBPlugin.Event.TEIID18034, buffer.toString()));
        }
    } else {
        ArrayList<DBObject> operations = new ArrayList<DBObject>();
        while (st.hasMoreTokens()) {
            String token = st.nextToken();
            operations.add((DBObject) JSON.parse(token));
        }
        if (operations.isEmpty()) {
            throw new TranslatorException(MongoDBPlugin.Event.TEIID18021, MongoDBPlugin.Util.gs(MongoDBPlugin.Event.TEIID18021, collectionName));
        }
        this.results = collection.aggregate(operations, this.executionFactory.getOptions(this.executionContext.getBatchSize()));
    }
}
Also used : SQLStringVisitor(org.teiid.language.visitor.SQLStringVisitor) Argument(org.teiid.language.Argument) ArrayList(java.util.ArrayList) Cursor(com.mongodb.Cursor) DBObject(com.mongodb.DBObject) DBCollection(com.mongodb.DBCollection) Literal(org.teiid.language.Literal) ReflectionHelper(org.teiid.core.util.ReflectionHelper) Method(java.lang.reflect.Method) InvocationTargetException(java.lang.reflect.InvocationTargetException) StringTokenizer(java.util.StringTokenizer) WriteResult(com.mongodb.WriteResult) TranslatorException(org.teiid.translator.TranslatorException) DBObject(com.mongodb.DBObject)

Example 2 with ReflectionHelper

use of org.teiid.core.util.ReflectionHelper in project teiid by teiid.

the class FunctionTree method createFunctionDescriptor.

private FunctionDescriptor createFunctionDescriptor(FunctionMetadataSource source, FunctionMethod method, Class<?>[] types, boolean system) {
    // Get return type
    FunctionParameter outputParam = method.getOutputParameter();
    Class<?> outputType = null;
    if (outputParam != null) {
        outputType = DataTypeManager.getDataTypeClass(outputParam.getRuntimeType());
    }
    List<Class<?>> inputTypes = new ArrayList<Class<?>>(Arrays.asList(types));
    boolean hasWrappedArg = false;
    if (!system) {
        for (int i = 0; i < types.length; i++) {
            if (types[i] == DataTypeManager.DefaultDataClasses.VARBINARY) {
                hasWrappedArg = true;
                inputTypes.set(i, byte[].class);
            }
        }
    }
    if (method.isVarArgs()) {
        inputTypes.set(inputTypes.size() - 1, DataTypeManager.getArrayType(inputTypes.get(inputTypes.size() - 1)));
    }
    Method invocationMethod = method.getMethod();
    boolean requiresContext = false;
    // Defect 20007 - Ignore the invocation method if pushdown is not required.
    if (validateClass && (method.getPushdown() == PushDown.CAN_PUSHDOWN || method.getPushdown() == PushDown.CANNOT_PUSHDOWN)) {
        if (invocationMethod == null) {
            if (method.getInvocationClass() == null || method.getInvocationMethod() == null) {
                throw new MetadataException(QueryPlugin.Event.TEIID31123, QueryPlugin.Util.gs(QueryPlugin.Event.TEIID31123, method.getName()));
            }
            try {
                Class<?> methodClass = source.getInvocationClass(method.getInvocationClass());
                ReflectionHelper helper = new ReflectionHelper(methodClass);
                try {
                    invocationMethod = helper.findBestMethodWithSignature(method.getInvocationMethod(), inputTypes);
                } catch (NoSuchMethodException e) {
                    inputTypes.add(0, CommandContext.class);
                    invocationMethod = helper.findBestMethodWithSignature(method.getInvocationMethod(), inputTypes);
                    requiresContext = true;
                }
            } catch (ClassNotFoundException e) {
                throw new MetadataException(QueryPlugin.Event.TEIID30387, e, QueryPlugin.Util.gs(QueryPlugin.Event.TEIID30387, method.getName(), method.getInvocationClass()));
            } catch (NoSuchMethodException e) {
                throw new MetadataException(QueryPlugin.Event.TEIID30388, e, QueryPlugin.Util.gs(QueryPlugin.Event.TEIID30388, method, method.getInvocationClass(), method.getInvocationMethod()));
            } catch (Exception e) {
                throw new MetadataException(QueryPlugin.Event.TEIID30389, e, QueryPlugin.Util.gs(QueryPlugin.Event.TEIID30389, method, method.getInvocationClass(), method.getInvocationMethod()));
            }
        } else {
            requiresContext = (invocationMethod.getParameterTypes().length > 0 && org.teiid.CommandContext.class.isAssignableFrom(invocationMethod.getParameterTypes()[0]));
        }
        if (invocationMethod != null) {
            // Check return type is non void
            Class<?> methodReturn = invocationMethod.getReturnType();
            if (method.getAggregateAttributes() == null && methodReturn.equals(Void.TYPE)) {
                throw new MetadataException(QueryPlugin.Event.TEIID30390, QueryPlugin.Util.gs(QueryPlugin.Event.TEIID30390, method.getName(), invocationMethod));
            }
            // Check that method is public
            int modifiers = invocationMethod.getModifiers();
            if (!Modifier.isPublic(modifiers)) {
                throw new MetadataException(QueryPlugin.Event.TEIID30391, QueryPlugin.Util.gs(QueryPlugin.Event.TEIID30391, method.getName(), invocationMethod));
            }
            // Check that method is static
            if (!Modifier.isStatic(modifiers)) {
                if (method.getAggregateAttributes() == null) {
                    throw new MetadataException(QueryPlugin.Event.TEIID30392, QueryPlugin.Util.gs(QueryPlugin.Event.TEIID30392, method.getName(), invocationMethod));
                }
            } else if (method.getAggregateAttributes() != null) {
                throw new MetadataException(QueryPlugin.Event.TEIID30600, QueryPlugin.Util.gs(QueryPlugin.Event.TEIID30600, method.getName(), invocationMethod));
            }
            if (method.getAggregateAttributes() != null && !(UserDefinedAggregate.class.isAssignableFrom(invocationMethod.getDeclaringClass()))) {
                throw new MetadataException(QueryPlugin.Event.TEIID30601, QueryPlugin.Util.gs(QueryPlugin.Event.TEIID30601, method.getName(), method.getInvocationClass(), UserDefinedAggregate.class.getName()));
            }
            try {
                // turn off access checks for a small performance boost
                invocationMethod.setAccessible(true);
            } catch (SecurityException e) {
            // just ignore
            }
            method.setMethod(invocationMethod);
        }
    }
    FunctionDescriptor result = new FunctionDescriptor(method, types, outputType, invocationMethod, requiresContext, source.getClassLoader());
    if (validateClass && method.getAggregateAttributes() != null && (method.getPushdown() == PushDown.CAN_PUSHDOWN || method.getPushdown() == PushDown.CANNOT_PUSHDOWN)) {
        try {
            result.newInstance();
        } catch (FunctionExecutionException e) {
            // should only happen if the method is null / not found
            throw new MetadataException(QueryPlugin.Event.TEIID30387, e, QueryPlugin.Util.gs(QueryPlugin.Event.TEIID30387, method.getName(), method.getInvocationClass()));
        }
    }
    result.setHasWrappedArgs(hasWrappedArg);
    return result;
}
Also used : CommandContext(org.teiid.query.util.CommandContext) UserDefinedAggregate(org.teiid.UserDefinedAggregate) ReflectionHelper(org.teiid.core.util.ReflectionHelper) Method(java.lang.reflect.Method) FunctionMethod(org.teiid.metadata.FunctionMethod) MetadataException(org.teiid.metadata.MetadataException) MetadataException(org.teiid.metadata.MetadataException) FunctionExecutionException(org.teiid.api.exception.query.FunctionExecutionException) FunctionExecutionException(org.teiid.api.exception.query.FunctionExecutionException) FunctionParameter(org.teiid.metadata.FunctionParameter)

Aggregations

Method (java.lang.reflect.Method)2 ReflectionHelper (org.teiid.core.util.ReflectionHelper)2 Cursor (com.mongodb.Cursor)1 DBCollection (com.mongodb.DBCollection)1 DBObject (com.mongodb.DBObject)1 WriteResult (com.mongodb.WriteResult)1 InvocationTargetException (java.lang.reflect.InvocationTargetException)1 ArrayList (java.util.ArrayList)1 StringTokenizer (java.util.StringTokenizer)1 UserDefinedAggregate (org.teiid.UserDefinedAggregate)1 FunctionExecutionException (org.teiid.api.exception.query.FunctionExecutionException)1 Argument (org.teiid.language.Argument)1 Literal (org.teiid.language.Literal)1 SQLStringVisitor (org.teiid.language.visitor.SQLStringVisitor)1 FunctionMethod (org.teiid.metadata.FunctionMethod)1 FunctionParameter (org.teiid.metadata.FunctionParameter)1 MetadataException (org.teiid.metadata.MetadataException)1 CommandContext (org.teiid.query.util.CommandContext)1 TranslatorException (org.teiid.translator.TranslatorException)1