// Path: raidenjpa-core/src/main/java/org/raidenjpa/query/executor/QueryExecutor.java
// public class QueryExecutor {
// 
// 	private Integer maxResult;
// 	private int firstResult;
// 	private	Map<String, Object> parameters;
// 	private QueryParser queryParser; 
// 	
// 	public QueryExecutor(String jpql, Map<String, Object> parameters, Integer maxResult) {
// 		this.queryParser = new QueryParser(jpql);
// 		this.parameters = parameters;
// 		this.maxResult = maxResult;
// 		this.firstResult = 0;
// 	}
// 
// 	public QueryExecutor(QueryParser queryParser, Map<String, Object> parameters) {
// 		this.queryParser = queryParser;
// 		this.parameters = parameters;
// 	}
// 
// 	@FixMe("Which one is the first, group or order?")
// 	public List<?> getResultList() {
// 		showJpql();
// 		
// 		QueryResult queryResult = new QueryResult();
// 		
// 		executeFrom(queryResult);
// 		executeJoin(queryResult);
// 		executeWhere(queryResult);
// 		executeGroup(queryResult);
// 		executeOrderBy(queryResult);
// 		executeLimit(queryResult);
// 		
// 		return queryResult.getList(queryParser.getSelect(), queryParser.getGroupBy());
// 	}
// 
// 	private void executeGroup(QueryResult queryResult) {
// 		if (queryParser.getGroupBy() == null && !queryParser.getSelect().isThereAggregationFunction()) {
// 			return;
// 		}
// 		
// 		List<List<String>> paths = new ArrayList<List<String>>();
// 		if (queryParser.getGroupBy() == null) {
// 			paths.add(Arrays.asList("fake_aggregation_for_group_all_rows"));
// 		} else {
// 			for (GroupByElements groupByElements : queryParser.getGroupBy().getElements()) {
// 				paths.add(groupByElements.getPath());
// 			}
// 		}
// 		
// 		queryResult.group(paths);
// 	}
// 
// 	private void showJpql() {
// 		String jpql = queryParser.getWords().getJpql();
// 		for (Entry<String, Object> entry : parameters.entrySet()) {
// 			jpql = jpql.replaceAll(":" + entry.getKey(), entry.getValue().toString());
// 		}
// 	}
// 
// 	private void executeOrderBy(QueryResult queryResult) {
// 		queryResult.sort(queryParser.getOrderBy());
// 	}
// 
// 	@BadSmell("It is kind of confused. Put it in QueryResult")
// 	private void executeJoin(QueryResult queryResult) {
// 		if (queryResult.size() == 0) {
// 			return;
// 		}
// 
// 		for (JoinClause join : queryParser.getJoins()) {
// 			queryResult.join(join, queryParser.getWhere(), parameters);
// 		}
// 		
// 		// @FixMe - There is some case when IN is not equals to JOIN, study it
// 		for (FromClauseItem item : queryParser.getFrom().getItens()) {
// 			if (item.isInFrom()) {
// 				JoinClause join = new JoinClause();
// 				join.setAlias(item.getAliasName());
// 				join.setPath(item.getInPath());
// 				join.setWith(new WithClause());
// 				queryResult.join(join, queryParser.getWhere(), parameters);
// 			}
// 		}
// 	}
// 
// 	@FixMe("Execute limit before than group by is correct?")
// 	private void executeLimit(QueryResult queryResult) {
// 		queryResult.limit(firstResult, maxResult);
// 	}
// 
// 	private void executeWhere(QueryResult queryResult) {
// 		if (!queryParser.getWhere().hasElements()) {
// 			return;
// 		}
// 		
// 		LogicExpressionExecutor logicExpressionExecutor = new LogicExpressionExecutor(queryParser.getWhere().getLogicExpression(), parameters);
// 		
// 		Iterator<QueryResultRow> it = queryResult.iterator();
// 		while(it.hasNext()) {
// 			QueryResultRow row = it.next();
// 			if (!logicExpressionExecutor.match(row, true)) {
// 				it.remove();
// 			}
// 		}
// 	}
// 
// 	@BadSmell("Refactory")
// 	private void executeFrom(QueryResult queryResult) {
// 		FromClause from = queryParser.getFrom();
// 		
// 		for (FromClauseItem item : from.getItens()) {
// 			if (!item.isInFrom()) {
// 				List<Object> rowsInDB = InMemoryDB.me().getAll(item.getClassName());
// 				queryResult.addFrom(item.getAliasName(), rowsInDB);
// 			}
// 		}
// 	}
// 	
// 	public QueryExecutor setFirstResult(int first) {
// 		this.firstResult = first;
// 		return this;
// 	}
// } 


