1

次のドメイン モデルがあるとします。

class Book {
  String title
  Set authors

  static hasMany = {authors: Author}
}

class Author {
  String name
}

タイトル Book に対するクエリを指定して Author のコレクションを取得する HQL クエリ:

Author.executeQuery("select distinct author from Book as book join book.authors as author where book.name like ?", ["%groovy%"])

しかし、私は DetachedCriteria または同様のものを使用して同じ結果を得ることができます (しかし、それは可能ですか?)、 Author から Book への関係を追加しません (そうでなければ、かなり明白です)

ありがとう

4

2 に答える 2

1

残念ながら、私の知る限り、これはこのクエリでは不可能です。ただし、次の醜いクエリでは可能です。


select author from Author author
where author.id in (select author2.id from Book book
                    join book.authors as author2 
                    where book.name like :bookName)

このような単純で動的に構成されていないクエリの場合、HQL クエリを使用します。本当に Criteria を使用する必要がある場合、これは対応するコードです。


Criteria c = session.createCriteria(Author.class, "author");
DetachedCriteria dc = DetachedCriteria.forClass(Book.class, "book");
dc.createAlias("book.authors", "author2");
dc.add(Restrictions.like("book.name", bookName));
dc.setProjection(Projections.property("author.id"));
c.add(Subqueries.propertyIn("author.id", dc);
List<Author> authors = (List<Author>) c.list();

于 2012-01-20T14:28:53.960 に答える
1

これは、基準または分離基準を使用していくつかの方法で実行できますが、Grails 2.2.2 の時点で分離基準にはない createAlias コマンドを実装しているため、通常の GORM 基準を使用すると少し簡単になります。

切り離された基準でエイリアスを作成する

ここに両方の​​方法があります:

package bookauthor

import grails.gorm.DetachedCriteria
import grails.orm.HibernateCriteriaBuilder


class MyController {

def index() {
  HibernateCriteriaBuilder ac2 = Author.createCriteria()
  HibernateCriteriaBuilder criteria2 = Author.createCriteria()

  HibernateCriteriaBuilder criteria = Book.createCriteria()

  def bookResults = criteria {
    projections {
      property 'aut.id'
    }
    createAlias('authors',  'aut')
    like('title', '%Groovy%')

  }

  def dc = new DetachedCriteria(Book).build {
    authors {}
    like('title', '%Groovy%')
  }

  def myList = dc.list().collect { it.authors.collect { author -> author.id} }.flatten()

  def resultsDetached = criteria2 {
    'in'('id', myList )
  }

  def results = ac2 {
    'in'('id', bookResults )
  }
log.info("RESULTS: " + results)
log.info("Detached RESULTS: " + resultsDetached)
}  

}

ログに次のように表示されます。

bookauthor.MyController  - RESULTS: [bookauthor.Author : 1, bookauthor.Author : 3]
bookauthor.MyController  - Detached RESULTS: [bookauthor.Author : 1, bookauthor.Author : 3]
于 2013-06-24T21:29:00.247 に答える