jOOQ-简短指南

您可以使用本指南来了解什么是jOOQ,如何快速入门,以及jOOQ如何与Spring和Hibernate之类的库进行集成或比较。

什么是jOOQ?

jOOQ是一个流行的Java数据库库,它使您可以用Java编写类型安全的SQL查询。 它是如何工作的?

  1. 您可以使用jOOQ的代码生成器连接到数据库并生成为数据库表和列建模的Java类。

  2. 与使用普通JDBC编写SQL String语句不同,您将使用这些生成的Java类编写SQL查询。

  3. jOOQ可以方便地将这些Java类和查询转换为真实的SQL,对数据库执行它们并将结果映射回Java代码。

当然,这只是非常高级的概述。 如果您想更详细地了解jOOQ的工作原理,请继续阅读。

jOOQ:速成课程

首先:您的数据库,然后:您的Java类

与其他流行的库(例如Hibernate)相比,jOOQ采用数据库优先或以SQL为中心的方法。

使用Hibernate,通常首先要开始编写Java类,然后再让Hibernate或类似Liquibase或Flyway的工具生成相应的数据库表。

使用jOOQ,您可以从数据库开始。 您的数据库和表必须已经存在,然后使用jOOQ的代码生成器为您生成Java类。

使用jOOQ的代码生成器

您可以通过三种方式使用jOOQ的代码生成器:

  1. 独立版本:您需要从其网站下载 jOOQ。

  2. Maven和jOOQ:您可以使用jOOQ的Maven插件生成代码。

  3. Gradle和jOOQ:您可以使用jOOQ的Gradle插件生成代码。

这三个选项的生成过程始终相同。 在独立情况下,您需要手动触发生成,而使用Maven和Gradle插件将在生成过程中自动进行代码生成。

无论如何,您都需要jOOQ的代码生成器的配置文件,默认情况下,该文件名为library.xml。 看起来像这样:

    <?xml version="1.0" encoding="UTF-8" standalone="yes"?>
    <configuration xmlns= "http://www.jooq.org/xsd/jooq-codegen-3.12.0.xsd" >

      <jdbc>  
        <driver> com.mysql.cj.jdbc.Driver </driver>
        <url> jdbc:mysql://localhost:3306/library </url>
        <user> root </user>
        <password></password>
      </jdbc>

      <generator>
        <database>  
            <!-- database specific options: What tables to schema/tables to include or exclujde ? What type of database? etc-->
            <includes> .* </includes>
        </database>

        <target> 
          <!-- The destination package of your generated classes (within the destination directory) -->
          <packageName> my.startup </packageName>

          <!-- The destination directory of your generated classes. Using Maven directory layout here -->
          <directory> c:/dev/myproject/src/main/java </directory>
        </target>
      </generator>
    </configuration>

如您所见,library.xml配置文件大致可归结为:

  • 您的数据库网址,用户名和密码。

  • 选项,如模式生成中要包括/排除的表。

  • 将生成的类放在哪里。

例:

假设您的数据库有一个USERS表 。 使用生成器配置运行代码生成器将创建(除其他外)两个类:

  • 一个my.startup.Users类 ,代表您的Users 数据库表

  • 一个my.startup.UsersRecord类,代表您的Users表一行

jOOQ代码生成器

让我们看看如何使用这些生成的类执行SQL查询:

jOOQ的DSL

jOOQ有两个类,DSL和DSLContext(特定于域的语言),开发人员需要使用它们来开始编写SQL查询。 您还可以将这些DSL类称为SQL Builder类,因为它们使您可以构建SQL查询。

由于jOOQ只是JDBC的包装,因此Java数据库基础适用,并且您需要获得数据库连接才能使jOOQ正常工作。 您要么自己打开一个,要么要求连接池给您一个。

