二、通用Dao层之BaseQueryDao接口与BaseQueryDaoImpl类

一、BaseQueryDao接口

二、通用Dao层之BaseQueryDao接口与BaseQueryDaoImpl类

/**
 * 
 * 通用的查询接口
 *
 * @param <T> 后台实体
 * @param <F> 前台Form(包含分页信息)
 * @author chendejiang
 */
public interface BaseQueryDao<T,F extends PageForm> {
    
    /**
     * 根据JPQL语句查询
     * @param jpql JPQL语句
     * @param params 零个或多个参数
     * @return 返回List<T>对象 
     */
    public List<T> findByJPQL(String jpql,Object... params);

    /**
     * 根据JPQL语句查询
     * @param entityClass 实体Bean的类型。如User.class
     * @param jpql JPQL语句
     * @param params 零个或多个参数
     * @return 返回List<E>对象 
     */
    public <E> List<E> findByJPQL(Class<E> entityClass,String jpql,Object... params);
    
    /**
     * 根据JPQL语句查询
     * @param hints jpa提供商参数(常用于设置二级缓存等参数)
     * @param entityClass 实体Bean的类型。如User.class
     * @param jpql JPQL语句
     * @param params 零个或多个参数
     * @return 返回List<E>对象 
     */
    public <E> List<E> findByJPQL(Map<String, Object> hints, Class<E> entityClass,String jpql,Object... params);

    /**
     * 根据SQL语句查询
     * @param sql SQL语句
     * @param params 零个或多个参数
     * @return 返回List<T>对象 
     */
    @SuppressWarnings("rawtypes")
    public List findBySQL(String sql,Object... params);

    /**
     * 根据SQL语句查询
     * @param entityClass 实体Bean的类型。如User.class
     * @param sql SQL语句
     * @param params 零个或多个参数
     * @return 返回List<T>对象 
     */
    public <E> List<E> findBySQL(Class<E> entityClass,String sql,Object... params);

    /**
     * 根据SQL语句查询
     * @param hints jpa提供商参数(常用于设置二级缓存等参数)
     * @param sql SQL语句
     * @param params 零个或多个参数
     * @return 返回List<T>对象 
     */
    @SuppressWarnings("rawtypes")
    public List findBySQL(Map<String, Object> hints, String sql,Object... params);

    /**
     * 根据SQL语句查询
     * @param hints jpa提供商参数(常用于设置二级缓存等参数)
     * @param entityClass 实体Bean的类型。如User.class
     * @param sql SQL语句
     * @param params 零个或多个参数
     * @return 返回List<T>对象 
     */
    public <E> List<E> findBySQL(Map<String, Object> hints, Class<E> entityClass,String sql,Object... params);

    /**
     * 根据JPQL语句查询单条记录 
     * @param jpql JPQL语句
     * @param params 零个或多个参数
     * @return 返回单条记录 
     */
    public Object getSingleResultByJPQL(String jpql,Object... params);

    /**
     * 根据JPQL语句查询单条记录 
     * @param entityClass 实体Bean的类型。如User.class
     * @param jpql JPQL语句
     * @param params 零个或多个参数
     * @return 返回单条记录 
     */
    public <E> E getSingleResultByJPQL(Class<E> entityClass, String jpql, Object... params);

    /**
     * 根据JPQL语句查询单条记录 
     * @param hints jpa提供商参数(常用于设置二级缓存等参数)
     * @param entityClass 实体Bean的类型。如User.class
     * @param jpql JPQL语句
     * @param params 零个或多个参数
     * @return 返回单条记录 
     */
    public <E> E getSingleResultByJPQL(Map<String, Object> hints, Class<E> entityClass, String jpql, Object... params);

    /**
     * 根据SQL语句查询单条记录 
     * @param sql SQL语句
     * @param params 零个或多个参数
     * @return 返回单条记录 
     */
    public Object getSingleResultBySQL(String sql,Object... params);

    /**
     * 根据SQL语句查询单条记录 
     * @param entityClass 实体Bean的类型。如User.class
     * @param sql SQL语句
     * @param params 零个或多个参数
     * @return 返回单条记录 
     */
    public <E> E getSingleResultBySQL(Class<E> entityClass, String sql, Object... params);

    /**
     * 根据SQL语句查询单条记录 
     * @param hints jpa提供商参数(常用于设置二级缓存等参数)
     * @param sql SQL语句
     * @param params 零个或多个参数
     * @return 返回单条记录 
     */
    public Object getSingleResultBySQL(Map<String, Object> hints, String sql,Object... params);

    /**
     * 根据SQL语句查询单条记录 
     * @param hints jpa提供商参数(常用于设置二级缓存等参数)
     * @param entityClass 实体Bean的类型。如User.class
     * @param sql SQL语句
     * @param params 零个或多个参数
     * @return 返回单条记录 
     */
    public <E> E getSingleResultBySQL(Map<String, Object> hints, Class<E> entityClass, String sql, Object... params);

    /**
     * 根据JPQL语句查询单条记录 
     * @param jpql JPQL语句
     * @param params 零个或多个参数
     * @return 返回单条记录 
     */
    public Long getSingleResultForLongByJPQL(String jpql,Object... params);

    /**
     * 根据SQL语句查询单条记录 
     * @param sql SQL语句
     * @param params 零个或多个参数
     * @return 返回单条记录 
     */
    public Long getSingleResultForLongBySQL(String sql,Object... params);

    /***
     * 根据主键获取实体
     * @param id 主键
     * @return 实体
     */
    public T find(Serializable id);

    /***
     * 根据主键获取指定实体
     * @param entityClass 实体Bean的类型。如User.class
     * @param id 主键
     * @return 实体
     */
    public <E> E find(Class<E> entityClass,Serializable id);

    /**
     * 查询实体的所有记录
     * @return
     */
    public List<T> findAll();

    /**
     * 查询实体的所有记录
     * @param entityClass 实体Bean的类型。如User.class
     * @return
     */
    public <E> List<E> findAll(Class<E> entityClass);

    /**
     * 查询实体的所有记录
     * @param orderby 排序属性key:属性;value:ASC或DESC
     * @return
     */
    public List<T> findAll(Map<String,String> orderby);

    /**
     * 查询实体的所有记录
     * @param entityClass 实体Bean的类型。如User.class
     * @param orderby 排序属性key:属性;value:ASC或DESC
     * @return
     */
    public <E> List<E> findAll(Class<E> entityClass,Map<String,String> orderby);
    
    /**
     * 查询实体的所有记录
     * @param hints jpa提供商参数(常用于设置二级缓存等参数)
     * @param entityClass 实体Bean的类型。如User.class
     * @return
     */
    public <E> List<E> findAll(Map<String, Object> hints, Class<E> entityClass);

    /**
     * 查询实体的所有记录
     * @param hints jpa提供商参数(常用于设置二级缓存等参数)
     * @param entityClass 实体Bean的类型。如User.class
     * @param orderby 排序属性key:属性;value:ASC或DESC
     * @return
     */
    public <E> List<E> findAll(Map<String, Object> hints, Class<E> entityClass,Map<String,String> orderby);

    /***
     * 根据主键获取实体
     * @param propertyName 比较的实体属性名
     * @param whereValue 按条件的值
     * @return 实体
     */
    public T findBy(String wherePropertyName,Object whereValue);
    
    /***
     * 根据多个属性条件获取实体
     * @param whereProperties 比较的实体属性集合(Map<String,Object>),key:比较的属性名,value:比较的属性值
     * @return 实体
     */
    public T findBy(Map<String,Object> whereProperties);

    /***
     * 根据指定属性名和值获取对应实体
     * @param entityClass 实体Bean的类型。如User.class
     * @param propertyName 比较的实体属性名
     * @param whereValue 按条件的值
     * @return 实体
     */
    public <E> E findBy(Class<E> entityClass,String wherePropertyName,Object whereValue);

    /***
     * 根据多个属性名条件获取对应实体
     * @param entityClass 实体Bean的类型。如User.class
     * @param whereProperties 比较的实体属性集合(Map<String,Object>),key:比较的属性名,value:比较的属性值
     * @return 实体
     */
    public <E> E findBy(Class<E> entityClass,Map<String,Object> whereProperties);

    /***
     * 根据指定属性名和值获取对应实体
     * @param hints jpa提供商参数(常用于设置二级缓存等参数)
     * @param entityClass 实体Bean的类型。如User.class
     * @param propertyName 比较的实体属性名
     * @param whereValue 按条件的值
     * @return 实体
     */
    public <E> E findBy(Map<String, Object> hints, Class<E> entityClass,String wherePropertyName,Object whereValue);

    /***
     * 根据多个属性名条件获取对应实体
     * @param hints jpa提供商参数(常用于设置二级缓存等参数)
     * @param entityClass 实体Bean的类型。如User.class
     * @param whereProperties 比较的实体属性集合(Map<String,Object>),key:比较的属性名,value:比较的属性值
     * @return 实体
     */
    public <E> E findBy(Map<String, Object> hints, Class<E> entityClass,Map<String,Object> whereProperties);

    /**
     * 根据指定属性名和值查询实体的所有记录
     * @param propertyName 比较的实体属性名
     * @param whereValue 按条件的值
     * @return
     */
    public List<T> findAllBy(String wherePropertyName,Object whereValue);
    
    /**
     * 根据多个属性名条件查询实体的所有记录
     * @param whereProperties 比较的实体属性集合(Map<String,Object>),key:比较的属性名,value:比较的属性值
     * @return
     */
    public List<T> findAllBy(Map<String,Object> whereProperties);

    /**
     * 根据指定属性名和值查询实体的所有记录
     * @param entityClass 实体Bean的类型。如User.class
     * @param propertyName 比较的实体属性名
     * @param whereValue 按条件的值
     * @return
     */
    public <E> List<E> findAllBy(Class<E> entityClass,String wherePropertyName,Object whereValue);
    
    /**
     * 根据多个属性名条件查询实体的所有记录
     * @param entityClass 实体Bean的类型。如User.class
     * @param whereProperties 比较的实体属性集合(Map<String,Object>),key:比较的属性名,value:比较的属性值
     * @return
     */
    public <E> List<E> findAllBy(Class<E> entityClass,Map<String,Object> whereProperties);

