int main (int argc, char* argv[]) { char *result; READ_OPTIONS_AND_INIT("testrewriter", "Run all stages on input and output rewritten SQL."); START_TIMER("TOTAL"); // read from terminal if (getStringOption("input.sql") == NULL) { result = rewriteQueryFromStream(stdin); ERROR_LOG("REWRITE RESULT FROM STREAM IS <%s>", result); } // parse input string else { result = rewriteQuery(getStringOption("input.sql")); ERROR_LOG("REWRITE RESULT FROM STRING IS:\n%s", result); } // call executor execute(result); STOP_TIMER("TOTAL"); OUT_TIMERS(); shutdownApplication(); // freeOptions(); // destroyMemManager(); return EXIT_SUCCESS; }
/** * Rewrites the expression rooted in ep so that it is in a form * that a query processor can evaluate while referencing only * state that is contained in the query processor or supplied * to the query processor in the form of arguments to the query. * For instance, a reference to a local variable in the scope * containing the query expression will be rewritten into a * reference to a (synthetic) parameter of the query expression. * This is similar to the way lambda expressions capture variables * from their enclosing environment. * Note that rewriting implies allocating new objects. * The original construct is not mutated in any way. * If the original construct is already in the right form, it is * returned as is. */ ExpressionPtr CaptureExtractor::rewrite(ExpressionPtr ep) { assert(ep != nullptr); switch (ep->getKindOf()) { case Expression::KindOfQueryExpression: { return rewriteQuery(static_pointer_cast<QueryExpression>(ep)); } case Expression::KindOfSelectClause: { // leave select clauses alone, another visitor deals with them. return ep; } case Expression::KindOfFromClause: case Expression::KindOfLetClause: case Expression::KindOfIntoClause: case Expression::KindOfWhereClause: { return rewriteSimpleClause(static_pointer_cast<SimpleQueryClause>(ep)); } case Expression::KindOfGroupClause: case Expression::KindOfJoinClause: case Expression::KindOfOrderbyClause: case Expression::KindOfOrdering: { // leave these alone. they are query specific and not parameterizable. return ep; } case Expression::KindOfObjectPropertyExpression: { return rewriteObjectProperty( static_pointer_cast<ObjectPropertyExpression>(ep)); } case Expression::KindOfSimpleFunctionCall: { return rewriteCall(static_pointer_cast<SimpleFunctionCall>(ep)); } case Expression::KindOfScalarExpression: { // Leave scalars alone. If the query processor can't handle them // rewriting won't help. return ep; } case Expression::KindOfUnaryOpExpression: { return rewriteUnary(static_pointer_cast<UnaryOpExpression>(ep)); } case Expression::KindOfBinaryOpExpression: { return rewriteBinary(static_pointer_cast<BinaryOpExpression>(ep)); } case Expression::KindOfSimpleVariable: { return rewriteSimpleVariable(static_pointer_cast<SimpleVariable>(ep)); } case Expression::KindOfExpressionList: { return rewriteExpressionList(static_pointer_cast<ExpressionList>(ep)); } default: { // If we get here, the expression is not a candidate for evaluation // by the query processor, so just turn it into a query parameter. return newQueryParamRef(ep); } } }