让我们看一下使用Java的DriverManager的jOOQ DSL示例。

    import static my . startup . Tables .*;

    public class Main {
        public static void main ( String [] args ) {
            String userName = "root" ;
            String password = "" ;
            String url = "jdbc:mysql://localhost:3306/myhotstartup" ;

            try ( Connection conn = DriverManager . getConnection ( url , userName , password )) {  

                 DSLContext create = DSL . using ( conn , SQLDialect . MYSQL );  

                 Result < Record > result = create . select (). from ( USERS ). fetch (); 

                for ( Record r : result ) {   
                    Integer id = r . getValue ( USERS . ID );
                    String username = r . getValue ( USERS . USERNAME );
                    String email = r . getValue ( USERS . EMAIL );

                    System . out . println ( "ID: " + id + " + email: " + email );
                }

            }
            catch ( Exception e ) {
                e . printStackTrace ();
            }
        }
    }

这里发生了什么事?

  • 您可以使用纯JDBC打开数据库连接。 这是标准的Java。

  • 您创建了jOOQ的DSLContext,可以对数据库执行查询。

  • 您可以使用jOOQ 从USERS执行一个简单的select * ,然后遍历结果行/记录,打印出用户ID和电子邮件。

而已。

jOOQ和CRUD查询

本简短指南无法为您提供每种可能的jOOQ查询的全面解释,因此让我们看一些简单的常见查询以获得基本的了解。

请记住,jOOQ查询的读取几乎与相应的SQL查询完全一样,因此,如果没有强大的SQL技能,您会遇到问题。

SQL选择在哪里

要从id =:id的USERS中执行一个简单的选择*,您将执行以下查询:

    UsersRecord record = dslContext . selectFrom ( USERS )
                    . where ( USERS . ID . eq ( id ))
                    . fetchAny ();
    // do something with record.getEmail()

仅需很小的更改,您就可以将查询转换为select * from USERS,其中id在(:ids)中

    Result < UsersRecord > userRecords  = dslContext . selectFrom ( USERS )
                    . where ( USERS . ID . in ( ids ))
                    . fetch ();
    // (for-loop over userRecords)

SQL联接

让我们看一下如何联接两个表,例如: 从用户中选择* u对u.id = p.user_id的内部联接PAYMENTS p

    Result <?> result = dslContext . select ()
                             . from ( USERS . join ( PAYMENTS )
                                         . on ( PAYMENTS . USER_ID . eq ( USERS . ID )))
                             . fetch ();
    // (for-loop over join records)

SQL更新和删除

最后,删除( 从id = 1的USERS中删除 )或更新( 更新user设置 id = 1的 email =:email,username =:username的user = )看起来像这样:

    dslContext . delete ( USERS )
          . where ( USERS . ID . eq ( 1 ))
          . execute ();

    dslContext . update ( USERS )
          . set ( USERS . USERNAME , "John Rambo" )
          . set ( USERS . EMAIL , "john@rambo.com" )
          . where ( USERS . ID . eq ( 1 ))
          . execute ();

摘要

现在您可能已经了解了为什么jOOQ会自己调用类型安全数据库库。 它使您可以编写类似于SQL的Java代码。 利用您生成的DSL的好处,例如,用户ID必须是数字,用户名必须是字符串等。

推荐:练习jOOQ

如果您想获得上述各个步骤的详细说明
试试这个由jOOQ的创作者Lukas Eder推荐的jOOQ视频课程

它从jOOQ的基础知识开始,涵盖了查询,记录和dao的更多细节,最终使您不得不构建一个很小的真实的Spring Boot / jOOQ项目。

jOOQ如何与Spring集成?

没有什么可以阻止您将jOOQ与Spring结合使用。 但是,jOOQ与庞大的Spring生态系统之间存在各种集成级别。

@交易集成

在Spring应用程序中,通常使用@Transactional批注定义数据库事务边界。 为了使jOOQ参与这些交易,您需要做一些额外的设置工作

Spring Boot集成