    /**
     * 根据指定属性名和值查询实体的所有记录
     * @param orderby 排序属性key:属性;value:ASC或DESC
     * @param propertyName 比较的实体属性名
     * @param whereValue 按条件的值
     * @return
     */
    public List<T> findAllBy(Map<String,String> orderby,String wherePropertyName,Object whereValue);
    
    /**
     * 根据多个属性名条件查询实体的所有记录
     * @param whereProperties 比较的实体属性集合(Map<String,Object>),key:比较的属性名,value:比较的属性值
     * @param orderby 排序属性key:属性;value:ASC或DESC
     * @return
     */
    public List<T> findAllBy(Map<String,Object> whereProperties, Map<String,String> orderby);

    /**
     * 根据指定属性名和值查询实体的所有记录
     * @param entityClass 实体Bean的类型。如User.class
     * @param orderby 排序属性key:属性;value:ASC或DESC
     * @param propertyName 比较的实体属性名
     * @param whereValue 按条件的值
     * @return
     */
    public <E> List<E> findAllBy(Class<E> entityClass,Map<String,String> orderby,String wherePropertyName,Object whereValue);
    
    /**
     * 根据多个属性名条件查询实体的所有记录
     * @param entityClass 实体Bean的类型。如User.class
     * @param whereProperties 比较的实体属性集合(Map<String,Object>),key:比较的属性名,value:比较的属性值
     * @param orderby 排序属性key:属性;value:ASC或DESC
     * @return
     */
    public <E> List<E> findAllBy(Class<E> entityClass,Map<String,Object> whereProperties,Map<String,String> orderby);

    /**
     * 根据指定属性名和值查询实体的所有记录
     * @param hints jpa提供商参数(常用于设置二级缓存等参数)
     * @param entityClass 实体Bean的类型。如User.class
     * @param propertyName 比较的实体属性名
     * @param whereValue 按条件的值
     * @return
     */
    public <E> List<E> findAllBy(Map<String, Object> hints, Class<E> entityClass,String wherePropertyName,Object whereValue);

    /**
     * 根据多个属性名条件查询实体的所有记录
     * @param hints jpa提供商参数(常用于设置二级缓存等参数)
     * @param entityClass 实体Bean的类型。如User.class
     * @param whereProperties 比较的实体属性集合(Map<String,Object>),key:比较的属性名,value:比较的属性值
     * @return
     */
    public <E> List<E> findAllBy(Map<String, Object> hints, Class<E> entityClass,Map<String,Object> whereProperties);

    /**
     * 根据指定属性名和值查询实体的所有记录
     * @param hints jpa提供商参数(常用于设置二级缓存等参数)
     * @param entityClass 实体Bean的类型。如User.class
     * @param orderby 排序属性key:属性;value:ASC或DESC
     * @param propertyName 比较的实体属性名
     * @param whereValue 按条件的值
     * @return
     */
    public <E> List<E> findAllBy(Map<String, Object> hints, Class<E> entityClass,Map<String,String> orderby,String wherePropertyName,Object whereValue);

    /**
     * 根据多个属性名条件查询实体的所有记录
     * @param hints jpa提供商参数(常用于设置二级缓存等参数)
     * @param entityClass 实体Bean的类型。如User.class
     * @param whereProperties 比较的实体属性集合(Map<String,Object>),key:比较的属性名,value:比较的属性值
     * @param orderby 排序属性key:属性;value:ASC或DESC
     * @return
     */
    public <E> List<E> findAllBy(Map<String, Object> hints, Class<E> entityClass,Map<String,Object> whereProperties,Map<String,String> orderby);

    /**
     * 按分页查询实体的所有数据
     * @param form 前台Form对象(包含分页信息)
     * @return 返回PageView<T>对象
     */
    public PageView<T> getScrollData(F form);
    
    /**
     * 按分页查询实体的所有数据
     * @param form 前台Form对象(包含分页信息)
     * @param entityClass 实体Bean的类型。如User.class
     * @return 返回PageView<E>对象
     */
    public <E> PageView<E> getScrollData(F form,Class<E> entityClass);

    /**
     * 按分页查询实体的所有数据
     * @param form 前台Form对象(包含分页信息)
     * @param whereJPQL 条件JPQL语句
     * @param params 零个或多个参数
     * @return 返回PageView<T>对象
     */
    public PageView<T> getScrollData(F form, String whereJPQL, Object... params);
    
    /**
     * 按分页查询实体的所有数据
     * @param form 前台Form对象(包含分页信息)
     * @param entityClass 实体Bean的类型。如User.class
     * @param whereJPQL 条件JPQL语句
     * @param params 零个或多个参数
     * @return 返回PageView<E>对象
     */
    public <E> PageView<E> getScrollData(F form,Class<E> entityClass, String whereJPQL, Object... params);

    /**
     * 按分页查询实体的所有数据
     * @param hints jpa提供商参数(常用于设置二级缓存等参数)
     * @param form 前台Form对象(包含分页信息)
     * @param entityClass 实体Bean的类型。如User.class
     * @return 返回PageView<E>对象
     */
    public <E> PageView<E> getScrollData(Map<String, Object> hints, F form,Class<E> entityClass);

    /**
     * 按分页查询实体的所有数据
     * @param hints jpa提供商参数(常用于设置二级缓存等参数)
     * @param form 前台Form对象(包含分页信息)
     * @param entityClass 实体Bean的类型。如User.class
     * @param whereJPQL 条件JPQL语句
     * @param params 零个或多个参数
     * @return 返回PageView<E>对象
     */
    public <E> PageView<E> getScrollData(Map<String, Object> hints, F form,Class<E> entityClass, String whereJPQL, Object... params);

    /**
     * 根据JPQL语句分页查询
     * @param form 前台Form对象(包含分页信息)
     * @param jpql JPQL语句
     * @param params 零个或多个参数
     * @return 返回PageView<T>对象
     */
    public PageView<T> getScrollDataByJPQL(F form, String jpql,Object... params);
    
    /**
     * 根据JPQL语句分页查询
     * @param form 前台Form对象(包含分页信息)
     * @param entityClass 实体Bean的类型。如User.class
     * @param jpql JPQL语句
     * @param params 零个或多个参数
     * @return 返回PageView<E>对象
     */
    public <E> PageView<E> getScrollDataByJPQL(F form,Class<E> entityClass, String jpql,Object... params);
    
    /**
     * 根据JPQL语句分页查询
     * @param totalJpql 查询总页数JPQL语句
     * @param form 前台Form对象(包含分页信息)
     * @param entityClass 实体Bean的类型。如User.class
     * @param jpql JPQL语句
     * @param params 零个或多个参数
     * @return 返回PageView<E>对象
     */
    public <E> PageView<E> getScrollDataByJPQL(String totalJpql,F form, Class<E> entityClass, String jpql, Object... params);

    /**
     * 根据JPQL语句分页查询
     * @param hints jpa提供商参数(常用于设置二级缓存等参数)
     * @param form 前台Form对象(包含分页信息)
     * @param entityClass 实体Bean的类型。如User.class
     * @param jpql JPQL语句
     * @param params 零个或多个参数
     * @return 返回PageView<E>对象
     */
    public <E> PageView<E> getScrollDataByJPQL(Map<String, Object> hints, F form,Class<E> entityClass, String jpql,Object... params);

    /**
     * 根据JPQL语句分页查询
     * @param hints jpa提供商参数(常用于设置二级缓存等参数)
     * @param totalJpql 查询总页数JPQL语句
     * @param form 前台Form对象(包含分页信息)
     * @param entityClass 实体Bean的类型。如User.class
     * @param jpql JPQL语句
     * @param params 零个或多个参数
     * @return 返回PageView<E>对象
     */
    public <E> PageView<E> getScrollDataByJPQL(Map<String, Object> hints, String totalJpql,F form, Class<E> entityClass, String jpql, Object... params);

    /**
     * 根据SQL语句分页查询
     * @param form 前台Form对象(包含分页信息)
     * @param sql SQL语句
     * @param params 零个或多个参数
     * @return 查询多个字段返回PageView<Object[]>对象;返回 查询一个字段返回PageView<Object>对象
     */
    @SuppressWarnings("rawtypes")
    public PageView getScrollDataBySQL(F form, String sql, Object... params);
    
    /**
     * 根据SQL语句分页查询
     * @param totalSql 查询总页数SQL语句
     * @param form 前台Form对象(包含分页信息)
     * @param sql SQL语句
     * @param params 零个或多个参数
     * @return 查询多个字段返回PageView<Object[]>对象;返回 查询一个字段返回PageView<Object>对象
     */
    @SuppressWarnings("rawtypes")
    public PageView getScrollDataBySQL(String totalSql, F form, String sql, Object... params);
    
    /**
     * 根据SQL语句分页查询
     * @param form 前台Form对象(包含分页信息)
     * @param entityClass 实体Bean的类型。如User.class
     * @param sql SQL语句
     * @param params 零个或多个参数
     * @return 查询多个字段返回PageView<Object[]>对象;返回 查询一个字段返回PageView<Object>对象
     */
    public <E> PageView<E> getScrollDataBySQL(F form, Class<E> entityClass, String sql, Object... params);
    
    /**
     * 根据SQL语句分页查询
     * @param totalSql 查询总页数SQL语句
     * @param form 前台Form对象(包含分页信息)
     * @param entityClass 实体Bean的类型。如User.class
     * @param sql SQL语句
     * @param params 零个或多个参数
     * @return 查询多个字段返回PageView<Object[]>对象;返回 查询一个字段返回PageView<Object>对象
     */
    public <E> PageView<E> getScrollDataBySQL(String totalSql, F form, Class<E> entityClass, String sql, Object... params);

    /**
     * 根据SQL语句分页查询
     * @param hints jpa提供商参数(常用于设置二级缓存等参数)
     * @param form 前台Form对象(包含分页信息)
     * @param sql SQL语句
     * @param params 零个或多个参数
     * @return 查询多个字段返回PageView<Object[]>对象;返回 查询一个字段返回PageView<Object>对象
     */
    @SuppressWarnings("rawtypes")
    public PageView getScrollDataBySQL(Map<String, Object> hints, F form, String sql, Object... params);

