Java Hibernate:从part解析/转换HQL以获取pairs类别名、类名
有谁能告诉我,我如何解析/计算HQL并获得映射,其中键是表别名和value-full限定类名 例如,对于HQL 从Foo a内部连接a.test b中选择a.id 我希望有两对: a、 包装1.Foo b。package2.TestClassName 对于结果集来说,这相对容易做到Java Hibernate:从part解析/转换HQL以获取pairs类别名、类名,java,hibernate,hql,Java,Hibernate,Hql,有谁能告诉我,我如何解析/计算HQL并获得映射,其中键是表别名和value-full限定类名 例如,对于HQL 从Foo a内部连接a.test b中选择a.id 我希望有两对: a、 包装1.Foo b。package2.TestClassName 对于结果集来说,这相对容易做到 请参阅。这不是一个很好的方法,但您似乎可以通过一些内部接口获得AST并遍历以下内容: QueryTranslator[] translators = hqlPlan.getTranslators(); AST ast
请参阅。这不是一个很好的方法,但您似乎可以通过一些内部接口获得AST并遍历以下内容:
QueryTranslator[] translators = hqlPlan.getTranslators();
AST ast = (AST)((QueryTranslatorImpl)translators[0]).getSqlAST();
new NodeTraverser(new NodeTraverser.VisitationStrategy() {
public void visit(AST node) {
if(node.getType() == SqlTokenTypes.FROM_FRAGMENT || node.getType() == SqlTokenTypes.JOIN_FRAGMENT) {
FromElement id = (FromElement)node;
System.out.println(node+": "+id.getClassAlias()+" - "+id.getClassName());
}
}
}).traverseDepthFirst(ast);
因此,这似乎可以从已编译的查询中检索别名映射,但我会非常小心地使用此解决方案:它将对象类型化为hibernate客户端通常不可见的子类,并根据猜测不同节点的语义来解释AST。这可能不适用于所有HQL语句,也可能不适用于将来的hibernate版本,或者具有不同的行为。我为我的问题找到了正确的解决方案。你最初的帖子几乎是正确的,除了那部分:
if(node.getType() == SqlTokenTypes.FROM_FRAGMENT || node.getType() == SqlTokenTypes.JOIN_FRAGMENT) {
FromElement id = (FromElement)node;
System.out.println(node+": "+id.getClassAlias()+" - "+id.getClassName());
}
请更正您的答案,我接受。我根据我们的内部API(标准窗格等)动态生成HQL,并针对过滤条件(即,其中的部分)需要知道HQL中每个类的别名。看起来像SqlTokenTypes。alias_REF不是我要找的。在我的示例中,上面的结果将是“a,package1.Foo”,但我还需要“b,package2.TestClassName”。我的意思是ALIAS_REF过程“选择”部分而不是“从”。关于您使用标准API的问题。我有两个理由:1。遗留代码2。HQL允许您构造所谓的报告查询(精确地提取您需要的数据,而不是构造整个对象)。请参阅链接了解详细信息哦,我不知道报告问题,这非常令人费解。Hibernate的全部要点当然是将数据从表映射到对象,但对于某些应用程序来说,表更适合,而报表查询似乎正好适合这一点。我需要对我们报告模块的控制器进行HQL的反向工程。
if(node.getType() == SqlTokenTypes.FROM_FRAGMENT || node.getType() == SqlTokenTypes.JOIN_FRAGMENT) {
FromElement id = (FromElement)node;
System.out.println(node+": "+id.getClassAlias()+" - "+id.getClassName());
}