>
도메인 클래스 A에 클래스 B 개체가 많이 있다고 가정 해 봅시다. 다음을 반환하는 기준 쿼리를 수행해야합니다.

<올>
  • A.id
  • A. 이름
  • B.count (A와 연결된 B 요소 없음)
  • B.last Updated (모든 B 요소에 대해 last_updated 날짜를 고려한 A와 관련된 B 요소의 최신 업데이트 날짜)
  • 또한 쿼리는 A 및 B 도메인 개체 모두에 조건/제한을 추가 할 수있을 정도로 유연해야합니다. 현재 나는 이것 에까지 도달했다 :

    A.createCriteria().list {
        createAlias('b','b')
        projections{
            property('id')
            property('gender')
            property('dateOfBirth')
            count('b.id')
            property('publicId')
        }
    }
    
    

    그러나 문제는 하나의 객체 만 반환하고 자식 객체의 수는 A와 관련된 요소 대신 B의 모든 요소에 대한 것입니다.

    • 답변 # 1

      최근에 비슷한 시나리오에 있었기 때문에 행 중 하나가 일대 다 관계로 많은 수를 저장할 쿼리가 필요했습니다

      그러나 귀하의 시나리오와 달리 네이티브 SQL 쿼리를 사용하여 쿼리를 해결했습니다.

      이 솔루션은 파생 테이블을 사용하는 것이 었습니다 (기준 쿼리를 사용하여 테이블을 구현하는 방법을 모르겠습니다).

      유용한 경우 grails 서비스에서 가져온 구현과 코드를 공유합니다.

      List<Map> resumeInMonth(final String monthName) {
              final session = sessionFactory.currentSession
              final String query = """
                  SELECT
                      t.id AS id,
                      e.full_name AS fullName,
                      t.subject AS issue,
                      CASE t.status
                          WHEN 'open' THEN 'open'
                          WHEN 'pending' THEN 'In progress'
                          WHEN 'closed' THEN 'closed'
                      END AS status,
                      CASE t.scheduled
                          WHEN TRUE THEN 'scheduled'
                          WHEN FALSE THEN 'non-scheduled'
                      END AS scheduled,
                      ifnull(d.name, '') AS device,
                      DATE(t.date_created) AS dateCreated,
                      DATE(t.last_updated) AS lastUpdated,
                      IFNULL(total_tasks, 0) AS tasks
                  FROM
                      tickets t
                          INNER JOIN
                      employees e ON t.employee_id = e.id
                          LEFT JOIN
                      devices d ON d.id = t.device_id
                          LEFT JOIN
                      (SELECT
                          ticket_id, COUNT(1) AS total_tasks
                      FROM
                          tasks
                      GROUP BY ticket_id) ta ON t.id = ta.ticket_id
                  WHERE
                      MONTHNAME(t.date_created) = :monthName
                  ORDER BY dateCreated DESC"""
              final sqlQuery = session.createSQLQuery(query)
              final results = sqlQuery.with {
                  resultTransformer = AliasToEntityMapResultTransformer.INSTANCE
                  setString('monthName', monthName)
                  list()
              }
              results
          }
      
      

      관심있는 부분은 기본 선택 내에서 행을 선언 한 다음 결과를 기본 선택에서 선언 된 이름과 같은 행에 결과를 저장하는 파생 쿼리 선언 절에서

      SELECT ...
             total_tasks --Add the count column to your select
      FROM ticket t
      JOIN (SELECT ticked_id, COUNT(1) as total_tasks
            FROM tasks
            GROUP BY ticked_id) ta ON t.id = ta.ticked_id
      ...rest of query
      
      

      이 마지막 예는 사용자 Aaron Dietz의 답변에서 공식화 한 질문까지 공유합니다

      나는 그것이 당신에게 도움이되기를 바랍니다.

    • 답변 # 2

      솔루션에서별로 멀지 않았으며 아이의 외래 키 열인 올바른 속성을 기반으로 그룹화해야했습니다. 이 경우 ba 인 테이블은 다음과 같이 작동합니다.

      A.createCriteria().list {
        createAlias('b','b')
        projections{
          property('id')
          property('gender')
          property('dateOfBirth')
          count('b.id')
          groupProperty('b.a')
          property('publicId')
          }
      }
      
      

    • 답변 # 3

      기준에 따라 집계되지 않은 속성별로 그룹화해야합니다.
      다음을 시도하십시오.

      A.createCriteria().list {
          createAlias('b','b')
          projections{
              groupProperty('id','id')
              groupProperty('gender','gender')
              groupProperty('dateOfBirth','dateOfBirth')
              count('b.id','total')
              groupProperty('publicId','publicId')
          }
      }
      
      

      또는 맵 객체 목록을 반환하려면 resultTransformer (CriteriaSpecification.ALIAS_TO_ENTITY_MAP)를 추가하십시오.

      A.createCriteria().list {
          resultTransformer(CriteriaSpecification.ALIAS_TO_ENTITY_MAP)
          createAlias('b','b')
          projections{
              groupProperty('id','id')
              groupProperty('gender','gender')
              groupProperty('dateOfBirth','dateOfBirth')
              count('b.id','total')
              groupProperty('publicId','publicId')        
          }
      }
      
      

      도움이 될 수 있기를 바랍니다

    관련 자료

  • 이전 구글 맵 자바 스크립트에서 특정 영역의 스냅 샷 찍기
  • 다음 reactjs : TypeScript 및 React-Router 4, 5 또는 6을 사용하여 보호 /개인 경로를 다시 작성하는 방법은 무엇입니까?