    /**
     * 根据SQL语句分页查询
     * @param hints jpa提供商参数(常用于设置二级缓存等参数)
     * @param totalSql 查询总页数SQL语句
     * @param form 前台Form对象(包含分页信息)
     * @param sql SQL语句
     * @param params 零个或多个参数
     * @return 查询多个字段返回PageView<Object[]>对象;返回 查询一个字段返回PageView<Object>对象
     */
    @SuppressWarnings("rawtypes")
    public PageView getScrollDataBySQL(Map<String, Object> hints, String totalSql, F form, String sql, Object... params);

    /**
     * 根据SQL语句分页查询
     * @param hints jpa提供商参数(常用于设置二级缓存等参数)
     * @param form 前台Form对象(包含分页信息)
     * @param entityClass 实体Bean的类型。如User.class
     * @param sql SQL语句
     * @param params 零个或多个参数
     * @return 查询多个字段返回PageView<Object[]>对象;返回 查询一个字段返回PageView<Object>对象
     */
    public <E> PageView<E> getScrollDataBySQL(Map<String, Object> hints, F form, Class<E> entityClass, String sql, Object... params);

    /**
     * 根据SQL语句分页查询
     * @param hints jpa提供商参数(常用于设置二级缓存等参数)
     * @param totalSql 查询总页数SQL语句
     * @param form 前台Form对象(包含分页信息)
     * @param entityClass 实体Bean的类型。如User.class
     * @param sql SQL语句
     * @param params 零个或多个参数
     * @return 查询多个字段返回PageView<Object[]>对象;返回 查询一个字段返回PageView<Object>对象
     */
    public <E> PageView<E> getScrollDataBySQL(Map<String, Object> hints, String totalSql, F form, Class<E> entityClass, String sql, Object... params);

    /**
     * 获得该实体对应的表的记录总数
     * @return 记录总数
     */
    public long getCount();

    /**
     * 获得该实体对应的表的记录总数
     * @param entityClass 实体Bean的类型。如User.class
     * @return 记录总数
     */
    public long getCount(Class<?> entityClass);
    
    /**
     * 根据多个属性名条件获得该实体对应的表的记录总数
     * @param propertyName 比较的实体属性名
     * @param whereValue 按条件的值
     * @return 记录总数
     */
    public long getCount(String wherePropertyName,Object whereValue);
    
    /**
     * 根据多个属性名条件查询该实体对应的表的记录总数
     * @param whereProperties 比较的实体属性集合(Map<String,Object>),key:比较的属性名,value:比较的属性值
     * @return 记录总数
     */
    public long getCount(Map<String,Object> whereProperties);

    /**
     * 根据指定属性名和值获得该实体对应的表的记录总数
     * @param entityClass 实体Bean的类型。如User.class
     * @param propertyName 比较的实体属性名
     * @param whereValue 按条件的值
     * @return 记录总数
     */
    public long getCount(Class<?> entityClass,String wherePropertyName,Object whereValue);
    
    /**
     * 根据多个属性名条件查询该实体对应的表的记录总数
     * @param entityClass 实体Bean的类型。如User.class
     * @param whereProperties 比较的实体属性集合(Map<String,Object>),key:比较的属性名,value:比较的属性值
     * @return 记录总数
     */
    public long getCount(Class<?> entityClass,Map<String,Object> whereProperties);

    /**
     * 获得实体的数字型的属性在数据库中的最大值
     * @param propertyName 实体的属性名
     * @return 最大值
     */
    public Long getMaxNum(String propertyName);

    /**
     * 获得实体的数字型的属性在数据库中的最大值
     * @param entityClass 实体Bean的类型。如User.class
     * @param propertyName 实体的属性名
     * @return 最大值
     */
    public Long getMaxNum(Class<?> entityClass,String propertyName);
    
    /**
     * 获得实体的数字型的属性在数据库中的最大值
     * @param propertyName 比较的实体属性名
     * @param wherePropertyName 按条件的实体属性名
     * @param whereValue 按条件的值
     * @return
     */
    public Long getMaxNum(String propertyName,String wherePropertyName,Object whereValue);
    
    /**
     * 获得实体的数字型的属性在数据库中的最大值
     * @param propertyName 比较的实体属性名
     * @param whereProperties 比较的实体属性集合(Map<String,Object>),key:比较的属性名,value:比较的属性值
     * @return
     */
    public Long getMaxNum(String propertyName,Map<String,Object> whereProperties);
    
    /**
     * 获得实体的数字型的属性在数据库中的最大值
     * @param entityClass 实体Bean的类型。如User.class
     * @param propertyName 比较的实体属性名
     * @param wherePropertyName 按条件的实体属性名
     * @param whereValue 按条件的值
     * @return
     */
    public Long getMaxNum(Class<?> entityClass,String propertyName,String wherePropertyName,Object whereValue);
    
    /**
     * 获得实体的数字型的属性在数据库中的最大值
     * @param entityClass 实体Bean的类型。如User.class
     * @param propertyName 比较的实体属性名
     * @param whereProperties 比较的实体属性集合(Map<String,Object>),key:比较的属性名,value:比较的属性值
     * @return
     */
    public Long getMaxNum(Class<?> entityClass,String propertyName,Map<String,Object> whereProperties);
    
    /**
     * 获得实体的下一个编号
     * @param entity 实体Bean对象。如User实例对象
     * @param propertyName 比较的实体属性名
     * @return
     */
    public Long getNextNum(Object entity,String propertyName);

    /**
     * 获得实体的下一个编号
     * @param entity 实体Bean对象。如User实例对象
     * @param propertyName 比较的实体属性名
     * @param parentPropertyName 父节点属性名
     * @return
     */
    public Long getNextNum(Object entity,String propertyName,String parentPropertyName);

    /**
     * 是否已存在
     * @param propertyName 比较的实体属性名
     * @param value 比较的值
     * @return
     */
    public boolean isExists(String propertyName,Object value);
    
    /**
     * 是否已存在
     * @param entityClass 实体Bean的类型。如User.class
     * @param propertyName 比较的实体属性名
     * @param value 比较的值
     * @return
     */
    public boolean isExists(Class<?> entityClass,String propertyName,Object value);
    
    /**
     * 是否已存在
     * @param propertyName 比较的实体属性名
     * @param value 比较的值
     * @param wherePropertyName 按条件的实体属性名
     * @param whereValue 按条件的值
     * @return
     */
    public boolean isExists(String propertyName,Object value,String wherePropertyName,Object whereValue);
    
    /**
     * 是否已存在
     * @param whereProperties 比较的实体属性集合(Map<String,Object>),key:比较的属性名,value:比较的属性值
     * @return
     */
    public boolean isExists(Map<String,Object> whereProperties);
    
    /**
     * 是否已存在
     * @param entityClass 实体Bean的类型。如User.class
     * @param propertyName 比较的实体属性名
     * @param value 比较的值
     * @param wherePropertyName 按条件的实体属性名
     * @param whereValue 按条件的值
     * @return
     */
    public boolean isExists(Class<?> entityClass,String propertyName,Object value,String wherePropertyName,Object whereValue);
    
    /**
     * 是否已存在
     * @param entityClass 实体Bean的类型。如User.class
     * @param whereProperties 比较的实体属性集合(Map<String,Object>),key:比较的属性名,value:比较的属性值
     * @return
     */
    public boolean isExists(Class<?> entityClass,Map<String,Object> whereProperties);
}

二、BaseQueryDaoImpl类

二、通用Dao层之BaseQueryDao接口与BaseQueryDaoImpl类

public class BaseQueryDaoImpl<T,F extends PageForm> extends BaseInternalDaoImpl<T, F> implements BaseQueryDao<T,F> {

    /* (non-Javadoc)
     * @see com.nenglong.base.dao.BaseQueryDao#findByJPQL(java.lang.String, java.lang.Object[])
     */
    public List<T> findByJPQL(final String jpql, final Object... params) {
        return findByJPQL(entityClass, jpql, params);
    }
    
    /* (non-Javadoc)
     * @see com.nenglong.base.dao.BaseQueryDao#findByJPQL(java.lang.Class, java.lang.String, java.lang.Object[])
     */
    @SuppressWarnings("unchecked")
    public <E> List<E> findByJPQL(final Class<E> entityClass, final String jpql, final Object... params) {
        Query query = em.createQuery(convertJPQL(jpql, params));
        setParameters(query, params);
        return query.getResultList();
    }

    /* (non-Javadoc)
     * @see com.nenglong.base.dao.BaseQueryDao#findByJPQL(java.util.Map, java.lang.Class, java.lang.String, java.lang.Object[])
     */
    @SuppressWarnings("unchecked")
    public <E> List<E> findByJPQL(final Map<String, Object> hints, final Class<E> entityClass, final String jpql, final Object... params) {
        Query query = em.createQuery(convertPosition(jpql, params));
        setParameters(query, params);
        setHints(query, hints);
        return query.getResultList();
    }

    /* (non-Javadoc)
     * @see com.nenglong.base.dao.BaseQueryDao#findBySQL(java.lang.String, java.lang.Object[])
     */
    @SuppressWarnings("rawtypes")
    public List findBySQL(final String sql, final Object... params) {
        Query query = em.createNativeQuery(sql);
        setParameters(query, params);
        return query.getResultList();
    }

    /* (non-Javadoc)
     * @see com.nenglong.base.dao.BaseQueryDao#findBySQL(java.lang.Class, java.lang.String, java.lang.Object[])
     */
    @SuppressWarnings("unchecked")
    public <E> List<E> findBySQL(final Class<E> entityClass, final String sql, final Object... params) {
        Query query = em.createNativeQuery(sql, entityClass);
        setParameters(query, params);
        return query.getResultList();
    }

