// Compile takes an expression and compiles it to a where clause for use with gorm.DB.Where()
// Returns the number of expected parameters for the query and a slice of errors if something goes wrong
func Compile(where criteria.Expression) (whereClause string, parameters []interface{}, err []error) {
	criteria.IteratePostOrder(where, bubbleUpJSONContext)

	compiler := newExpressionCompiler()
	compiled := where.Accept(&compiler)

	return compiled.(string), compiler.parameters, compiler.err
}
// iterate the parent chain to see if this expression references json fields
func isInJSONContext(exp criteria.Expression) bool {
	result := false
	criteria.IterateParents(exp, func(exp criteria.Expression) bool {
		if exp.Annotation(jsonAnnotation) == true {
			result = true
			return false
		}
		return true
	})
	return result
}