最近使用mysql做一个交易网站,使用hibernate作为持久化框架。
当我使用hibernate的Order进行排序的时候,杯具发生了。中文给我乱排了。
mysql中如果需要正常按照中文排序,其中一种处理方法是
SELECT * FROM BZ_COMPANY ORDER BY CONVERT( COMPANY_NAME USING GBK ) ASC
可问题是这样就脱离hibernate了。本打算使用QBC做一些公共的方法的。
然后就去看了下hibernate中Order的实现。
hibernate的Order:
//$Id: Order.java,v 1.1 2011/05/29 18:11:15 Surui Exp $ package org.hibernate.criterion; import java.io.Serializable; import java.sql.Types; import org.hibernate.Criteria; import org.hibernate.HibernateException; import org.hibernate.engine.SessionFactoryImplementor; import org.hibernate.type.Type; /** * Represents an order imposed upon a <tt>Criteria</tt> result set * @author Gavin King */ public class Order implements Serializable { private boolean ascending; private boolean ignoreCase; private String propertyName; public String toString() { return propertyName + ' ' + (ascending?"asc":"desc"); } public Order ignoreCase() { ignoreCase = true; return this; } /** * Constructor for Order. */ protected Order(String propertyName, boolean ascending) { this.propertyName = propertyName; this.ascending = ascending; } /** * Render the SQL fragment * */ public String toSqlString(Criteria criteria, CriteriaQuery criteriaQuery) throws HibernateException { String[] columns = criteriaQuery.getColumnsUsingProjection(criteria, propertyName); Type type = criteriaQuery.getTypeUsingProjection(criteria, propertyName); StringBuffer fragment = new StringBuffer(); for ( int i=0; i<columns.length; i++ ) { SessionFactoryImplementor factory = criteriaQuery.getFactory(); boolean lower = ignoreCase && type.sqlTypes( factory )[i]==Types.VARCHAR; if (lower) { fragment.append( factory.getDialect().getLowercaseFunction() ) .append('('); } fragment.append( columns[i] ); if (lower) fragment.append(')'); fragment.append( ascending ? " asc" : " desc" ); if ( i<columns.length-1 ) fragment.append(", "); } return fragment.toString(); } /** * Ascending order * * @param propertyName * @return Order */ public static Order asc(String propertyName) { return new Order(propertyName, true); } /** * Descending order * * @param propertyName * @return Order */ public static Order desc(String propertyName) { return new Order(propertyName, false); } }
重点就在toSqlString上了,QBC的Criteria也是toSqlString产生对应sql的,所以只要在这里做手脚,就能达到效果。
当然,不赞成直接改源码。
然后就有了GBKOrder:
package comm; import java.sql.Types; import org.hibernate.Criteria; import org.hibernate.HibernateException; import org.hibernate.criterion.CriteriaQuery; import org.hibernate.criterion.Order; import org.hibernate.engine.SessionFactoryImplementor; import org.hibernate.type.Type; public class GBKOrder extends Order { private String encoding = "GBK"; private boolean ascending; private boolean ignoreCase; private String propertyName; @Override public String toString() { return "CONVERT( " + propertyName + " USING " + encoding + " ) " + (ascending ? "asc" : "desc"); } @Override public Order ignoreCase() { ignoreCase = true; return this; } /** * Constructor for Order. */ protected GBKOrder(String propertyName, boolean ascending) { super(propertyName, ascending); this.propertyName = propertyName; this.ascending = ascending; } /** * Constructor for Order. */ protected GBKOrder(String propertyName, String dir) { super(propertyName, dir.equalsIgnoreCase("ASC") ? true : false); ascending = dir.equalsIgnoreCase("ASC") ? true : false; this.propertyName = propertyName; this.ascending = ascending; } /** * Render the SQL fragment * */ @Override public String toSqlString(Criteria criteria, CriteriaQuery criteriaQuery) throws HibernateException { String[] columns = criteriaQuery.getColumnsUsingProjection(criteria, propertyName); Type type = criteriaQuery.getTypeUsingProjection(criteria, propertyName); StringBuffer fragment = new StringBuffer(); for (int i = 0; i < columns.length; i++) { SessionFactoryImplementor factory = criteriaQuery.getFactory(); boolean lower = ignoreCase && type.sqlTypes(factory)[i] == Types.VARCHAR; if (lower) { fragment.append(factory.getDialect().getLowercaseFunction()).append('('); } fragment.append("CONVERT( " + columns[i] + " USING " + encoding + " )"); if (lower) fragment.append(')'); fragment.append(ascending ? " asc" : " desc"); if (i < columns.length - 1) fragment.append(", "); } return fragment.toString(); } /** * Ascending order * * @param propertyName * @return Order */ public static Order asc(String propertyName) { return new GBKOrder(propertyName, true); } /** * Descending order * * @param propertyName * @return Order */ public static Order desc(String propertyName) { return new GBKOrder(propertyName, false); } }
使用例子:
public PageControl findPage(final PageControl pageControl, final Object bean) { try { final Class clazz = bean.getClass(); List data = (List) this.getHibernateTemplate().execute(new HibernateCallback() { public Object doInHibernate(Session session) throws HibernateException, SQLException { Criteria criteria = session.createCriteria(clazz); criteria.add(Example.create(bean) .ignoreCase() .enableLike(MatchMode.ANYWHERE)); if (pageControl != null) { int start = pageControl.getStart(); int limit = pageControl.getLimit(); criteria.setFirstResult(start); criteria.setMaxResults(limit); String sort = pageControl.getSort(); String dir = pageControl.getDir(); if (sort != null && dir != null) { criteria.addOrder(dir.equalsIgnoreCase("ASC") ? GBKOrder.asc(sort) : GBKOrder.desc(sort)); } } return criteria.list(); } }); Long totalCount = getTotalCount(bean); PageControl rt = new PageControl(); rt.setData(data); rt.setTotalCount(totalCount); return rt; } catch (RuntimeException e) { log.error("find page failed", e); throw e; } }
当然,你有需要的话,不必写死GBK
附上效果图:
http://www.surui.cc/archives/78
相关推荐
在Java企业级开发中,Hibernate是一个非常重要的对象关系映射(ORM)框架,它极大地简化了数据库操作。本文将深入探讨在使用Hibernate进行MySQL查询时的一些关键知识点,以帮助开发者更好地理解和应用这些技术。 ...
本系统利用Java技术栈中的Struts、Hibernate和MySQL三大组件进行构建,实现了用户登录注册、邮件管理、联系人等功能,为用户提供了一个高效、便捷的内部通信环境。 Struts作为MVC(模型-视图-控制器)框架,负责...
在本网上书城系统中,Hibernate用于管理数据库交互,将Java对象(如书籍、订单等)与MySQL数据库中的表格对应起来。通过Hibernate,开发者可以避免编写大量的SQL语句,提高开发效率,并实现数据持久化的灵活管理和...
### jsp源码网上书城系统(Struts+Hibernate+Mysql)知识点解析 #### 一、项目概述 该项目是一款基于JSP技术栈构建的网上书城系统,主要采用Struts框架进行前端展示与控制,利用Hibernate作为持久层框架实现数据访问...
在本项目中,MySQL作为存储数据的主要平台,与Hibernate4配合,提供数据持久化支持。 **项目结构与示例** 项目中的14个示例涵盖了从基础到进阶的多个方面,可能包括: 1. Hello World示例,展示SpringMVC的基本...
JPA 使用 Hibernate 作为实现方式JPA + Hibernate + MySQL in Spring Boot注意此项目使用spring-boot 1.4.0版本,不适用于spring-boot 2.0 版本;2.0版本的项目配置可参考:本项目使用IDEA构建,直接导入IDEA即可...
1,这个项目是strut2.0 + hibernate3.0 + jquery.datatables+mysql 5.0实现的 hibernate分页(无排序,搜索,仅仅分页显示),服务器端分页在datatables上展现,有关 datatables的知识请关注它的官网...
4. **Query与Criteria API**:介绍如何使用HQL(Hibernate Query Language)和Criteria API进行复杂的数据查询,包括条件、排序、分组和连接等。 5. **Caching**:探讨了Hibernate的缓存机制,包括第一级缓存...
3.1.x版本中,Hibernate已经包含了对主流数据库的方言支持,如MySQL、Oracle、PostgreSQL等,使得代码更具移植性。 八、性能优化 在3.1.x版本中,Hibernate对性能进行了多方面的优化,包括延迟加载(Lazy Loading)...
在Hibernate中,你需要这个驱动来建立与MySQL数据库的连接,以便进行数据交互。 3. **javassist-3.12.0.GA.jar**: Javassist是一个开源的分析、转换和生成Java字节码的类库。Hibernate使用它在运行时动态地修改类和...
Java S2SH框架是Java Web开发中常用的一种技术栈,由Struts2、Hibernate4和Spring3三个组件组成。这三个组件分别负责不同的职责,共同构建了一个功能强大的MVC(Model-View-Controller)架构的网上订餐管理系统。 1...
总之,Hibernate 5.4.25为Java开发者提供了强大的数据持久化解决方案,通过合理的jar包配置和应用,可以极大地提升开发效率,降低项目维护成本。在理解和掌握其核心特性的基础上,灵活运用到实际项目中,将有助于...
好友:可以在指定的日记分类中添加并维护自己的日记 普通用户:可以评论任何可见分类下的日记并维护自己的评论 游客:可以浏览任何可见分类下的所有日记和评论信息 所有人拥有一般使用的权限,例如查看用户资料,...
例如,如果你使用的是MySQL,你可以设置为`org.hibernate.dialect.MySQL5Dialect`。 2. **hibernate.show_sql**:如果设置为`true`,Hibernate将在控制台上打印出执行的所有SQL语句,这对于调试非常有用。 3. **...
- **描述**:强制 Hibernate 按照被更新数据的主键为 SQL 更新排序,以减少高并发系统中事务的死锁。 - **取值**:`true` 或 `false`。 - **示例**:`hibernate.order_updates=true` ##### 11. 统计数据生成 ...
**取值**:支持各种数据库方言的全限定类名,例如`org.hibernate.dialect.MySQL5Dialect`。 ##### 2. `hibernate.show_sql` **用途**:启用或禁用在控制台上显示执行的SQL语句。对于开发阶段来说,这是一个非常...
通过 PostMan 等 RestClient 将待排序的多个数值发给 RestServer,RestServer 对这些数值进行排序,将排序前和排序后的数值存入数据库(可以是MySQL/H2等),并将排序结果返回给 RestClient。如果对 SpringBoot/...
Hibernate 支持多种数据库,如MySQL、Oracle、PostgreSQL等,并提供了丰富的API和工具。 2. **配置Hibernate** 在使用Hibernate之前,你需要在项目中配置Hibernate。这通常包括创建`hibernate.cfg.xml`配置文件,...
在这个实例中,Hibernate 可能用于将Java对象映射到MySQL数据库表,简化数据库操作。 4. **jQuery**:jQuery 是一个轻量级的JavaScript库,简化了DOM操作、事件处理、动画效果和Ajax交互。在Web前端,jQuery 可能...