    /* (non-Javadoc)
     * @see com.nenglong.base.dao.BaseQueryDao#findBySQL(java.util.Map, java.lang.String, java.lang.Object[])
     */
    @SuppressWarnings("rawtypes")
    public List findBySQL(final Map<String, Object> hints, final String sql, final Object... params) {
        Query query = em.createNativeQuery(sql);
        setParameters(query, params);
        setHints(query, hints);
        return query.getResultList();
    }

    /* (non-Javadoc)
     * @see com.nenglong.base.dao.BaseQueryDao#findBySQL(java.util.Map, java.lang.Class, java.lang.String, java.lang.Object[])
     */
    @SuppressWarnings("unchecked")
    public <E> List<E> findBySQL(final Map<String, Object> hints, final Class<E> entityClass, final String sql, final Object... params) {
        Query query = em.createNativeQuery(sql, entityClass);
        setParameters(query, params);
        setHints(query, hints);
        return query.getResultList();
    }

    /* (non-Javadoc)
     * @see com.nenglong.base.dao.BaseQueryDao#getSingleResultByJPQL(java.lang.String, java.lang.Object[])
     */
    public Object getSingleResultByJPQL(final String jpql, final Object... params) {
        List<Object> list = findByJPQL(Object.class, jpql, params);
        return list.size()>0 ? list.get(0) : null;
    }

    /* (non-Javadoc)
     * @see com.nenglong.base.dao.BaseQueryDao#getSingleResultByJPQL(java.lang.Class, java.lang.String, java.lang.Object[])
     */
    public <E> E getSingleResultByJPQL(final Class<E> entityClass, final String jpql, final Object... params) {
        List<E> list = findByJPQL(entityClass, jpql, params);
        return list.size()>0 ? list.get(0) : null;
    }

    /* (non-Javadoc)
     * @see com.nenglong.base.dao.BaseQueryDao#getSingleResultByJPQL(java.util.Map, java.lang.Class, java.lang.String, java.lang.Object[])
     */
    public <E> E getSingleResultByJPQL(final Map<String, Object> hints, final Class<E> entityClass, final String jpql, final Object... params) {
        List<E> list = findByJPQL(hints, entityClass, jpql, params);
        return list.size()>0 ? list.get(0) : null;
    }

    /* (non-Javadoc)
     * @see com.nenglong.base.dao.BaseQueryDao#getSingleResultBySQL(java.lang.String, java.lang.Object[])
     */
    public Object getSingleResultBySQL(final String sql, final Object... params) {
        List<?> list = findBySQL(sql, params);
        return list.size()>0 ? list.get(0) : null;
        
    }

    /* (non-Javadoc)
     * @see com.nenglong.base.dao.BaseQueryDao#getSingleResultBySQL(java.lang.Class, java.lang.String, java.lang.Object[])
     */
    public <E> E getSingleResultBySQL(final Class<E> entityClass, final String sql, final Object... params) {
        List<E> list = findBySQL(entityClass, sql, params);
        return list.size()>0 ? list.get(0) : null;
        
    }

    /* (non-Javadoc)
     * @see com.nenglong.base.dao.BaseQueryDao#getSingleResultBySQL(java.util.Map, java.lang.String, java.lang.Object[])
     */
    public Object getSingleResultBySQL(final Map<String, Object> hints, final String sql, final Object... params) {
        List<?> list = findBySQL(hints, sql, params);
        return list.size()>0 ? list.get(0) : null;
        
    }

    /* (non-Javadoc)
     * @see com.nenglong.base.dao.BaseQueryDao#getSingleResultBySQL(java.util.Map, java.lang.Class, java.lang.String, java.lang.Object[])
     */
    public <E> E getSingleResultBySQL(final Map<String, Object> hints, final Class<E> entityClass, final String sql, final Object... params) {
        List<E> list = findBySQL(hints, entityClass, sql, params);
        return list.size()>0 ? list.get(0) : null;
        
    }

    /* (non-Javadoc)
     * @see com.nenglong.base.dao.BaseQueryDao#getSingleResultForLongByJPQL(java.lang.String, java.lang.Object[])
     */
    public Long getSingleResultForLongByJPQL(final String jpql, final Object... params) {
        Object obj = getSingleResultByJPQL(jpql, params);
        return objectToLong(obj);
    }

    /* (non-Javadoc)
     * @see com.nenglong.base.dao.BaseQueryDao#getSingleResultForLongBySQL(java.lang.String, java.lang.Object[])
     */
    public Long getSingleResultForLongBySQL(final String sql, final Object... params) {
        Object obj = getSingleResultBySQL(sql, params);
        return objectToLong(obj);
    }

    /* (non-Javadoc)
     * @see com.nenglong.base.dao.BaseQueryDao#find(java.io.Serializable)
     */
    public T find(final Serializable id) {
        return find(entityClass, id);
    }

    /* (non-Javadoc)
     * @see com.nenglong.base.dao.BaseQueryDao#find(java.lang.Class, java.io.Serializable)
     */
    public <E> E find(final Class<E> entityClass, final Serializable id) {
        return em.find(entityClass, id);
//        return findBy(entityClass, getIdPropertyName(entityClass), id);
    }

    /* (non-Javadoc)
     * @see com.nenglong.base.dao.BaseQueryDao#findBy(java.lang.String, java.lang.Object)
     */
    public T findBy(final String wherePropertyName, final Object whereValue) {
        return findBy(entityClass, wherePropertyName, whereValue);
    }

    /* (non-Javadoc)
     * @see com.nenglong.base.dao.BaseQueryDao#findBy(java.lang.Class, java.lang.String, java.lang.Object)
     */
    public <E> E findBy(final Class<E> entityClass, final String wherePropertyName,final Object whereValue) {
        StringBuilder sb = new StringBuilder();
        sb.append("from ");
        sb.append(getEntityName(entityClass));
        sb.append(" where ");
        sb.append(wherePropertyName);
        sb.append("=?1");
        return getSingleResultByJPQL(entityClass, sb.toString(), whereValue);
    }
    
    /* (non-Javadoc)
     * @see com.nenglong.base.dao.BaseQueryDao#findBy(java.util.Map)
     */
    public T findBy(final Map<String,Object> whereProperties) {
        return findBy(entityClass, whereProperties);
    }

    /* (non-Javadoc)
     * @see com.nenglong.base.dao.BaseQueryDao#findBy(java.lang.Class, java.util.Map)
     */
    public <E> E findBy(final Class<E> entityClass, final Map<String,Object> whereProperties) {
        StringBuilder sb = new StringBuilder();
        sb.append("from ");
        sb.append(getEntityName(entityClass));
        List<Object> params = new ArrayList<Object>();
        if(whereProperties!=null && whereProperties.size()>0){
            sb.append(" where ");
            Set<Entry<String, Object>> set = whereProperties.entrySet();
            int i=0;
            for (Entry<String, Object> entry : set) {
                if(i>0)
                    sb.append(" and ");
                sb.append(entry.getKey());
                if(entry.getValue()==null){
                    sb.append(" is null");
                }else{
                    sb.append("=?");
                    params.add(entry.getValue());
                }
                i++;
            }
        }
        return getSingleResultByJPQL(entityClass, sb.toString(), params.toArray());
    }

    /* (non-Javadoc)
     * @see com.nenglong.base.dao.BaseQueryDao#findBy(java.util.Map, java.lang.Class, java.lang.String, java.lang.Object)
     */
    public <E> E findBy(final Map<String, Object> hints, final Class<E> entityClass, final String wherePropertyName,final Object whereValue) {
        StringBuilder sb = new StringBuilder();
        sb.append("from ");
        sb.append(getEntityName(entityClass));
        sb.append(" where ");
        sb.append(wherePropertyName);
        sb.append("=?1");
        return getSingleResultByJPQL(hints, entityClass, sb.toString(), whereValue);
    }

    /* (non-Javadoc)
     * @see com.nenglong.base.dao.BaseQueryDao#findBy(java.util.Map, java.lang.Class, java.util.Map)
     */
    public <E> E findBy(final Map<String, Object> hints, final Class<E> entityClass, final Map<String,Object> whereProperties) {
        StringBuilder sb = new StringBuilder();
        sb.append("from ");
        sb.append(getEntityName(entityClass));
        List<Object> params = new ArrayList<Object>();
        if(whereProperties!=null && whereProperties.size()>0){
            sb.append(" where ");
            Set<Entry<String, Object>> set = whereProperties.entrySet();
            int i=0;
            for (Entry<String, Object> entry : set) {
                if(i>0)
                    sb.append(" and ");
                sb.append(entry.getKey());
                if(entry.getValue()==null){
                    sb.append(" is null");
                }else{
                    sb.append("=?");
                    params.add(entry.getValue());
                }
                i++;
            }
        }
        return getSingleResultByJPQL(hints, entityClass, sb.toString(), params.toArray());
    }

    /* (non-Javadoc)
     * @see com.nenglong.base.dao.BaseQueryDao#findAll()
     */
    public List<T> findAll() {
        return findAll(entityClass);
    }

    /* (non-Javadoc)
     * @see com.nenglong.base.dao.BaseQueryDao#findAll(java.lang.Class)
     */
    public <E> List<E> findAll(final Class<E> entityClass) {
        return findAll(entityClass, null);
    }

    /* (non-Javadoc)
     * @see com.nenglong.base.dao.BaseQueryDao#findAll(java.util.Map)
     */
    public List<T> findAll(final Map<String, String> orderby) {
        return findAll(entityClass, orderby);
    }

    /* (non-Javadoc)
     * @see com.nenglong.base.dao.BaseQueryDao#findAll(java.lang.Class, java.util.Map)
     */
    public <E> List<E> findAll(final Class<E> entityClass, final Map<String, String> orderby) {
        StringBuilder sb = new StringBuilder("from ");
        sb.append(getEntityName(entityClass));
        if(orderby!=null && orderby.size()>0){
            sb.append(" order by ");
            Set<String> keys = orderby.keySet();
            int i=-1;
            for (String key : keys) {
                if(++i>=1){
                    sb.append(" , ");
                }
                sb.append(key);
                sb.append(" ");
                sb.append(orderby.get(key));
            }
        }
        return findByJPQL(entityClass, sb.toString());
    }
    
