Skip to content

Commit

Permalink
refactor
Browse files Browse the repository at this point in the history
  • Loading branch information
teosarca committed May 2, 2017
1 parent c560fa6 commit 9326a67
Show file tree
Hide file tree
Showing 4 changed files with 240 additions and 71 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -40,7 +40,7 @@
* @author metas-dev <dev@metasfresh.com>
*
*/
interface IViewDataRepository
public interface IViewDataRepository
{
String getTableName();

Expand Down
121 changes: 51 additions & 70 deletions src/main/java/de/metas/ui/web/view/SqlViewDataRepository.java
Original file line number Diff line number Diff line change
Expand Up @@ -3,17 +3,15 @@
import java.sql.PreparedStatement;
import java.sql.ResultSet;
import java.sql.SQLException;
import java.util.ArrayList;
import java.util.Collection;
import java.util.List;
import java.util.Map;
import java.util.Objects;

import org.adempiere.ad.dao.IQueryBL;
import org.adempiere.ad.dao.impl.TypedSqlQueryFilter;
import org.adempiere.ad.expression.api.IExpressionEvaluator.OnVariableNotFound;
import org.adempiere.ad.security.IUserRolePermissions;
import org.adempiere.ad.security.IUserRolePermissionsDAO;
import org.adempiere.ad.security.UserRolePermissionsKey;
import org.adempiere.ad.security.permissions.WindowMaxQueryRecordsConstraint;
import org.adempiere.ad.expression.api.IStringExpression;
import org.adempiere.ad.trx.api.ITrx;
import org.adempiere.exceptions.DBException;
import org.adempiere.model.PlainContextAware;
Expand All @@ -23,8 +21,8 @@
import org.slf4j.Logger;

import com.google.common.base.MoreObjects;
import com.google.common.base.Stopwatch;
import com.google.common.collect.ImmutableList;
import com.google.common.collect.ImmutableMap;

import de.metas.logging.LogManager;
import de.metas.ui.web.exceptions.EntityNotFoundException;
Expand All @@ -36,7 +34,6 @@
import de.metas.ui.web.window.descriptor.filters.DocumentFilterDescriptorsProvider;
import de.metas.ui.web.window.model.DocumentQueryOrderBy;
import de.metas.ui.web.window.model.filters.DocumentFilter;
import de.metas.ui.web.window.model.sql.SqlDocumentOrderByBuilder;
import lombok.NonNull;

/*
Expand All @@ -49,12 +46,12 @@
* it under the terms of the GNU General Public License as
* published by the Free Software Foundation, either version 2 of the
* License, or (at your option) any later version.
*
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
*
* You should have received a copy of the GNU General Public
* License along with this program. If not, see
* <http://www.gnu.org/licenses/gpl-2.0.html>.
Expand All @@ -65,86 +62,71 @@ class SqlViewDataRepository implements IViewDataRepository
{
private static final Logger logger = LogManager.getLogger(SqlViewDataRepository.class);

private final SqlViewBinding sqlBindings;
private final String tableName;
private final IStringExpression sqlSelectById;
private final IStringExpression sqlSelectByPage;
private final ViewRowIdsOrderedSelectionFactory viewRowIdsOrderedSelectionFactory;
private final DocumentFilterDescriptorsProvider viewFilterDescriptors;

private final String keyFieldName;
private final ImmutableMap<String, SqlViewRowFieldLoader> rowFieldLoaders;

SqlViewDataRepository(@NonNull final SqlViewBinding sqlBindings)
{
this.sqlBindings = sqlBindings;
tableName = sqlBindings.getTableName();
sqlSelectById = sqlBindings.getSqlSelectById();
sqlSelectByPage = sqlBindings.getSqlSelectByPage();
viewFilterDescriptors = sqlBindings.getViewFilterDescriptors();
viewRowIdsOrderedSelectionFactory = new SqlViewRowIdsOrderedSelectionFactory(sqlBindings);

String keyFieldName = null;
final ImmutableMap.Builder<String, SqlViewRowFieldLoader> rowFieldLoaders = ImmutableMap.builder();
for (final SqlViewRowFieldBinding field : sqlBindings.getFields())
{
final String fieldName = field.getFieldName();
rowFieldLoaders.put(fieldName, field.getFieldLoader());

if (field.isKeyColumn())
{
keyFieldName = fieldName;
}
}

this.keyFieldName = keyFieldName;
this.rowFieldLoaders = rowFieldLoaders.build();

}

@Override
public String toString()
{
return MoreObjects.toStringHelper(this).addValue(sqlBindings).toString();
return MoreObjects.toStringHelper(this)
.add("tableName", tableName)
.toString();
}

@Override
public String getTableName()
{
return sqlBindings.getTableName();
return tableName;
}

@Override
public String getSqlWhereClause(final ViewId viewId, final Collection<DocumentId> rowIds)
{
return sqlBindings.getSqlWhereClause(viewId.getViewId(), rowIds);
return viewRowIdsOrderedSelectionFactory.getSqlWhereClause(viewId, rowIds);
}

@Override
public ViewRowIdsOrderedSelection createOrderedSelection(final ViewEvaluationCtx viewEvalCtx, final WindowId windowId, final List<DocumentFilter> filters)
{
final ViewId viewId = ViewId.random(windowId);

final UserRolePermissionsKey permissionsKey = viewEvalCtx.getPermissionsKey();
final IUserRolePermissions permissions = Services.get(IUserRolePermissionsDAO.class).retrieveUserRolePermissions(permissionsKey);
final int queryLimit = permissions.getConstraint(WindowMaxQueryRecordsConstraint.class)
.or(WindowMaxQueryRecordsConstraint.DEFAULT)
.getMaxQueryRecordsPerRole();

//
//
final List<Object> sqlParams = new ArrayList<>();
final String sql = sqlBindings.getSqlCreateSelectionFrom(sqlParams, viewEvalCtx, viewId, filters, queryLimit);

//
// Execute it, so we insert in our T_WEBUI_ViewSelection
final Stopwatch stopwatch = Stopwatch.createStarted();
final long rowsCount = DB.executeUpdateEx(sql, sqlParams.toArray(), ITrx.TRXNAME_ThreadInherited);
stopwatch.stop();
logger.trace("Created selection {}, rowsCount={}, duration={} \n SQL: {} -- {}", viewId, rowsCount, stopwatch, sql, sqlParams);

return ViewRowIdsOrderedSelection.builder()
.setViewId(viewId)
.setSize(rowsCount)
.setOrderBys(sqlBindings.getDefaultOrderBys())
.setQueryLimit(queryLimit)
.build();
return viewRowIdsOrderedSelectionFactory.createOrderedSelection(viewEvalCtx, windowId, filters);
}

@Override
public ViewRowIdsOrderedSelection createOrderedSelectionFromSelection(final ViewEvaluationCtx viewEvalCtx, final ViewRowIdsOrderedSelection fromSelection, final List<DocumentQueryOrderBy> orderBys)
{
final WindowId windowId = fromSelection.getWindowId();
final String fromSelectionId = fromSelection.getSelectionId();

final ViewId newViewId = ViewId.random(windowId);
final String newSelectionId = newViewId.getViewId();

final String sqlOrderBys = SqlDocumentOrderByBuilder.newInstance(fieldName -> sqlBindings.getFieldByFieldName(fieldName).getSqlOrderBy())
.buildSqlOrderBy(orderBys)
.evaluate(viewEvalCtx.toEvaluatee(), OnVariableNotFound.Fail);

final String sqlCreateFromViewId = sqlBindings.getSqlCreateSelectionFromSelection();
final String sqlFinal = sqlCreateFromViewId.replace(SqlViewBinding.PLACEHOLDER_OrderBy, sqlOrderBys);

final int rowsCount = DB.executeUpdateEx(sqlFinal, new Object[] { newSelectionId, fromSelectionId }, ITrx.TRXNAME_ThreadInherited);

return ViewRowIdsOrderedSelection.builder()
.setViewId(newViewId)
.setSize(rowsCount)
.setOrderBys(orderBys)
.setQueryLimit(fromSelection.getQueryLimit())
.build();
return viewRowIdsOrderedSelectionFactory.createOrderedSelectionFromSelection(viewEvalCtx, fromSelection, orderBys);
}

@Override
Expand All @@ -154,7 +136,7 @@ public IViewRow retrieveById(final ViewEvaluationCtx viewEvalCtx, final ViewId v
final String viewSelectionId = viewId.getViewId();
final String adLanguage = viewEvalCtx.getAD_Language();

final String sql = sqlBindings.getSqlSelectById().evaluate(viewEvalCtx.toEvaluatee(), OnVariableNotFound.Fail);
final String sql = sqlSelectById.evaluate(viewEvalCtx.toEvaluatee(), OnVariableNotFound.Fail);

final Object[] sqlParams = new Object[] { viewSelectionId, rowId.toInt() };
PreparedStatement pstmt = null;
Expand Down Expand Up @@ -208,15 +190,14 @@ public IViewRow retrieveById(final ViewEvaluationCtx viewEvalCtx, final ViewId v
private IViewRow loadViewRow(final ResultSet rs, final WindowId windowId, final String adLanguage) throws SQLException
{
final ViewRow.Builder viewRowBuilder = ViewRow.builder(windowId);

for (final SqlViewRowFieldBinding field : sqlBindings.getFields())
for (final Map.Entry<String, SqlViewRowFieldLoader> fieldNameAndLoader : rowFieldLoaders.entrySet())
{
final String fieldName = field.getFieldName();
final boolean keyColumn = field.isKeyColumn();
final SqlViewRowFieldLoader fieldLoader = field.getFieldLoader();
final String fieldName = fieldNameAndLoader.getKey();
final SqlViewRowFieldLoader fieldLoader = fieldNameAndLoader.getValue();
final Object value = fieldLoader.retrieveValueAsJson(rs, adLanguage);

if (keyColumn)
if(Objects.equals(fieldName, keyFieldName))
{
if (value == null)
{
Expand All @@ -236,7 +217,7 @@ private IViewRow loadViewRow(final ResultSet rs, final WindowId windowId, final
@Override
public DocumentFilterDescriptorsProvider getViewFilterDescriptors()
{
return sqlBindings.getViewFilterDescriptors();
return viewFilterDescriptors;
}

@Override
Expand All @@ -255,7 +236,7 @@ public List<IViewRow> retrievePage(final ViewEvaluationCtx viewEvalCtx, final Vi
final int firstSeqNo = firstRow + 1; // NOTE: firstRow is 0-based while SeqNo are 1-based
final int lastSeqNo = firstRow + pageLength;

final String sql = sqlBindings.getSqlSelectByPage().evaluate(viewEvalCtx.toEvaluatee(), OnVariableNotFound.Fail);
final String sql = sqlSelectByPage.evaluate(viewEvalCtx.toEvaluatee(), OnVariableNotFound.Fail);
final Object[] sqlParams = new Object[] { viewSelectionId, firstSeqNo, lastSeqNo };
PreparedStatement pstmt = null;
ResultSet rs = null;
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,146 @@
package de.metas.ui.web.view;

import java.util.ArrayList;
import java.util.Collection;
import java.util.List;

import org.adempiere.ad.expression.api.IExpressionEvaluator.OnVariableNotFound;
import org.adempiere.ad.expression.api.IStringExpression;
import org.adempiere.ad.security.IUserRolePermissions;
import org.adempiere.ad.security.IUserRolePermissionsDAO;
import org.adempiere.ad.security.UserRolePermissionsKey;
import org.adempiere.ad.security.permissions.WindowMaxQueryRecordsConstraint;
import org.adempiere.ad.trx.api.ITrx;
import org.adempiere.util.Services;
import org.compiere.util.DB;
import org.slf4j.Logger;

import com.google.common.base.Stopwatch;

import de.metas.logging.LogManager;
import de.metas.ui.web.view.descriptor.SqlViewBinding;
import de.metas.ui.web.window.datatypes.DocumentId;
import de.metas.ui.web.window.datatypes.WindowId;
import de.metas.ui.web.window.model.DocumentQueryOrderBy;
import de.metas.ui.web.window.model.filters.DocumentFilter;
import de.metas.ui.web.window.model.sql.SqlDocumentOrderByBuilder;
import lombok.NonNull;

/*
* #%L
* metasfresh-webui-api
* %%
* Copyright (C) 2017 metas GmbH
* %%
* This program is free software: you can redistribute it and/or modify
* it under the terms of the GNU General Public License as
* published by the Free Software Foundation, either version 2 of the
* License, or (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public
* License along with this program. If not, see
* <http://www.gnu.org/licenses/gpl-2.0.html>.
* #L%
*/

public class SqlViewRowIdsOrderedSelectionFactory implements ViewRowIdsOrderedSelectionFactory
{

private static final Logger logger = LogManager.getLogger(SqlViewRowIdsOrderedSelectionFactory.class);

private final String sqlCreateFromViewId;
private final List<DocumentQueryOrderBy> defaultOrderBys;
private final SqlViewBinding _sqlBindings;

SqlViewRowIdsOrderedSelectionFactory(@NonNull final SqlViewBinding sqlBindings)
{
this._sqlBindings = sqlBindings;
sqlCreateFromViewId = sqlBindings.getSqlCreateSelectionFromSelection();

defaultOrderBys = sqlBindings.getDefaultOrderBys();
}

private String getSqlCreateSelectionFrom( //
final List<Object> sqlParams //
, final ViewEvaluationCtx viewEvalCtx //
, final ViewId newViewId //
, final List<DocumentFilter> filters //
, final int queryLimit //
)
{
return _sqlBindings.getSqlCreateSelectionFrom(sqlParams, viewEvalCtx, newViewId, filters, queryLimit);
}

private final IStringExpression getFieldOrderBy(final String fieldName)
{
return _sqlBindings.getFieldOrderBy(fieldName);
}

@Override
public ViewRowIdsOrderedSelection createOrderedSelection(final ViewEvaluationCtx viewEvalCtx, final WindowId windowId, final List<DocumentFilter> filters)
{
final ViewId viewId = ViewId.random(windowId);

final UserRolePermissionsKey permissionsKey = viewEvalCtx.getPermissionsKey();
final IUserRolePermissions permissions = Services.get(IUserRolePermissionsDAO.class).retrieveUserRolePermissions(permissionsKey);
final int queryLimit = permissions.getConstraint(WindowMaxQueryRecordsConstraint.class)
.or(WindowMaxQueryRecordsConstraint.DEFAULT)
.getMaxQueryRecordsPerRole();

//
//
final List<Object> sqlParams = new ArrayList<>();
final String sql = getSqlCreateSelectionFrom(sqlParams, viewEvalCtx, viewId, filters, queryLimit);

//
// Execute it, so we insert in our T_WEBUI_ViewSelection
final Stopwatch stopwatch = Stopwatch.createStarted();
final long rowsCount = DB.executeUpdateEx(sql, sqlParams.toArray(), ITrx.TRXNAME_ThreadInherited);
stopwatch.stop();
logger.trace("Created selection {}, rowsCount={}, duration={} \n SQL: {} -- {}", viewId, rowsCount, stopwatch, sql, sqlParams);

return ViewRowIdsOrderedSelection.builder()
.setViewId(viewId)
.setSize(rowsCount)
.setOrderBys(defaultOrderBys)
.setQueryLimit(queryLimit)
.build();
}

@Override
public ViewRowIdsOrderedSelection createOrderedSelectionFromSelection(final ViewEvaluationCtx viewEvalCtx, final ViewRowIdsOrderedSelection fromSelection, final List<DocumentQueryOrderBy> orderBys)
{
final WindowId windowId = fromSelection.getWindowId();
final String fromSelectionId = fromSelection.getSelectionId();

final ViewId newViewId = ViewId.random(windowId);
final String newSelectionId = newViewId.getViewId();

final String sqlOrderBys = SqlDocumentOrderByBuilder.newInstance(this::getFieldOrderBy)
.buildSqlOrderBy(orderBys)
.evaluate(viewEvalCtx.toEvaluatee(), OnVariableNotFound.Fail);

final String sqlFinal = sqlCreateFromViewId.replace(SqlViewBinding.PLACEHOLDER_OrderBy, sqlOrderBys);

final int rowsCount = DB.executeUpdateEx(sqlFinal, new Object[] { newSelectionId, fromSelectionId }, ITrx.TRXNAME_ThreadInherited);

return ViewRowIdsOrderedSelection.builder()
.setViewId(newViewId)
.setSize(rowsCount)
.setOrderBys(orderBys)
.setQueryLimit(fromSelection.getQueryLimit())
.build();
}

@Override
public String getSqlWhereClause(final ViewId viewId, final Collection<DocumentId> rowIds)
{
return _sqlBindings.getSqlWhereClause(viewId.getViewId(), rowIds);
}

}
Loading

0 comments on commit 9326a67

Please sign in to comment.