Hibernate / JPA генерирует запрос без псевдонима для подзапроса - PullRequest
0 голосов
/ 02 ноября 2018

У меня есть следующий класс, который генерирует динамический Hibernate / JPA-запрос (из-за динамической природы параметров):

      import java.util.ArrayList;
      import java.util.List;
     import java.util.Map;

   import javax.persistence.EntityManager;
   import javax.persistence.PersistenceContext;
   import javax.persistence.Query;

    import org.apache.commons.lang3.StringUtils;
    import org.springframework.beans.factory.annotation.Value;
    import org.springframework.stereotype.Repository;

        import com.charter.egateway.datalayer.model.AccountDatabase;

        @Repository
        public class AccountRepositoryCustomImpl implements AccountRepositoryCustom 
       {

        @PersistenceContext
        private EntityManager em;

        @Value("${recordLimit}")
        private String recordLimit;

        @Override
        public List<AccountDatabase> searchForAccounts(Map<String, Object> map) {

            boolean hasPassedParameters = false;
            List<String> whereClause = new ArrayList<>();

            StringBuilder queryBuilder = new StringBuilder();
            queryBuilder.append("select ad from AccountDatabase ad ");

            for (String key : map.keySet()) {
                if (!key.equals("city") && !key.equalsIgnoreCase("address")
                        && !key.equalsIgnoreCase("billingAccountNumber")) {

                    if (key.equals("accountType")) {
                        whereClause.add(" ad." + key + " = :" + key);
                    } else {
                        whereClause.add(" UPPER(ad." + key + ") LIKE :" + key);

                    }
                    hasPassedParameters = true;
                }
            }

            queryBuilder.append(" where " + StringUtils.join(whereClause, " and "));

            if (map.containsKey("city")) {
                if (hasPassedParameters) {
                    queryBuilder.append(" AND ");
                }
                queryBuilder.append(" (( ad.accountType LIKE :accountType AND UPPER(ad.billingCity) LIKE :billingCity ) OR "
                        + "( ad.accountType LIKE :accountType2 AND UPPER(ad.shippingCity) LIKE :shippingCity )) ");

                hasPassedParameters = true;

            }

            if (map.containsKey("address")) {
                if (hasPassedParameters) {
                    queryBuilder.append(" AND ");
                }
                queryBuilder
                        .append(" (( ad.accountType LIKE :accountType AND UPPER(ad.billingStreet) LIKE :billingStreet ) OR "
                                + "( ad.accountType LIKE :accountType2 AND UPPER(ad.shippingStreet) LIKE :shippingStreet )) ");

                hasPassedParameters = true;

            }

            if (map.containsKey("billingAccountNumber")) {
                if (hasPassedParameters) {
                    queryBuilder.append(" AND ");
                }
                queryBuilder
                        .append(" (( ad.accountType LIKE :accountType AND ad.billingAccountNumber LIKE :billingAccountNumber ) OR "
                                + "( ad.accountType LIKE :accountType2 AND ad.billingAccountNumberForServiceLocation LIKE :billingAccountNumberForServiceLocation )) ");

            }



            Query jpaQuery = em.createQuery(queryBuilder.toString(), AccountDatabase.class);    

            //Query jpaQuery = em.createQuery(queryBuilder.toString(), AccountDatabase.class);

            for (String key : map.keySet()) {
                if (!key.equals("city") && !key.equalsIgnoreCase("address")
                        && !key.equalsIgnoreCase("billingAccountNumber")) {

                    if (key.equals("accountType")) {
                        jpaQuery.setParameter(key, map.get(key));
                    } else {
                        jpaQuery.setParameter(key, "%" + String.valueOf(map.get(key)).toUpperCase() + "%");
                    }
                }
            }

            if (map.containsKey("address")) {
                if (map.containsKey("accountType")) {

                    jpaQuery.setParameter("accountType", map.get("accountType"));
                    jpaQuery.setParameter("accountType2", map.get("accountType"));
                } else {
                    jpaQuery.setParameter("accountType", "Billing Account");
                    jpaQuery.setParameter("accountType2", "Service Location");

                }
                jpaQuery.setParameter("billingStreet", "%" + String.valueOf(map.get("address")).toUpperCase() + "%");
                jpaQuery.setParameter("shippingStreet", "%" + String.valueOf(map.get("address")).toUpperCase() + "%");
            }

            if (map.containsKey("city")) {
                if (map.containsKey("accountType")) {
                    jpaQuery.setParameter("accountType", map.get("accountType"));
                    jpaQuery.setParameter("accountType2", map.get("accountType"));
                } else {
                    jpaQuery.setParameter("accountType", "Billing Account");
                    jpaQuery.setParameter("accountType2", "Service Location");

                }
                jpaQuery.setParameter("billingCity", "%" + String.valueOf(map.get("city")).toUpperCase() + "%");
                jpaQuery.setParameter("shippingCity", "%" + String.valueOf(map.get("city")).toUpperCase() + "%");
            }

            if (map.containsKey("billingAccountNumber")) {
                if (map.containsKey("accountType")) {
                    jpaQuery.setParameter("accountType", map.get("accountType"));
                    jpaQuery.setParameter("accountType2", map.get("accountType"));
                } else {
                    jpaQuery.setParameter("accountType", "Billing Account");
                    jpaQuery.setParameter("accountType2", "Service Location");

                }

                jpaQuery.setParameter("billingAccountNumber", "%" + map.get("billingAccountNumber") + "%");
                jpaQuery.setParameter("billingAccountNumberForServiceLocation",
                        "%" + map.get("billingAccountNumber") + "%");
            }

            int limit = Integer.valueOf(recordLimit);



            //TypedQuery<AccountDatabase> query = em.createQuery(queryBuilder.toString(), AccountDatabase.class);    

            //List<AccountDatabase> list = jpaQuery.getResultList();

            jpaQuery.setMaxResults(limit);
            List<AccountDatabase> list = jpaQuery.getResultList();
            if (list.size() > limit) {
                list = list.subList(0, limit);
            }

            em.close();
            return list;

        }

    }

