Please wait. This can take some minutes ...
Many resources are needed to download a project. Please understand that we have to compensate our server costs. Thank you in advance.
Project price only 1 $
You can buy this project and download/modify it how often you want.
br.com.anteros.persistence.handler.MultiSelectHandler Maven / Gradle / Ivy
package br.com.anteros.persistence.handler;
import java.sql.ResultSet;
import java.sql.SQLException;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import br.com.anteros.core.utils.ObjectUtils;
import br.com.anteros.persistence.metadata.EntityCache;
import br.com.anteros.persistence.session.SQLSession;
import br.com.anteros.persistence.session.cache.PersistenceMetadataCache;
import br.com.anteros.persistence.session.cache.SQLCache;
import br.com.anteros.persistence.session.cache.WeakReferenceSQLCache;
import br.com.anteros.persistence.session.lock.LockOptions;
import br.com.anteros.persistence.session.query.SQLQueryAnalyzer;
import br.com.anteros.persistence.session.query.SQLQueryAnalyzerException;
import br.com.anteros.persistence.session.query.SQLQueryAnalyzerResult;
import br.com.anteros.persistence.sql.command.Select;
import br.com.anteros.persistence.sql.format.SqlFormatRule;
import br.com.anteros.persistence.sql.parser.INode;
import br.com.anteros.persistence.sql.parser.ParserUtil;
import br.com.anteros.persistence.sql.parser.SqlParser;
import br.com.anteros.persistence.sql.parser.node.ColumnNode;
import br.com.anteros.persistence.sql.parser.node.FunctionNode;
import br.com.anteros.persistence.sql.parser.node.RootNode;
import br.com.anteros.persistence.sql.parser.node.SelectNode;
import br.com.anteros.persistence.sql.parser.node.SelectStatementNode;
public class MultiSelectHandler implements ScrollableResultSetHandler {
private static final boolean LOAD_ALL_FIELDS = false;
private List definitions;
private Map cacheHandler = new HashMap();
private SQLSession session;
private String sql;
private String parsedSql;
private int numberOfColumnAlias;
private boolean allowDuplicateObjects;
private SQLCache transactionCache;
public MultiSelectHandler(SQLSession session, String sql, List definitions, int numberOfColumnAlias, boolean allowDuplicateObjects)
throws SQLQueryAnalyzerException {
this.definitions = definitions;
this.session = session;
this.sql = sql;
this.numberOfColumnAlias = numberOfColumnAlias;
this.parsedSql = parseSqlForResultClass();
this.allowDuplicateObjects = allowDuplicateObjects;
this.transactionCache = new WeakReferenceSQLCache();
}
@Override
public Object handle(ResultSet resultSet) throws Exception {
List result = new ArrayList();
EntityHandler.validateDuplicateColumns(resultSet, null);
if (resultSet.next()) {
try {
/*
* Faz o loop para processar os registros do ResultSet
*/
do {
result.add(readCurrentRow(resultSet));
} while (resultSet.next());
} catch (SQLException ex) {
throw new MultiSelectHandlerException("Erro processando MultiSelectHandler." + ex.getMessage());
}
}
return result;
}
@Override
public Object[] readCurrentRow(ResultSet resultSet) throws Exception {
List record = new ArrayList();
/*
* Primeira etapa para montagem dos objetos
*/
for (ResultClassDefinition rcd : definitions) {
if (session.getEntityCacheManager().isEntity(rcd.getResultClass())) {
/*
* Obtém a análise do sql para a classe de resultado
*/
SQLQueryAnalyzerResult analyzerResult = getAnalyzerResult(rcd);
/*
* Obtém o Handler para a criação do objeto
*/
EntityHandler entityHandler = getEntityHandler(rcd, analyzerResult, transactionCache);
/*
* Se a classe passada for uma entidade abstrata localiza no entityCache a classe correspondente ao
* discriminator colum
*/
EntityCache entityCache = entityHandler.getEntityCacheByResultSetRow(rcd.getResultClass(), resultSet);
/*
* Processa a linha do resultSet montando o objeto da classe de resultado
*/
List resultHandler = new ArrayList();
if (entityCache != null) {
entityHandler.handleRow(resultSet, resultHandler, entityCache, LOAD_ALL_FIELDS);
}
if (resultHandler.size() > 0)
record.add(resultHandler.get(0));
else
record.add(null);
} else {
Object value = null;
if (rcd.getSimpleColumn().getColumnIndex() > 0) {
value = resultSet.getObject(rcd.getSimpleColumn().getColumnIndex());
} else {
value = resultSet.getObject(getColumnIndex(rcd.getSimpleColumn().getColumnName()));
}
record.add(ObjectUtils.convert(value, rcd.getResultClass()));
}
}
/*
* Segunda etapa para finzalizar montagem dos objetos carregando as coleções e relacionamentos
*/
int index = 0;
for (ResultClassDefinition rcd : definitions) {
if (session.getEntityCacheManager().isEntity(rcd.getResultClass())) {
/*
* Obtém a análise do sql para a classe de resultado
*/
SQLQueryAnalyzerResult analyzerResult = getAnalyzerResult(rcd);
/*
* Obtém o Handler para a criação do objeto
*/
EntityHandler entityHandler = getEntityHandler(rcd, analyzerResult, transactionCache);
/*
* Se a classe passada for uma entidade abstrata localiza no entityCache a classe correspondente ao
* discriminator colum
*/
EntityCache entityCache = entityHandler.getEntityCacheByResultSetRow(rcd.getResultClass(), resultSet);
Object targetObject = record.get(index);
if (targetObject != null) {
entityHandler.loadCollectionsRelationShipAndLob(targetObject, entityCache, resultSet);
}
}
index++;
}
return record.toArray();
}
protected SQLQueryAnalyzerResult getAnalyzerResult(ResultClassDefinition rcd, String parsedSql, String originalSql) throws SQLQueryAnalyzerException {
SQLQueryAnalyzerResult analyzerResult = (SQLQueryAnalyzerResult) PersistenceMetadataCache.getInstance(session.getEntityCacheManager())
.get(rcd.getResultClass().getName() + ":" + originalSql);
if (analyzerResult == null) {
analyzerResult = new SQLQueryAnalyzer(session.getEntityCacheManager(), session.getDialect(), SQLQueryAnalyzer.IGNORE_NOT_USED_ALIAS_TABLE)
.analyze(parsedSql, rcd.getResultClass());
PersistenceMetadataCache.getInstance(session.getEntityCacheManager()).put(rcd.getResultClass().getName() + ":" + originalSql, analyzerResult);
}
return analyzerResult;
}
protected SQLQueryAnalyzerResult getAnalyzerResult(ResultClassDefinition rcd) throws SQLQueryAnalyzerException {
SQLQueryAnalyzerResult analyzerResult = (SQLQueryAnalyzerResult) PersistenceMetadataCache.getInstance(session.getEntityCacheManager()).get(rcd.getResultClass().getName() + ":" + sql);
if (analyzerResult == null) {
throw new MultiSelectHandlerException("Não foi possível encontrar a análise do SQL para a classe de resultado " + rcd.getResultClass().getName());
}
return analyzerResult;
}
private EntityHandler getEntityHandler(ResultClassDefinition rcd, SQLQueryAnalyzerResult analyzerResult, SQLCache transactionCache) throws Exception {
EntityHandler result = cacheHandler.get(rcd);
if (result == null) {
result = session.createNewEntityHandler(rcd.getResultClass(), analyzerResult.getExpressionsFieldMapper(), analyzerResult.getColumnAliases(),
transactionCache, allowDuplicateObjects, null, 0, 0, false, LockOptions.NONE, null);
cacheHandler.put(rcd, result);
}
return result;
}
protected String parseSqlForResultClass() throws SQLQueryAnalyzerException {
String parsedSql = sql;
for (ResultClassDefinition rcd : definitions) {
if (session.getEntityCacheManager().isEntity(rcd.getResultClass())) {
SQLQueryAnalyzerResult analyzerResult = getAnalyzerResult(rcd, parsedSql, sql);
parsedSql = analyzerResult.getParsedSql();
}
}
return parsedSql;
}
public String getParsedSql() {
return parsedSql;
}
protected int getColumnIndex(String columnName) {
SqlParser parser = new SqlParser(parsedSql, new SqlFormatRule());
INode node = new RootNode();
parser.parse(node);
SelectNode selectNode = (SelectNode) ParserUtil.findFirstChild(getFirstSelectStatement(node), "SelectNode");
int i = 1;
/*
* Localiza pelo alias da coluna caso o usuário tenha informado. O alias definido pelo usuário não será alterado
* durante a análise do sql.
*/
for (INode nd : selectNode.getChildren()) {
if (nd instanceof ColumnNode) {
ColumnNode columnNode = (ColumnNode) nd;
if (columnNode.hasAlias()) {
if (columnNode.getAliasName().equalsIgnoreCase(columnName)) {
return i;
}
}
i++;
} else if (nd instanceof FunctionNode) {
FunctionNode columnNode = (FunctionNode) nd;
if (columnNode.hasAlias()) {
if (columnNode.getAliasName().equalsIgnoreCase(columnName)) {
return i;
}
}
i++;
}
}
/*
* Caso não encontre pelo alias da coluna procura pelo nome da coluna.
*/
i = 1;
for (INode nd : selectNode.getChildren()) {
if (nd instanceof ColumnNode) {
ColumnNode columnNode = (ColumnNode) nd;
if (columnNode.getColumnName().equalsIgnoreCase(columnName)) {
return i;
}
i++;
} else if (nd instanceof FunctionNode) {
i++;
}
}
return -1;
}
/**
* Retorna o primeiro nó do tipo SelectStatement da árvore do SQL
*
* @param node
* Árvore do SQL
* @return Nó que representa o SelectStatement
*/
private SelectStatementNode getFirstSelectStatement(INode node) {
return (SelectStatementNode) ParserUtil.findFirstChild(node, "SelectStatementNode");
}
}