    /* (non-Javadoc)
     * @see com.nenglong.base.dao.BaseQueryDao#findAll(java.util.Map, java.lang.Class)
     */
    public <E> List<E> findAll(final Map<String, Object> hints, final Class<E> entityClass) {
        return findAll(hints, entityClass, null);
    }

    /* (non-Javadoc)
     * @see com.nenglong.base.dao.BaseQueryDao#findAll(java.util.Map, java.lang.Class, java.util.Map)
     */
    public <E> List<E> findAll(final Map<String, Object> hints, final Class<E> entityClass, final Map<String, String> orderby) {
        StringBuilder sb = new StringBuilder("from ");
        sb.append(getEntityName(entityClass));
        if(orderby!=null && orderby.size()>0){
            sb.append(" order by ");
            Set<String> keys = orderby.keySet();
            int i=-1;
            for (String key : keys) {
                if(++i>=1){
                    sb.append(" , ");
                }
                sb.append(key);
                sb.append(" ");
                sb.append(orderby.get(key));
            }
        }
        return findByJPQL(hints, entityClass, sb.toString());
    }

    /* (non-Javadoc)
     * @see com.nenglong.base.dao.BaseQueryDao#findAllBy(java.lang.String, java.lang.Object)
     */
    public List<T> findAllBy(final String wherePropertyName, final Object whereValue) {
        return findAllBy(entityClass, wherePropertyName, whereValue);
    }
    
    /* (non-Javadoc)
     * @see com.nenglong.base.dao.BaseQueryDao#findAllBy(java.util.Map)
     */
    public List<T> findAllBy(final Map<String,Object> whereProperties) {
        return findAllBy(entityClass, whereProperties);
    }

    /* (non-Javadoc)
     * @see com.nenglong.base.dao.BaseQueryDao#findAllBy(java.lang.Class, java.lang.String, java.lang.Object)
     */
    public <E> List<E> findAllBy(final Class<E> entityClass,final String wherePropertyName, final Object whereValue) {
        return findAllBy(entityClass, null, wherePropertyName, whereValue);
    }
    
    /* (non-Javadoc)
     * @see com.nenglong.base.dao.BaseQueryDao#findAllBy(java.lang.Class, java.util.Map)
     */
    public <E> List<E> findAllBy(final Class<E> entityClass, final Map<String,Object> whereProperties) {
        return findAllBy(entityClass, whereProperties, null);
    }

    /* (non-Javadoc)
     * @see com.nenglong.base.dao.BaseQueryDao#findAllBy(java.util.Map, java.lang.String, java.lang.Object)
     */
    public List<T> findAllBy(final Map<String, String> orderby, final String wherePropertyName, final Object whereValue) {
        return findAllBy(entityClass, orderby, wherePropertyName, whereValue);
    }

    /* (non-Javadoc)
     * @see com.nenglong.base.dao.BaseQueryDao#findAllBy(java.util.Map, java.util.Map)
     */
    public List<T> findAllBy(final Map<String,Object> whereProperties, final Map<String, String> orderby) {
        return findAllBy(entityClass, whereProperties, orderby);
    }

    /* (non-Javadoc)
     * @see com.nenglong.base.dao.BaseQueryDao#findAllBy(java.lang.Class, java.util.Map, java.lang.String, java.lang.Object)
     */
    public <E> List<E> findAllBy(final Class<E> entityClass, final Map<String, String> orderby, final String wherePropertyName,final Object whereValue) {
        StringBuilder sb = new StringBuilder("from ");
        sb.append(getEntityName(entityClass));
        sb.append(" where ");
        sb.append(wherePropertyName);
        sb.append("=?");
        
        if(orderby!=null && orderby.size()>0){
            sb.append(" order by ");
            Set<String> keys = orderby.keySet();
            int i=-1;
            for (String key : keys) {
                if(++i>=1){
                    sb.append(" , ");
                }
                sb.append(key);
                sb.append(" ");
                sb.append(orderby.get(key));
            }
        }
        
        return findByJPQL(entityClass, sb.toString(), whereValue);
    }

    /* (non-Javadoc)
     * @see com.nenglong.base.dao.BaseQueryDao#findAllBy(java.lang.Class, java.util.Map, java.util.Map)
     */
    public <E> List<E> findAllBy(final Class<E> entityClass, final Map<String,Object> whereProperties, final Map<String, String> orderby) {
        StringBuilder sb = new StringBuilder();
        sb.append("from ");
        sb.append(getEntityName(entityClass));
        List<Object> params = new ArrayList<Object>();
        if(whereProperties!=null && whereProperties.size()>0){
            sb.append(" where ");
            Set<Entry<String, Object>> set = whereProperties.entrySet();
            int i=0;
            for (Entry<String, Object> entry : set) {
                if(i>0)
                    sb.append(" and ");
                sb.append(entry.getKey());
                if(entry.getValue()==null){
                    sb.append(" is null");
                }else{
                    sb.append("=?");
                    params.add(entry.getValue());
                }
                i++;
            }
        }
        
        if(orderby!=null && orderby.size()>0){
            sb.append(" order by ");
            Set<String> keys = orderby.keySet();
            int i=-1;
            for (String key : keys) {
                if(++i>=1){
                    sb.append(" , ");
                }
                sb.append(key);
                sb.append(" ");
                sb.append(orderby.get(key));
            }
        }
        
        return findByJPQL(entityClass, sb.toString(), params.toArray());
    }

    /* (non-Javadoc)
     * @see com.nenglong.base.dao.BaseQueryDao#findAllBy(java.util.Map, java.lang.Class, java.lang.String, java.lang.Object)
     */
    public <E> List<E> findAllBy(final Map<String, Object> hints, final Class<E> entityClass,final String wherePropertyName, final Object whereValue) {
        return findAllBy(hints, entityClass, null, wherePropertyName, whereValue);
    }

    /* (non-Javadoc)
     * @see com.nenglong.base.dao.BaseQueryDao#findAllBy(java.util.Map, java.lang.Class, java.util.Map)
     */
    public <E> List<E> findAllBy(final Map<String, Object> hints, final Class<E> entityClass, final Map<String,Object> whereProperties) {
        return findAllBy(hints, entityClass, whereProperties, null);
    }

    /* (non-Javadoc)
     * @see com.nenglong.base.dao.BaseQueryDao#findAllBy(java.util.Map, java.lang.Class, java.util.Map, java.lang.String, java.lang.Object)
     */
    public <E> List<E> findAllBy(final Map<String, Object> hints, final Class<E> entityClass, final Map<String, String> orderby, final String wherePropertyName,final Object whereValue) {
        StringBuilder sb = new StringBuilder("from ");
        sb.append(getEntityName(entityClass));
        sb.append(" where ");
        sb.append(wherePropertyName);
        sb.append("=?");
        
        if(orderby!=null && orderby.size()>0){
            sb.append(" order by ");
            Set<String> keys = orderby.keySet();
            int i=-1;
            for (String key : keys) {
                if(++i>=1){
                    sb.append(" , ");
                }
                sb.append(key);
                sb.append(" ");
                sb.append(orderby.get(key));
            }
        }
        
        return findByJPQL(hints, entityClass, sb.toString(), whereValue);
    }

    /* (non-Javadoc)
     * @see com.nenglong.base.dao.BaseQueryDao#findAllBy(java.util.Map, java.lang.Class, java.util.Map, java.util.Map)
     */
    public <E> List<E> findAllBy(final Map<String, Object> hints, final Class<E> entityClass, final Map<String,Object> whereProperties, final Map<String, String> orderby) {
        StringBuilder sb = new StringBuilder();
        sb.append("from ");
        sb.append(getEntityName(entityClass));
        List<Object> params = new ArrayList<Object>();
        if(whereProperties!=null && whereProperties.size()>0){
            sb.append(" where ");
            Set<Entry<String, Object>> set = whereProperties.entrySet();
            int i=0;
            for (Entry<String, Object> entry : set) {
                if(i>0)
                    sb.append(" and ");
                sb.append(entry.getKey());
                if(entry.getValue()==null){
                    sb.append(" is null");
                }else{
                    sb.append("=?");
                    params.add(entry.getValue());
                }
                i++;
            }
        }
        
        if(orderby!=null && orderby.size()>0){
            sb.append(" order by ");
            Set<String> keys = orderby.keySet();
            int i=-1;
            for (String key : keys) {
                if(++i>=1){
                    sb.append(" , ");
                }
                sb.append(key);
                sb.append(" ");
                sb.append(orderby.get(key));
            }
        }
        
        return findByJPQL(hints, entityClass, sb.toString(), params.toArray());
    }

    /* (non-Javadoc)
     * @see com.nenglong.base.dao.BaseQueryDao#getScrollData(com.nenglong.base.pagination.PageForm)
     */
    public PageView<T> getScrollData(final F form) {
        return getScrollData(form, entityClass);
    }

    /* (non-Javadoc)
     * @see com.nenglong.base.dao.BaseQueryDao#getScrollData(com.nenglong.base.pagination.PageForm, java.lang.Class)
     */
    public <E> PageView<E> getScrollData(final F form, final Class<E> entityClass) {
        return getScrollData(form, entityClass, null);
    }

    /* (non-Javadoc)
     * @see com.nenglong.base.dao.BaseQueryDao#getScrollData(com.nenglong.base.pagination.PageForm, java.lang.String, java.lang.Object[])
     */
    public PageView<T> getScrollData(final F form, final String whereJPQL, final Object... params) {
        return getScrollData(form, entityClass, whereJPQL, params);
    }