Что я могу сделать, не используя собственный запрос? как заставить это работать?

Table subquery missing an alias.  On line 1, column 734.  [parser-2909810]

BlablablaBlablablaBlablablaBlablablaBlablablaBlablablaBlablablaBlablablaBlablablaBlablablaBlablablaBlablablaBlablablaBlablablaBlablablaBlablablaBlablablaBlablablaBlablablaBlablablaBlablablaBlablablaBlablablaBlablablaBlablablaBlablablaBlablablaBlablablaBlablablaBlablablaBlablablaBlablablaBlablablaBlablablaBlablablaBlablablaBlablablaBlablablaBlablablaBlablablaBlablablaBlablablaBlablablaBlablablaBlablablaBlablablaBlablablaBlablablaBlablablaBlablablaBlablablaBlablablaBlablablaBlablablaBlablablaBlablablaBlablablaBlablablaBlablablaBlablablaBlablablaBlablablaBlablablaBlablablaBlablablaBlablablaBlablablaBlablablaBlablablaBlablablaBlablablaBlablablaBlablablaBlablablaBlablablaBlablablaBlablablaBlablablaBlablablaBlablablaBlablablaBlablablaBlablablaBlablablaBlablablaBlablablaBlablablaBlablablaBlablablaBlablablaBlablablaBlablabla

1 Ответ

0 голосов
/ 02 февраля 2019

Недавно я столкнулся с этой проблемой и проследил ее до этого изменения в спящем режиме.

Чтобы решить эту проблему, я написал следующий пользовательский диалект, который по существу отменяет это изменение:

import org.hibernate.dialect.Oracle12cDialect;
import org.hibernate.dialect.pagination.LimitHandler;
import org.hibernate.dialect.pagination.SQL2008StandardLimitHandler;

public class CustomDialect extends Oracle12cDialect {

    @Override
    public LimitHandler getLimitHandler() {
        return SQL2008StandardLimitHandler.INSTANCE;
    }

}

Кроме того, использование версии 5.3.3.Final также должно решить вашу проблему, так как это последний выпуск перед этим изменением. Если использовать Maven, это будет выглядеть так:

<dependency>
    <groupId>org.hibernate</groupId>
    <artifactId>hibernate-core</artifactId>
    <version>5.3.3.Final</version>
</dependency>

Мне любопытно, подключаетесь ли вы к платформе виртуализации данных Tibco / (была Cisco).

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...