大概是这样的,在优化报表的时候,系统有一个需求,想用jdbc代替hibernate,但是这个系统里有些代码是hibernate来做的,或者说在我需要优化的地方,有很多HQL的代码,我现在想把这个HQL转换成SQL。
1. hibernate2 的简单优化方案:QueryTranslator translator = new QueryTranslator(hqlStr); 
translator.compile((SessionFactoryImplementor)db.getDBSession().getSessionFactory(), Collections.EMPTY_MAP, false);
String newString =translator.getSQLString();
后来发现不行,因为hqlStr里面的内容是
select Employee from Employee in class com.technodex.evodex.apps.bo.Employee  where Employee.deleted = 0 and Employee.companyId in ('MYDIN')无法转换,但是要是把hql的内容改成select from Employee是可以转换的,我估计是这个translator的分析功能有限。
我就换成了hibernate3 的AST 优化,请看方案22. Hibernate3的AST 语句分析方案
HqlParser  parser =HqlParser.getInstance(hqlStr);
AST ast =parser.getAST();
SessionFactoryImplementor sf = (SessionFactoryImplementor)(db.getDBSession().getSessionFactory());
String newString =generate(ast, sf);-----
private String generate(AST sqlAst,SessionFactoryImplementor factory) throws QueryException, RecognitionException 
    { 
        System.out.println("************generate begin"); 
   
            SqlGenerator gen = new SqlGenerator(factory); 
            gen.statement(sqlAst); 
            System.out.println("--generate1"); 
            System.out.println(gen.getSQL()); 
            System.out.println("--generate2"); 
            String sql = gen.getSQL(); 
            return sql;
      } //发现始终无法打印出我想要的SQL 结果。
3. 在google和百度上搜索了半天 只找到了一点
HqlSqlWalker w = new HqlSqlWalker(QueryTranslatroImpl,sessionFactory,HqlParser,Map,CollectionRole);//不知道怎么设置这些参数
AST hqlAst = parser.getAST();
w.statement( hqlAst );
第三个方案,因为不知道构造参数,所以始终无法获得HqlSqlWalker所以上来求救,问题: 1. 如何构造一个HqlSqlWalker 对象, 2.假如没有的话,是否还有其他方案?

解决方案 »

  1.   

    现在 就是要解决这个问题,AST 这个就是为了解决这个问题
    我现在就是不知道如何构建一个sqlAST对象。
      

  2.   

    http://cownew.blog.51cto.com/413531/87199
      

  3.   


    二、让我们从QueryTranslatorImpl开始分析,当调用session.find('...')的时候将会调用QueryTranslatorImpl的compile方法来解析hql语句为sql语句。compile则主要是调用的doCompile方法。
    // PHASE 1 : Parse the HQL into an AST.
    HqlParser parser = parse( true );
    // PHASE 2 : Analyze the HQL AST, and produce an SQL AST.
    HqlSqlWalker w = analyze( parser, collectionRole );
    sqlAst = ( Statement ) w.getAST();
    generate( ( QueryNode ) sqlAst );
    queryLoader = new QueryLoader( this, factory, w.getSelectClause() );
    parse的主要代码:
    private HqlParser parse(boolean filter)
     HqlParser parser = HqlParser.getInstance( hql );
     parser.statement();
     AST hqlAst = parser.getAST();
      return parser;
    }
    analyze的主要代码:
    private HqlSqlWalker analyze(HqlParser parser, String collectionRole) throws QueryException, RecognitionException {
     HqlSqlWalker w = new HqlSqlWalker( this, factory, parser, tokenReplacements, collectionRole );
     AST hqlAst = parser.getAST();
     w.statement( hqlAst );
     return w;
    }
    generate的主要代码:
    private void generate(AST sqlAst) throws QueryException, RecognitionException {
     SqlGenerator gen = new SqlGenerator(factory);
     gen.statement( sqlAst );
     sql = gen.getSQL();
    }
      楼主找的还是不够细心啊。。
        这个代码是上面连接的部分
         资源来自Google关键字HqlSqlWalker第9个
      

  4.   

    hib能做到的纯sql做起来应该一样的。
      

  5.   

    不会,我觉得还不如自已针对hql写个sql...
      

  6.   

    直接写sql还要好些, 你这样转来转去影响性能