import java.util.List;
import java.util.Map;
import org.raidenjpa.query.executor.QueryExecutor;
import org.raidenjpa.util.FixMe;
		do {
			word = words.next();
			
			if (word.contains("(")) {
				parentheses++;
			} 
			
			if (word.contains("))")) {
				parentheses = parentheses - 2;
			} else if (word.contains(")")) {
				parentheses--;
			}
			
			if (word.equals(",")) {
				jpql += word;
			} else {
				jpql += " " + word;
			}
		} while(parentheses > 0);

		jpql = jpql.substring(1, jpql.length() - 1);
		
		queryParser = new QueryParser(jpql);
		
		if (queryParser.getSelect().getElements().size() > 1) {
			throw new RuntimeException("The subquery has more than one value in select: '" + jpql + "'");
		}
	}
	
	public List<?> getResultList(Map<String, Object> parameters) {
// Path: raidenjpa-core/src/main/java/org/raidenjpa/query/executor/QueryExecutor.java
// public class QueryExecutor {
// 
// 	private Integer maxResult;
// 	private int firstResult;
// 	private	Map<String, Object> parameters;
// 	private QueryParser queryParser; 
// 	
// 	public QueryExecutor(String jpql, Map<String, Object> parameters, Integer maxResult) {
// 		this.queryParser = new QueryParser(jpql);
// 		this.parameters = parameters;
// 		this.maxResult = maxResult;
// 		this.firstResult = 0;
// 	}
// 
// 	public QueryExecutor(QueryParser queryParser, Map<String, Object> parameters) {
// 		this.queryParser = queryParser;
// 		this.parameters = parameters;
// 	}
// 
// 	@FixMe("Which one is the first, group or order?")
// 	public List<?> getResultList() {
// 		showJpql();
// 		
// 		QueryResult queryResult = new QueryResult();
// 		
// 		executeFrom(queryResult);
// 		executeJoin(queryResult);
// 		executeWhere(queryResult);
// 		executeGroup(queryResult);
// 		executeOrderBy(queryResult);
// 		executeLimit(queryResult);
// 		
// 		return queryResult.getList(queryParser.getSelect(), queryParser.getGroupBy());
// 	}
// 
// 	private void executeGroup(QueryResult queryResult) {
// 		if (queryParser.getGroupBy() == null && !queryParser.getSelect().isThereAggregationFunction()) {
// 			return;
// 		}
// 		
// 		List<List<String>> paths = new ArrayList<List<String>>();
// 		if (queryParser.getGroupBy() == null) {
// 			paths.add(Arrays.asList("fake_aggregation_for_group_all_rows"));
// 		} else {
// 			for (GroupByElements groupByElements : queryParser.getGroupBy().getElements()) {
// 				paths.add(groupByElements.getPath());
// 			}
// 		}
// 		
// 		queryResult.group(paths);
// 	}
// 
// 	private void showJpql() {
// 		String jpql = queryParser.getWords().getJpql();
// 		for (Entry<String, Object> entry : parameters.entrySet()) {
// 			jpql = jpql.replaceAll(":" + entry.getKey(), entry.getValue().toString());
// 		}
// 	}
// 
// 	private void executeOrderBy(QueryResult queryResult) {
// 		queryResult.sort(queryParser.getOrderBy());
// 	}
// 
// 	@BadSmell("It is kind of confused. Put it in QueryResult")
// 	private void executeJoin(QueryResult queryResult) {
// 		if (queryResult.size() == 0) {
// 			return;
// 		}
// 
// 		for (JoinClause join : queryParser.getJoins()) {
// 			queryResult.join(join, queryParser.getWhere(), parameters);
// 		}
// 		
// 		// @FixMe - There is some case when IN is not equals to JOIN, study it
// 		for (FromClauseItem item : queryParser.getFrom().getItens()) {
// 			if (item.isInFrom()) {
// 				JoinClause join = new JoinClause();
// 				join.setAlias(item.getAliasName());
// 				join.setPath(item.getInPath());
// 				join.setWith(new WithClause());
// 				queryResult.join(join, queryParser.getWhere(), parameters);
// 			}
// 		}
// 	}
// 
// 	@FixMe("Execute limit before than group by is correct?")
// 	private void executeLimit(QueryResult queryResult) {
// 		queryResult.limit(firstResult, maxResult);
// 	}
// 
// 	private void executeWhere(QueryResult queryResult) {
// 		if (!queryParser.getWhere().hasElements()) {
// 			return;
// 		}
// 		
// 		LogicExpressionExecutor logicExpressionExecutor = new LogicExpressionExecutor(queryParser.getWhere().getLogicExpression(), parameters);
// 		
// 		Iterator<QueryResultRow> it = queryResult.iterator();
// 		while(it.hasNext()) {
// 			QueryResultRow row = it.next();
// 			if (!logicExpressionExecutor.match(row, true)) {
// 				it.remove();
// 			}
// 		}
// 	}
// 
// 	@BadSmell("Refactory")
// 	private void executeFrom(QueryResult queryResult) {
// 		FromClause from = queryParser.getFrom();
// 		
// 		for (FromClauseItem item : from.getItens()) {
// 			if (!item.isInFrom()) {
// 				List<Object> rowsInDB = InMemoryDB.me().getAll(item.getClassName());
// 				queryResult.addFrom(item.getAliasName(), rowsInDB);
// 			}
// 		}
// 	}
// 	
// 	public QueryExecutor setFirstResult(int first) {
// 		this.firstResult = first;
// 		return this;
// 	}
// } 


// Path: raidenjpa-core/src/main/java/org/raidenjpa/query/parser/ConditionSubQuery.java
import java.util.List;
import java.util.Map;
import org.raidenjpa.query.executor.QueryExecutor;
import org.raidenjpa.util.FixMe;

		do {
			word = words.next();
			
			if (word.contains("(")) {
				parentheses++;
			} 
			
			if (word.contains("))")) {
				parentheses = parentheses - 2;
			} else if (word.contains(")")) {
				parentheses--;
			}
			
			if (word.equals(",")) {
				jpql += word;
			} else {
				jpql += " " + word;
			}
		} while(parentheses > 0);

		jpql = jpql.substring(1, jpql.length() - 1);
		
		queryParser = new QueryParser(jpql);
		
		if (queryParser.getSelect().getElements().size() > 1) {
			throw new RuntimeException("The subquery has more than one value in select: '" + jpql + "'");
		}
	}
	
	public List<?> getResultList(Map<String, Object> parameters) {
		QueryExecutor queryExecutor = new QueryExecutor(queryParser, parameters);