    /* (non-Javadoc)
     * @see com.nenglong.base.dao.BaseQueryDao#getScrollData(com.nenglong.base.pagination.PageForm, java.lang.Class, java.lang.String, java.lang.Object[])
     */
    public <E> PageView<E> getScrollData(final F form, final Class<E> entityClass, final String whereJPQL, final Object... params) {
        StringBuilder sb = new StringBuilder("from ");
        sb.append(getEntityName(entityClass));
        
        if(StringUtils.isNotEmpty(whereJPQL)){
            sb.append(" ");
            if(!Pattern.compile("^\\s*where\\s*", Pattern.CASE_INSENSITIVE).matcher(whereJPQL).matches()){
                sb.append("where ");
            }
            sb.append(whereJPQL);
        }
        
        String totalJpql=new StringBuilder("select count(*) ").append(sb.toString()).toString();
        
        if(StringUtils.isNotEmpty(form.getSortBy())){
            sb.append(" order by ");
            sb.append(form.getSortBy());
            sb.append(" ");
            sb.append(form.getSortDir());
        }else{
            //没有设置排序,默认按主键倒序
            sb.append(" order by ");
            sb.append(getIdPropertyName(entityClass));
            sb.append(" desc ");
        }
        return getScrollDataByJPQL(totalJpql, form, entityClass, sb.toString(), params);
    }

    /* (non-Javadoc)
     * @see com.nenglong.base.dao.BaseQueryDao#getScrollData(java.util.Map, com.nenglong.base.pagination.PageForm, java.lang.Class)
     */
    public <E> PageView<E> getScrollData(final Map<String, Object> hints, final F form, final Class<E> entityClass) {
        return getScrollData(hints, form, entityClass, null);
    }

    /* (non-Javadoc)
     * @see com.nenglong.base.dao.BaseQueryDao#getScrollData(java.util.Map, com.nenglong.base.pagination.PageForm, java.lang.Class, java.lang.String, java.lang.Object[])
     */
    public <E> PageView<E> getScrollData(final Map<String, Object> hints, final F form, final Class<E> entityClass, final String whereJPQL, final Object... params) {
        StringBuilder sb = new StringBuilder("from ");
        sb.append(getEntityName(entityClass));
        
        if(StringUtils.isNotEmpty(whereJPQL)){
            sb.append(" ");
            if(!Pattern.compile("^\\s*where\\s*", Pattern.CASE_INSENSITIVE).matcher(whereJPQL).matches()){
                sb.append("where ");
            }
            sb.append(whereJPQL);
        }
        
        String totalJpql=new StringBuilder("select count(*) ").append(sb.toString()).toString();
        
        if(StringUtils.isNotEmpty(form.getSortBy())){
            sb.append(" order by ");
            sb.append(form.getSortBy());
            sb.append(" ");
            sb.append(form.getSortDir());
        }else{
            //没有设置排序,默认按主键倒序
            sb.append(" order by ");
            sb.append(getIdPropertyName(entityClass));
            sb.append(" desc ");
        }
        return getScrollDataByJPQL(hints, totalJpql, form, entityClass, sb.toString(), params);
    }

    /* (non-Javadoc)
     * @see com.nenglong.sshtest.base.dao.BaseQueryDao#getScrollDataByJPQL(int, int, java.lang.String, java.lang.Object[])
     */
    public PageView<T> getScrollDataByJPQL(final F form, final String jpql, final Object... params) {
        return getScrollDataByJPQL(form, entityClass, jpql, params);
    }

    /* (non-Javadoc)
     * @see com.nenglong.sshtest.base.dao.BaseQueryDao#getScrollDataByJPQL(java.lang.Class, int, int, java.lang.String, java.lang.Object[])
     */
    public <E> PageView<E> getScrollDataByJPQL(final F form, final Class<E> entityClass, final String jpql, final Object... params) {
        String totalJpql=null;
        if(Pattern.compile("^\\s*\\bfrom\\s.+", Pattern.CASE_INSENSITIVE).matcher(jpql).matches()){
            totalJpql = Pattern.compile("^\\s*\\bfrom\\b", Pattern.CASE_INSENSITIVE).matcher(jpql).replaceFirst("select count(*) from");
        }else{
            Matcher m = Pattern.compile("\\bfrom\\b",Pattern.CASE_INSENSITIVE).matcher(jpql);
            if(m.find()){
                totalJpql = new StringBuilder("select count(*) ").append(jpql.substring(m.start())).toString();
            }
        }
        return getScrollDataByJPQL(totalJpql,form, entityClass, jpql, params);
    }
    
    /* (non-Javadoc)
     * @see com.nenglong.base.dao.BaseQueryDao#getScrollDataByJPQL(java.lang.String, com.nenglong.base.pagination.PageForm, java.lang.Class, java.lang.String, java.lang.Object[])
     */
    @SuppressWarnings("unchecked")
    public <E> PageView<E> getScrollDataByJPQL(final String totalJpql, final F form, final Class<E> entityClass, final String jpql, final Object... params) {
        Query query = em.createQuery(convertJPQL(jpql, params));
        setParameters(query, params);
        
        PageView<E> pageView= new PageView<E>(form);
        
        if(pageView.getLimit()>0)
            query.setFirstResult(pageView.getStart()).setMaxResults(pageView.getLimit());
        
        pageView.setRows(query.getResultList());
        if(totalJpql!=null){
            long totalRecord = getSingleResultForLongByJPQL(convertJPQL(totalJpql, params), params);
            // 设置总记录数
            pageView.setTotal(totalRecord);
        }
        
        return pageView;
    }

    /* (non-Javadoc)
     * @see com.nenglong.base.dao.BaseQueryDao#getScrollDataByJPQL(java.util.Map, com.nenglong.base.pagination.PageForm, java.lang.Class, java.lang.String, java.lang.Object[])
     */
    public <E> PageView<E> getScrollDataByJPQL(final Map<String, Object> hints, final F form, final Class<E> entityClass, final String jpql, final Object... params) {
        String totalJpql=null;
        if(Pattern.compile("^\\s*\\bfrom\\s.+", Pattern.CASE_INSENSITIVE).matcher(jpql).matches()){
            totalJpql = Pattern.compile("^\\s*\\bfrom\\b", Pattern.CASE_INSENSITIVE).matcher(jpql).replaceFirst("select count(*) from");
        }else{
            Matcher m = Pattern.compile("\\bfrom\\b",Pattern.CASE_INSENSITIVE).matcher(jpql);
            if(m.find()){
                totalJpql = new StringBuilder("select count(*) ").append(jpql.substring(m.start())).toString();
            }
        }
        return getScrollDataByJPQL(hints, totalJpql, form, entityClass, jpql, params);
    }

    /* (non-Javadoc)
     * @see com.nenglong.base.dao.BaseQueryDao#getScrollDataByJPQL(java.util.Map, java.lang.String, com.nenglong.base.pagination.PageForm, java.lang.Class, java.lang.String, java.lang.Object[])
     */
    @SuppressWarnings("unchecked")
    public <E> PageView<E> getScrollDataByJPQL(final Map<String, Object> hints, final String totalJpql, final F form, final Class<E> entityClass, final String jpql, final Object... params) {
        Query query = em.createQuery(convertPosition(jpql, params));
        setParameters(query, params);
        setHints(query, hints);
        
        PageView<E> pageView= new PageView<E>(form);
        
        if(pageView.getLimit()>0)
            query.setFirstResult(pageView.getStart()).setMaxResults(pageView.getLimit());
        
        pageView.setRows(query.getResultList());
        if(totalJpql!=null){
            long totalRecord = getSingleResultForLongByJPQL(convertJPQL(totalJpql, params), params);
            // 设置总记录数
            pageView.setTotal(totalRecord);
        }
        
        return pageView;
    }

    /* (non-Javadoc)
     * @see com.nenglong.sshtest.base.dao.BaseQueryDao#getScrollDataBySQL(int, int, java.lang.String, java.lang.Object[])
     */
    @SuppressWarnings({ "rawtypes", "unchecked" })
    public PageView getScrollDataBySQL(final F form, final String sql, final Object... params) {
        String selectSql =sql;
        Query query = em.createNativeQuery(selectSql);
        setParameters(query, params);
        
        PageView pageView= new PageView(form);
        
        if(pageView.getLimit()>0)
            query.setFirstResult(pageView.getStart()).setMaxResults(pageView.getLimit());
        
        pageView.setRows(query.getResultList());
        
        //替换成查询总SQL语句
        Matcher matcher = Pattern.compile("(\\bfrom\\b)", Pattern.CASE_INSENSITIVE).matcher(selectSql);
        int count=0;
        while(matcher.find()){
            count++;
        }
        if(count >=2){
            //有子查询
            StringBuffer sb = new StringBuffer("select count(*) from ( ");
            sb.append(selectSql);
            sb.append(" ) totalRecord"); 
            selectSql = sb.toString();
        }else{            
            selectSql = Pattern.compile("^.*\\bfrom\\b", Pattern.CASE_INSENSITIVE)
            .matcher(selectSql).replaceFirst("select count(*) from");
        }
        
        long totalRecord = getSingleResultForLongBySQL(selectSql, params);
        // 设置总记录数
        pageView.setTotal(totalRecord);
        
        return pageView;
    }
    
    /* (non-Javadoc)
     * @see com.nenglong.base.dao.BaseQueryDao#getScrollDataBySQL(java.lang.String, com.nenglong.base.pagination.PageForm, java.lang.String, java.lang.Object[])
     */
    @SuppressWarnings({ "rawtypes", "unchecked" })
    public PageView getScrollDataBySQL(final String totalSql, final F form, final String sql, final Object... params) {
        Query query = em.createNativeQuery(sql);
        setParameters(query, params);
        
        PageView pageView= new PageView(form);
        
        if(pageView.getLimit()>0)
            query.setFirstResult(pageView.getStart()).setMaxResults(pageView.getLimit());
        
        pageView.setRows(query.getResultList());
        if(totalSql!=null){
            long totalRecord = getSingleResultForLongBySQL(totalSql, params);
            // 设置总记录数
            pageView.setTotal(totalRecord);
        }
        
        return pageView;
    }

