Search in sources :

Example 21 with SqlStatement

use of org.jumpmind.pos.persist.SqlStatement in project openpos-framework by JumpMind.

the class QueryTemplate method generateSQL.

public SqlStatement generateSQL(Query<?> query, Map<String, Object> params) {
    String select = this.getSelect();
    List<String> keys = new ArrayList<>();
    StringSubstitutor literalSubstitution = new StringSubstitutor(new StringLookup() {

        @Override
        public String lookup(String key) {
            Object paramValue = params.get(key);
            return paramValue != null ? paramValue.toString() : "null";
        }
    }, "$${", "}", '\\');
    StringSubstitutor sub = new StringSubstitutor(new StringLookup() {

        @Override
        public String lookup(String key) {
            keys.add(key);
            return ":" + key;
        }
    });
    String preppedSelectClause = literalSubstitution.replace(select);
    preppedSelectClause = sub.replace(preppedSelectClause);
    String preppedWhereClause = literalSubstitution.replace(this.getWhere());
    preppedWhereClause = sub.replace(preppedWhereClause);
    StringBuilder buff = new StringBuilder();
    preppedSelectClause = stripWhere(preppedSelectClause);
    boolean hasWhereKeyword = false;
    buff.append(preppedSelectClause);
    if (!StringUtils.isEmpty(preppedWhereClause)) {
        hasWhereKeyword = true;
        buff.append(" WHERE ");
        buff.append(preppedWhereClause);
    }
    boolean firstIncluded = true;
    for (String optionalWhereClause : this.getOptionalWhereClauses()) {
        Set<String> optionalWhereClauseKeys = new LinkedHashSet<>();
        String preppedOptionalWhereClause = literalSubstitution.replace(optionalWhereClause);
        StringSubstitutor optionalSubstitution = new StringSubstitutor(new StringLookup() {

            @Override
            public String lookup(String key) {
                optionalWhereClauseKeys.add(key);
                return ":" + key;
            }
        });
        preppedOptionalWhereClause = optionalSubstitution.replace(preppedOptionalWhereClause);
        boolean shouldInclude = true;
        for (String key : optionalWhereClauseKeys) {
            if (!params.containsKey(key)) {
                shouldInclude = false;
                break;
            }
        }
        if (shouldInclude) {
            if (!hasWhereKeyword) {
                buff.append(" WHERE 1=1 ");
                hasWhereKeyword = true;
            }
            if (query.isUseAnd() || firstIncluded) {
                buff.append(" AND (");
            } else {
                buff.append(" OR (");
            }
            buff.append(preppedOptionalWhereClause);
            buff.append(")");
            keys.addAll(optionalWhereClauseKeys);
        }
        if (shouldInclude) {
            firstIncluded = false;
        }
    }
    splitTooManyValuesInClause(query, params, buff);
    if (!StringUtils.isEmpty(this.getGroupBy())) {
        buff.append(" GROUP BY ");
        buff.append(this.getGroupBy());
    }
    if (!StringUtils.isEmpty(this.getOrderBy())) {
        buff.append(" ORDER BY ");
        buff.append(this.getOrderBy());
    }
    SqlStatement sqlStatement = new SqlStatement();
    sqlStatement.setSql(buff.toString());
    for (String key : keys) {
        Object value = params.get(key);
        if (value == null) {
            value = params.get("*");
            params.put(key, value);
        }
        if (value == null) {
            if (params.containsKey(key)) {
                throw new PersistException(String.format("Required query parameter '%s' was present but the value is null. A value must be provided. Cannot build query: %s", key, sqlStatement.getSql()));
            } else {
                throw new PersistException(String.format("Missing required query parameter '%s'. Cannot build query: %s", key, sqlStatement.getSql()));
            }
        } else if (value instanceof Boolean) {
            boolean bool = (Boolean) value;
            value = bool ? 1 : 0;
            params.put(key, value);
        } else if (value instanceof AbstractTypeCode) {
            value = ((AbstractTypeCode) value).value();
            params.put(key, value);
        }
    }
    if (params != null) {
        params.remove("*");
    }
    sqlStatement.setParameters(params);
    return sqlStatement;
}
Also used : StringLookup(org.apache.commons.text.lookup.StringLookup) SqlStatement(org.jumpmind.pos.persist.SqlStatement) PersistException(org.jumpmind.pos.persist.PersistException) StringSubstitutor(org.apache.commons.text.StringSubstitutor) AbstractTypeCode(org.jumpmind.pos.util.model.AbstractTypeCode)

Aggregations

SqlStatement (org.jumpmind.pos.persist.SqlStatement)21 Test (org.junit.Test)19 HashMap (java.util.HashMap)2 StringSubstitutor (org.apache.commons.text.StringSubstitutor)2 StringLookup (org.apache.commons.text.lookup.StringLookup)2 PersistException (org.jumpmind.pos.persist.PersistException)2 Query (org.jumpmind.pos.persist.Query)2 CarModel (org.jumpmind.pos.persist.cars.CarModel)2 AbstractTypeCode (org.jumpmind.pos.util.model.AbstractTypeCode)2