龙哥网

龙哥网

Spring Data JPA实现查询结果返回map或自定义的实体类_java
2022-03-01

目录
  • Spring Data JPA查询结果返回map或自定义的实体类
    • 1.工具类
    • 2.具体应用
  • spingboot:jpa:Spring data jpa 返回map 结果集

    Spring Data JPA查询结果返回map或自定义的实体类

    在JPA中我们可以使用entityManager.createNativeQuery()来执行原生的SQL语句,并且JPA的底层实现都是支持返回Map对象的。

    例如:

    • EclipseLink 的
     query.setHint(QueryHints.RESULT_TYPE, ResultType.Map);
    • Hibernate 的
     query.unwrap(SQLQuery.class).setResultTransformer(Transformers.ALIAS_TO_ENTITY_MAP);
    • OpenJPA 的
     QueryImpl impl = q.unwrap(QueryImpl.class); impl.setResultClass(Map.class);

    本文中使用的是Spring Data JPA(Spring Data JPA 可以理解为 JPA 规范的再次封装抽象,底层还是使用了 Hibernate 的 JPA 技术实现),遂用 Hibernate 的query.unwrap(SQLQuery.class).setResultTransformer(Transformers.ALIAS_TO_ENTITY_MAP)。

    1.工具类

    @Component
    public class EntityManagerUtil<T> {
       @PersistenceContext
       private EntityManager entityManager;
      
       //1.返回map
       public List<Map<String, Object>> getListMap(String sql){
          Query nativeQuery=entityManager.createNativeQuery(sql);
          nativeQuery.unwrap(SQLQuery.class).setResultTransformer(Transformers.ALIAS_TO_ENTITY_MAP);
          List resultList=nativeQuery.getResultList();
          return resultList;
       }
      
       //2.返回自定义实体类
       public List<T> nativeQueryResult(String sql, Class clazz) {
         sql = Normalizer.normalize(sql, Normalizer.Form.NFKC);
         sql = sql.replaceAll(".*([';]+|(--)+).*", "");
         Query query = entityManager.createNativeQuery(sql);
         List<T> queryList = query.unwrap(SQLQuery.class).setResultTransformer(Transformers.aliasToBean(clazz)).list();
         return queryList;
       }
    }

    2.具体应用

     //1.自动注入
     @Autowired
     private EntityManagerUtil entityManagerUtil;
         //1.返回map
         String sql="sql语句";
         List<Map> list=entityManagerUtil.getListMap(sql);
         //2.1 返回自定义实体类(方法一)
         List<实体类> list = entityManagerUtil.nativeQueryResult(sql, 实体类.class);
        //2.2  返回自定义实体类(方法二 hql)
    

    在hql中使用 select new 包名.类名(属性1,属性2……) from 实体类,同时在实体类中添加带参的构造方法,参数的个数和顺序与(属性1,属性2……) 保持一致,这样我们得到的list中存放的依然是实体类的对象,所查询到的属性得到了填充。

    spingboot:jpa:Spring data jpa 返回map 结果集

       @PersistenceContext
        private EntityManager em;
        /**
         * 通过时间范围查询职位统计结果
         * @param startMonth
         * @param endMonth
         * @return
         */
        @Override
        public String queryPositionByMonthOfYear(String startMonth, String endMonth) {
     
            int sumNewPosn =0;
            int sumCurrPosn =0;
            int dailyAverage =0;
            Map<String, Object> resultMap=null;
            JSONObject jo =null;
            JSONObject jod =null;
            String endMonthTmp=null;
            List<Map<String,Object>> lis = null;
            try {
                int tmp = Integer.valueOf(endMonth.split("-")[1])+1;
                endMonthTmp=Integer.valueOf(endMonth.split("-")[0])+"-"+tmp;
                String sql = "select left(statistic_time,7) time ,sum(new_position) newPosition ,sum(curr_position) nowRecruitposition  from t_cal_positions " +
                                "where statistic_time > '"+startMonth+"' and statistic_time <'"+endMonthTmp+"' group by left(statistic_time,7)";
                Query query = em.createNativeQuery(sql);
                query.unwrap(org.hibernate.SQLQuery.class)
                        .setResultTransformer(Transformers.ALIAS_TO_ENTITY_MAP);
                    List<Map<String, Object>> rows  = query.getResultList();
                    if(null!=rows &&  rows.size()>0){
                            resultMap  = new HashMap<String, Object>();
                            lis= new ArrayList<Map<String,Object>>();
                            for (Map<String, Object> map : rows) {
                                if(map.get("time").equals(endMonth)){
    //                              int daynum = DateUtil.getDayOfMonth(Integer.valueOf(endMonth.split("-")[0]),Integer.valueOf(endMonth.split("-")[1]));
                                    dailyAverage=Integer.valueOf(String.valueOf(map.get("nowRecruitposition")))/DateUtil.getDateOfMonth();
                                }
                                  lis.add(map);
                            }
                            jo = new JSONObject();
                            jod = new JSONObject();
                            jod.put("dailyAverage",dailyAverage);
                            jod.put("list",lis);
                            jo.put("code", EnumHttpStatusType.success.getCode());
                            jo.put("msg",EnumHttpStatusType.success.getStatus());
                            jo.put("data",jod);
                            return jo.toString();
                        }
            } catch (Exception e) {
                e.printStackTrace();
            }
            return jo.toString();
        }
     
    免责声明
    本站部分资源来源于互联网 如有侵权 请联系站长删除
    龙哥网是优质的互联网科技创业资源_行业项目分享_网络知识引流变现方法的平台为广大网友提供学习互联网相关知识_内容变现的方法。