Search code examples
hibernategrailscriteria

Grails CriteriaBuilder add Restrictions


I want to create my criteria object and add some restrictions dependent on some other properties.

I tried something like that ...

    long from, to;
    use(TimeCategory) {
        from = (1.month.ago).getTime() / 1000L
        to = (new Date()).getTime() / 1000L
    }

    def crit = Map.createCriteria()       

    // set date range
    crit.between("appear", from, to)

    // if testParam1 is present
    if (params.testParam1 && !(params.testParam1.equals("all") || params.testParam1.isEmpty())) {
        crit.eq("test1", testParam1)
    }

    // if testParam2 is present
    if (params.testParam2 && !(params.testParam2.equals("all") || params.testParam2.isEmpty())) {
        crit.eq("test2", testParam2)
    }

But every Time I get an java.lang.IllegalArgumentException

This Exception is comming from the HibernateCriteriaBuilder class where the validateSimpleExpression test fails

/**
 * Creates a "between" Criterion based on the property name and specified lo and hi values
 * @param propertyName The property name
 * @param lo The low value
 * @param hi The high value
 * @return A Criterion instance
 */
public Object between(String propertyName, Object lo, Object hi) {
    if(!validateSimpleExpression()) {
        throwRuntimeException( new IllegalArgumentException("Call to [between] with propertyName ["+propertyName+"]  not allowed here."));
    }
    propertyName = calculatePropertyName(propertyName);
    return addToCriteria(Restrictions.between(propertyName, lo, hi));
}


private boolean validateSimpleExpression() {
    if(this.criteria == null) {
        return false;
    }
    return true;
}

Any Idea how to dynamically add some Restrictions ?


Solution

  • Thank you both for your suggestions. It lead me to the right direction. Here's my final approach

    long from, to;
    use(TimeCategory) {
        from = (1.month.ago).getTime() / 1000L
        to = (new Date()).getTime() / 1000L
    }
    
    def records = Map.withCriteria {       
    
        // set date range
        between("appear", from, to)
    
        // if testParam1 is present
        if (params.testParam1 && !(params.testParam1.equals("all") || params.testParam1.isEmpty())) {
            eq("test1", testParam1)
        }
    
        // if testParam2 is present
        if (params.testParam2 && !(params.testParam2.equals("all") || params.testParam2.isEmpty())) {
            eq("test2", testParam2)
        }
    
    }