INNER JOIN HQL-запрос от Grails - PullRequest
       31

INNER JOIN HQL-запрос от Grails

1 голос
/ 25 октября 2011

Я пытаюсь выяснить, как заставить этот фрагмент кода работать:

def searchString = unchecked.join(",");
        searchString = searchString.replace("\"", "'")
        println("searchString: " + searchString);

        def matches=Employee.executeQuery("select e.id from Employee as e INNER JOIN Education as ed ON e.id = ed.employee_id INNER JOIN education_type AS et ON et.id = ed.type_id WHERE et.name  in (" +searchString + ")");

Это строка запроса, переданная executeQuery

select e.id from Employee as e INNER JOIN Education as ed ON e.id = ed.employee_id INNER JOIN education_type AS et ON et.id = ed.type_id WHERE et.name  in ('AA','BS')

, который я могу запустить в SQL Server, и он возвращает правильные результаты, однако мой код grails жалуется:

Stacktrace follows:
org.hibernate.hql.ast.QuerySyntaxException: unexpected token: ON near line 1, column 59 [select e.id from Employee as e INNER JOIN Education as ed ON e.id = ed.employee_id INNER JOIN education_type AS et ON et.id = ed.type_id WHERE et.name  in ('AA','BS')]

Так что я делаю не так? Это неправильный объект домена, выполняющий запрос?

Ответы [ 2 ]

2 голосов
/ 26 октября 2011

Подумайте о том, чтобы сделать это так:

def employee = Employee.withCriteria {
    education {
        educationType {
            in("name", ["AA", "BS"])
        }
    }
}
0 голосов
/ 25 октября 2011

HQL немного / достаточно отличается от стандартного SQL.Предполагая, что Hibernate знает о взаимосвязи между этими объектами, вы можете упростить ваш запрос до

List<String> typeNames = unchecked.collect { it.replace("\"", "") }
String query = """FROM Employee e
                  WHERE e.education.educationType.name IN (:typeNames)"""
List<Employee> = Employee.executeQuery(query, [typeNames: typeNames])

. Для предотвращения внедрения sql очень важно использовать в запросе как именованные, так и позиционные параметры.Также, если вы действительно хотите получить список идентификаторов сотрудников, а не экземпляров, вы можете поместить туда SELECT e.id.Также нет смысла включать кавычки, поскольку, когда параметры связаны, они будут использовать правильные кавычки для базы данных, с которой вы работаете, учитывая, что приведенный выше фрагмент кода также удаляет кавычки, но вы могли бы переосмыслить, даже если разрешить их включение впервое место.

...