Spring Boot带有jOOQ自动配置功能,这意味着它可以为您设置DSLContext并将jOOQ与Spring的事务处理集成在一起-您无需为Spring Boot项目添加以下依赖项就可以做任何事情。

    <dependency>
        <groupId> org.springframework.boot </groupId>
        <artifactId> spring-boot-starter-jooq </artifactId>
        <version> 2.2.2.RELEASE </version> <!-- or your appropriate Spring boot version -->
    </dependency>

然后,您可以执行以下操作:

    import static my . startup . Tables .*;

    @Service
    public class UserService {

        @Autowired
        private DSLContext content ; 

        @Transactional 
        public void registerUser ( String email ) {
            UsersRecord existingRecord = dslContext . selectFrom ( USERS )
                    . where ( USERS . EMAIL . eq ( email ))
                    . fetchAny ();
            if ( existingRecord != null ) {
                return false ;
            }

            // register user etc.
        }
    }
  • Spring Boot为您自动创建DSLContext(取决于数据源)。

  • jOOQ将参与@Transactional界定的Spring交易。

Spring数据

当前没有用于jOOQ的本地Spring Data项目,例如Spring Data JDBCSpring Data JPA 。 抱歉。

jOOQ与其他Java数据库框架相比如何?

jOOQ vs休眠

正如本指南开头已经提到的,两者完全不同。 Hibernate采用Java优先的方法,而您(通常)通常首先编写Java类和映射。 然后,您考虑数据库(表)。

另一方面,jOOQ首先是数据库或SQL,它需要一个现有的数据库架构来进行操作并从中生成其Java类。

但是,没有什么可以阻止您在同一项目中使用这两个库 。 有关如何执行此操作的快速介绍,请参阅Thorben Janssen的精彩文章

jOOQ vs MyBatis

MyBatis是一种SQL模板语言,您可以在其中以XML文件形式编写SQL。 有关两者之间差异的更多信息,请查看此stackoverflow线程

MyBatis XML文件如下所示:

    <?xml version="1.0" encoding="UTF-8" ?>
    <!DOCTYPE mapper PUBLIC "-//mybatis.org//DTD Mapper 3.0//EN" "http://mybatis.org/dtd/mybatis-3-mapper.dtd">

    <mapper namespace= "org.mybatis.example.UserMapper" >
      <select id= "selectUser" resultType= "User" >
        select * from Users where id = #{id}
      </select>
    </mapper>

这使您可以执行此操作:

    // sqlsessionfactory is a myBatis specific entry point
    try ( SqlSession session = sqlSessionFactory . openSession ()) {
        UserMapper mapper = session . getMapper ( UserMapper . class );
        User user = mapper . selectUser ( 1 );
    }

jOOQ与QueryDSL

jOOQ和QueryDSL的功能存在一定的重叠,并且QueryDSL也可以与生成的类一起使用。 上面的示例与QueryDSL相似:

     // 'Q' classes are generated and let you access tables, columns etc
    QUser user = QUser . user ;
    User john = queryFactory . selectFrom ( user )
      . where ( user . id . eq ( 1 ))
      . fetchOne ();

综上所述,在基于JPA(Lucene / Mongodb / JDO)的环境中,QueryDSL通常是一个不错的选择,在基于SQL的环境中,jOOQ是更好的选择。

但是请注意,QueryDSL停滞了一段时间,目前正在进行项目接管。

也可以看一下这篇比较两篇文章的(较旧的)文章: QueryDSL与jOOQ

本指南只是快速的速成班,介绍jOOQ可以为您和您的项目做些什么以及如何与其他选择进行比较。 有关更多信息,请查看jOOQ课程官方的jOOQ文档

如果您有任何意见或反馈,只需在下面留言。

谢谢阅读。

还有更多来自哪里

本文最初出现在https://www.marcobehler.com/guides/jooq上 ,是有关现代Java编程的一系列指南的一部分。 要查找更多指南,请访问网站或订阅新闻通讯以获取有关新发布的指南的通知: https : //bit.ly/2K0Ao4F

From: https://dev.to/marcobehler/jooq-a-short-guide-542e

  • 0
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值