    /* (non-Javadoc)
     * @see com.nenglong.base.dao.BaseQueryDao#getScrollDataBySQL(com.nenglong.base.pagination.PageForm, java.lang.Class, java.lang.String, java.lang.Object[])
     */
    @SuppressWarnings("unchecked")
    public <E> PageView<E> getScrollDataBySQL(final F form, final Class<E> entityClass, final String sql, final Object... params) {
        String selectSql = sql;
        Query query = em.createNativeQuery(selectSql, entityClass);
        setParameters(query, params);
        
        PageView<E> pageView= new PageView<E>(form);
        
        if(pageView.getLimit()>0)
            query.setFirstResult(pageView.getStart()).setMaxResults(pageView.getLimit());
        
        pageView.setRows(query.getResultList());
        
        //替换成查询总SQL语句
        Matcher matcher = Pattern.compile("(\\bfrom\\b)", Pattern.CASE_INSENSITIVE).matcher(selectSql);
        int count=0;
        while(matcher.find()){
            count++;
        }
        if(count >=2){
            //有子查询
            StringBuffer sb = new StringBuffer("select count(*) from ( ");
            sb.append(selectSql);
            sb.append(" ) totalRecord"); 
            selectSql = sb.toString();
        }else{            
            selectSql = Pattern.compile("^.*\\bfrom\\b", Pattern.CASE_INSENSITIVE)
            .matcher(selectSql).replaceFirst("select count(*) from");
        }
        
        long totalRecord = getSingleResultForLongBySQL(selectSql, params);
        // 设置总记录数
        pageView.setTotal(totalRecord);
        
        return pageView;
    }

    /* (non-Javadoc)
     * @see com.nenglong.base.dao.BaseQueryDao#getScrollDataBySQL(java.lang.String, com.nenglong.base.pagination.PageForm, java.lang.Class, java.lang.String, java.lang.Object[])
     */
    @SuppressWarnings("unchecked")
    public <E> PageView<E> getScrollDataBySQL(final String totalSql, final F form, final Class<E> entityClass, final String sql, final Object... params) {
        Query query = em.createNativeQuery(sql, entityClass);
        setParameters(query, params);
        
        PageView<E> pageView= new PageView<E>(form);
        
        if(pageView.getLimit()>0)
            query.setFirstResult(pageView.getStart()).setMaxResults(pageView.getLimit());
        
        pageView.setRows(query.getResultList());
        if(totalSql!=null){
            long totalRecord = getSingleResultForLongBySQL(totalSql, params);
            // 设置总记录数
            pageView.setTotal(totalRecord);
        }
        
        return pageView;
    }

    /* (non-Javadoc)
     * @see com.nenglong.base.dao.BaseQueryDao#getScrollDataBySQL(java.util.Map, com.nenglong.base.pagination.PageForm, java.lang.String, java.lang.Object[])
     */
    @SuppressWarnings({ "rawtypes", "unchecked" })
    public PageView getScrollDataBySQL(final Map<String, Object> hints, final F form, final String sql, final Object... params) {
        String selectSql =sql;
        Query query = em.createNativeQuery(selectSql);
        setParameters(query, params);
        setHints(query, hints);
        
        PageView pageView= new PageView(form);
        
        if(pageView.getLimit()>0)
            query.setFirstResult(pageView.getStart()).setMaxResults(pageView.getLimit());
        
        pageView.setRows(query.getResultList());
        
        //替换成查询总SQL语句
        Matcher matcher = Pattern.compile("(\\bfrom\\b)", Pattern.CASE_INSENSITIVE).matcher(selectSql);
        int count=0;
        while(matcher.find()){
            count++;
        }
        if(count >=2){
            //有子查询
            StringBuffer sb = new StringBuffer("select count(*) from ( ");
            sb.append(selectSql);
            sb.append(" ) totalRecord"); 
            selectSql = sb.toString();
        }else{            
            selectSql = Pattern.compile("^.*\\bfrom\\b", Pattern.CASE_INSENSITIVE)
            .matcher(selectSql).replaceFirst("select count(*) from");
        }
        
        long totalRecord = getSingleResultForLongBySQL(selectSql, params);
        // 设置总记录数
        pageView.setTotal(totalRecord);
        
        return pageView;
    }

    /* (non-Javadoc)
     * @see com.nenglong.base.dao.BaseQueryDao#getScrollDataBySQL(java.util.Map, java.lang.String, com.nenglong.base.pagination.PageForm, java.lang.String, java.lang.Object[])
     */
    @SuppressWarnings({ "rawtypes", "unchecked" })
    public PageView getScrollDataBySQL(final Map<String, Object> hints, final String totalSql, final F form, final String sql, final Object... params) {
        Query query = em.createNativeQuery(sql);
        setParameters(query, params);
        setHints(query, hints);
        
        PageView pageView= new PageView(form);
        
        if(pageView.getLimit()>0)
            query.setFirstResult(pageView.getStart()).setMaxResults(pageView.getLimit());
        
        pageView.setRows(query.getResultList());
        if(totalSql!=null){
            long totalRecord = getSingleResultForLongBySQL(totalSql, params);
            // 设置总记录数
            pageView.setTotal(totalRecord);
        }
        
        return pageView;
    }

    /* (non-Javadoc)
     * @see com.nenglong.base.dao.BaseQueryDao#getScrollDataBySQL(java.util.Map, com.nenglong.base.pagination.PageForm, java.lang.Class, java.lang.String, java.lang.Object[])
     */
    @SuppressWarnings("unchecked")
    public <E> PageView<E> getScrollDataBySQL(final Map<String, Object> hints, final F form, final Class<E> entityClass, final String sql, final Object... params) {
        String selectSql = sql;
        Query query = em.createNativeQuery(selectSql, entityClass);
        setParameters(query, params);
        setHints(query, hints);
        
        PageView<E> pageView= new PageView<E>(form);
        
        if(pageView.getLimit()>0)
            query.setFirstResult(pageView.getStart()).setMaxResults(pageView.getLimit());
        
        pageView.setRows(query.getResultList());
        
        //替换成查询总SQL语句
        Matcher matcher = Pattern.compile("(\\bfrom\\b)", Pattern.CASE_INSENSITIVE).matcher(selectSql);
        int count=0;
        while(matcher.find()){
            count++;
        }
        if(count >=2){
            //有子查询
            StringBuffer sb = new StringBuffer("select count(*) from ( ");
            sb.append(selectSql);
            sb.append(" ) totalRecord"); 
            selectSql = sb.toString();
        }else{            
            selectSql = Pattern.compile("^.*\\bfrom\\b", Pattern.CASE_INSENSITIVE)
            .matcher(selectSql).replaceFirst("select count(*) from");
        }
        
        long totalRecord = getSingleResultForLongBySQL(selectSql, params);
        // 设置总记录数
        pageView.setTotal(totalRecord);
        
        return pageView;
    }

    /* (non-Javadoc)
     * @see com.nenglong.base.dao.BaseQueryDao#getScrollDataBySQL(java.util.Map, java.lang.String, com.nenglong.base.pagination.PageForm, java.lang.Class, java.lang.String, java.lang.Object[])
     */
    @SuppressWarnings("unchecked")
    public <E> PageView<E> getScrollDataBySQL(final Map<String, Object> hints, final String totalSql, final F form, final Class<E> entityClass, final String sql, final Object... params) {
        Query query = em.createNativeQuery(sql, entityClass);
        setParameters(query, params);
        setHints(query, hints);
        
        PageView<E> pageView= new PageView<E>(form);
        
        if(pageView.getLimit()>0)
            query.setFirstResult(pageView.getStart()).setMaxResults(pageView.getLimit());
        
        pageView.setRows(query.getResultList());
        if(totalSql!=null){
            long totalRecord = getSingleResultForLongBySQL(totalSql, params);
            // 设置总记录数
            pageView.setTotal(totalRecord);
        }
        
        return pageView;
    }

    /* (non-Javadoc)
     * @see com.nenglong.sshtest.base.dao.BaseQueryDao#getCount()
     */
    public long getCount() {
        return getCount(entityClass);
    }

    /* (non-Javadoc)
     * @see com.nenglong.sshtest.base.dao.BaseQueryDao#getCount(java.lang.Class)
     */
    public long getCount(final Class<?> entityClass) {
        return getCount(entityClass, null, null);
    }
    
    /* (non-Javadoc)
     * @see com.nenglong.base.dao.BaseQueryDao#getCount(java.lang.String, java.lang.Object)
     */
    public long getCount(final String wherePropertyName, final Object whereValue) {
        return getCount(entityClass, wherePropertyName, whereValue);
    }
    
    /* (non-Javadoc)
     * @see com.nenglong.base.dao.BaseQueryDao#getCount(java.util.Map)
     */
    public long getCount(final Map<String,Object> whereProperties) {
        return getCount(entityClass, whereProperties);
    }
    
    /* (non-Javadoc)
     * @see com.nenglong.base.dao.BaseQueryDao#getCount(java.lang.Class, java.lang.String, java.lang.Object)
     */
    public long getCount(final Class<?> entityClass, final String wherePropertyName, final Object whereValue) {
        StringBuilder sb = new StringBuilder("select count(*) from ");
        sb.append(getEntityName(entityClass));
        List<Object> list = new LinkedList<Object>();
        if(StringUtils.isNotEmpty(wherePropertyName)){
            sb.append(" where ");
            sb.append(wherePropertyName);
            sb.append("=?");
            list.add(whereValue);
        }
        return getSingleResultForLongByJPQL(sb.toString(),list.toArray());
    }
    
    /* (non-Javadoc)
     * @see com.nenglong.base.dao.BaseQueryDao#getCount(java.lang.Class, java.util.Map)
     */
    public long getCount(final Class<?> entityClass, final Map<String,Object> whereProperties) {
        StringBuilder sb = new StringBuilder("select count(*) from ");
        sb.append(getEntityName(entityClass));
        List<Object> params = new LinkedList<Object>();
        if(whereProperties!=null && whereProperties.size()>0){
            sb.append(" where ");
            Set<Entry<String, Object>> set = whereProperties.entrySet();
            int i=0;
            for (Entry<String, Object> entry : set) {
                if(i>0)
                    sb.append(" and ");
                sb.append(entry.getKey());
                if(entry.getValue()==null){
                    sb.append(" is null");
                }else{
                    sb.append("=?");
                    params.add(entry.getValue());
                }
                i++;
            }
        }
        return getSingleResultForLongByJPQL(sb.toString(),params.toArray());
    }

    /* (non-Javadoc)
     * @see com.nenglong.sshtest.base.dao.BaseQueryDao#getMaxNum(java.lang.String)
     */
    public Long getMaxNum(final String propertyName) {
        return getMaxNum(entityClass, propertyName);
    }

    /* (non-Javadoc)
     * @see com.nenglong.sshtest.base.dao.BaseQueryDao#getMaxNum(java.lang.Class, java.lang.String)
     */
    public Long getMaxNum(final Class<?> entityClass, final String propertyName) {
        return getMaxNum(entityClass, propertyName, null, null);
    }

    /* (non-Javadoc)
     * @see com.nenglong.sshtest.base.dao.BaseQueryDao#getMaxNum(java.lang.String, java.lang.String, java.lang.Object)
     */
    public Long getMaxNum(final String propertyName, final String wherePropertyName, final Object whereValue) {
        return getMaxNum(entityClass, propertyName, wherePropertyName, whereValue);
    }
    
    /* (non-Javadoc)
     * @see com.nenglong.base.dao.BaseQueryDao#getMaxNum(java.lang.String, java.util.Map)
     */
    public Long getMaxNum(final String propertyName, final Map<String,Object> whereProperties) {
        return getMaxNum(entityClass, propertyName, whereProperties);
    }


    /* (non-Javadoc)
     * @see com.nenglong.sshtest.base.dao.BaseQueryDao#getMaxNum(java.lang.Class, java.lang.String, java.lang.String, java.lang.Object)
     */
    public Long getMaxNum(final Class<?> entityClass, final String propertyName, final String wherePropertyName, final Object whereValue) {
        StringBuilder sb = new StringBuilder();
        sb.append("select max(");
        sb.append(propertyName);
        sb.append(") from ");
        sb.append(getEntityName(entityClass));
        List<Object> list = new LinkedList<Object>();
        if(StringUtils.isNotEmpty(wherePropertyName)){
            sb.append(" where ");
            sb.append(wherePropertyName);
            if(whereValue==null){
                sb.append(" is null");
            }else{
                sb.append(" =?");
                list.add(whereValue);
            }
        }
        
        Long num = getSingleResultForLongByJPQL(sb.toString(),list.toArray());
        return num==null?0:num;
    }
    
    /* (non-Javadoc)
     * @see com.nenglong.base.dao.BaseQueryDao#getMaxNum(java.lang.Class, java.lang.String, java.util.Map)
     */
    public Long getMaxNum(final Class<?> entityClass, final String propertyName, final Map<String,Object> whereProperties) {
        StringBuilder sb = new StringBuilder();
        sb.append("select max(");
        sb.append(propertyName);
        sb.append(") from ");
        sb.append(getEntityName(entityClass));
        List<Object> params = new LinkedList<Object>();
        if(whereProperties!=null && whereProperties.size()>0){
            sb.append(" where ");
            Set<Entry<String, Object>> set = whereProperties.entrySet();
            int i=0;
            for (Entry<String, Object> entry : set) {
                if(i>0)
                    sb.append(" and ");
                sb.append(entry.getKey());
                if(entry.getValue()==null){
                    sb.append(" is null");
                }else{
                    sb.append("=?");
                    params.add(entry.getValue());
                }
                i++;
            }
        }
        
        Long num = getSingleResultForLongByJPQL(sb.toString(), params.toArray());
        return num==null?0:num;
    }
    
    /* (non-Javadoc)
     * @see com.nenglong.sshtest.base.dao.BaseQueryDao#getOrderBy(java.lang.Object, java.lang.String)
     */
    public Long getNextNum(final Object entity, final String propertyName) {
        return getNextNum(entity, propertyName, null);
    }
    
    /* (non-Javadoc)
     * @see com.nenglong.sshtest.base.dao.BaseQueryDao#getMaxNumAndAdd1(java.lang.Object, java.lang.String, java.lang.String)
     */
    public synchronized Long getNextNum(final Object entity, final String propertyName, final String parentPropertyName) {
        Class<?> entityClass = entity.getClass();
        String idName = getIdPropertyName(entityClass);
        try {
            Object id = PropertyUtils.getProperty(entity, idName);
            boolean isNotParent = StringUtils.isEmpty(parentPropertyName);
            Object newParentProperty = isNotParent? null : PropertyUtils.getProperty(entity, parentPropertyName);
            if(id==null){
                //保存方式,返回最大值+1
                Long num = getMaxNum(entityClass, propertyName, parentPropertyName, newParentProperty);
                return num==null?1:num.longValue()+1;
            }else{
                //修改方式
                Object oldBean = find(entityClass, (Serializable)id);
                Long property = objectToLong(PropertyUtils.getProperty(oldBean, propertyName));
                if(isNotParent){//如果没有父节点,则直接返回原排序值
                    return property;
                }else{//如果有父节点
                    boolean isNotUpdate = false;
                    Object oldParentProperty = PropertyUtils.getProperty(oldBean, parentPropertyName);
                    boolean oldParentPropertyIsNull = oldParentProperty==null;
                    boolean newParentPropertyIsNull = newParentProperty==null;
                    if(oldParentPropertyIsNull && newParentPropertyIsNull){
                        isNotUpdate = true;
                    }else {
                        Class<?> parentPropertyType = PropertyUtils.getPropertyType(entity, parentPropertyName);
                        if(parentPropertyType.getName().matches("^java.+$")){
                            //如果是基本类型可以直接比较
                            isNotUpdate = oldParentPropertyIsNull?newParentProperty.equals(oldParentProperty):oldParentProperty.equals(newParentProperty);
                        }else{
                            //如果是对象类型,要取出主键才能比较
                            String pIdName = getIdPropertyName(parentPropertyType);
                            Object oldParentId = oldParentPropertyIsNull?null:PropertyUtils.getProperty(oldParentProperty, pIdName);
                            Object newParentId = newParentPropertyIsNull?null:PropertyUtils.getProperty(newParentProperty, pIdName);
                            oldParentPropertyIsNull = oldParentId==null;
                            newParentPropertyIsNull = newParentId==null;
                            if(oldParentPropertyIsNull && newParentPropertyIsNull){
                                isNotUpdate = true;
                            }else{
                                isNotUpdate = oldParentPropertyIsNull?newParentId.equals(oldParentId):oldParentId.equals(newParentId);
                            }
                        }
                    }
                    
                    if(isNotUpdate){
                        //如果没有修改父节点,则直接返回原排序值
                        return property;
                    }else{
                        //如果有修改父节点,则按新父节点获取最大值+1
                        Object bean = org.apache.commons.beanutils.BeanUtils.cloneBean(entity);
                        PropertyUtils.setProperty(bean, idName, null);
                        return getNextNum(bean, propertyName, parentPropertyName);
                    }
                }
            }
        } catch (Exception e) {
            e.printStackTrace();
        }
        return Long.valueOf(1);
    }

    /* (non-Javadoc)
     * @see com.nenglong.sshtest.base.dao.BaseQueryDao#isExists(java.lang.String, java.lang.Object)
     */
    public boolean isExists(final String propertyName, final Object value) {
        return isExists(entityClass, propertyName, value);
    }

    /* (non-Javadoc)
     * @see com.nenglong.sshtest.base.dao.BaseQueryDao#isExists(java.lang.Class, java.lang.String, java.lang.Object)
     */
    public boolean isExists(final Class<?> entityClass, final String propertyName,final Object value) {
        return isExists(entityClass, propertyName, value, null, null);
    }

    /* (non-Javadoc)
     * @see com.nenglong.sshtest.base.dao.BaseQueryDao#isExists(java.lang.String, java.lang.Object, java.lang.String, java.lang.Object)
     */
    public boolean isExists(final String propertyName, final Object value, final String wherePropertyName, final Object whereValue) {
        return isExists(entityClass, propertyName, value, wherePropertyName, whereValue);
    }
    
    /* (non-Javadoc)
     * @see com.nenglong.base.dao.BaseQueryDao#isExists(java.util.Map)
     */
    public boolean isExists(final Map<String,Object> whereProperties) {
        return isExists(entityClass, whereProperties);
    }

    /* (non-Javadoc)
     * @see com.nenglong.sshtest.base.dao.BaseQueryDao#isExists(java.lang.Class, java.lang.String, java.lang.Object, java.lang.String, java.lang.Object)
     */
    public boolean isExists(final Class<?> entityClass, final String propertyName, final Object value, final String wherePropertyName, final Object whereValue) {
        StringBuilder sb = new StringBuilder("select count(*) from ");
        sb.append(getEntityName(entityClass));
        sb.append(" where ");
        sb.append(propertyName);
        sb.append("=?");
        List<Object> list = new LinkedList<Object>();
        if(value instanceof String)
            list.add(((String)value).trim());
        else
            list.add(value);
        if(StringUtils.isNotEmpty(wherePropertyName)){
            sb.append(" and ");
            sb.append(wherePropertyName);
            if(whereValue==null){
                sb.append(" is null");
            }else{
                sb.append(" =?");
                list.add(whereValue);
            }
        }
        
        long count = getSingleResultForLongByJPQL(sb.toString(), list.toArray());
        
        return count>=1;
    }
    
    /* (non-Javadoc)
     * @see com.nenglong.base.dao.BaseQueryDao#isExists(java.lang.Class, java.util.Map)
     */
    public boolean isExists(final Class<?> entityClass, final Map<String,Object> whereProperties) {
        StringBuilder sb = new StringBuilder("select count(*) from ");
        sb.append(getEntityName(entityClass));
        List<Object> params = new LinkedList<Object>();
        if(whereProperties!=null && whereProperties.size()>0){
            sb.append(" where ");
            Set<Entry<String, Object>> set = whereProperties.entrySet();
            int i=0;
            for (Entry<String, Object> entry : set) {
                if(i>0)
                    sb.append(" and ");
                sb.append(entry.getKey());
                if(entry.getValue()==null){
                    sb.append(" is null");
                }else{
                    sb.append("=?");
                    params.add(entry.getValue());
                }
                i++;
            }
        }
        
        long count = getSingleResultForLongByJPQL(sb.toString(), params.toArray());
        
        return count>=1;
    }
    
}


你可能感兴趣的:(二、通用Dao层之BaseQueryDao接口与BaseQueryDaoImpl类)