Data Business Logic In Java: jOOQ VS SPL

Maddy - Mar 6 '23 - - Dev Community

If you're a Java Engineer, you probably know about Hibernate, an open-source object relation mapping (ORM) that helps map an object domain to a relational database.

jOOQ generates Java code from your database and lets you build type safe SQL queries through its fluent API.[jooq.org]

What are the features of jOOQ?

Object-oriented

jOOQ is object-oriented.

It supports lambda expressions, flow control, etc.

High performance

jOOQ has excellent performance but lacks flexibility and computing power.

jOOQ creates the SQL statements after execution and sends them to the database to perform calculations and give back the result.

This process makes jOOQ poor in flexibility.

Type-safety

jOOQ uses the Java compiler to compile SQL syntax.

Code generation

jOOQ creates Java classes from the database metadata.

Easy library import

jOOQ allows you to import external libraries easily.

IDE and debugging

jOOQ has its graphical IDE and debugging support.

What are the disadvantages of jOOQ?

Steep learning curve

Before you consider learning jOOQ, you should be comfortable with SQL.

jOOQ is straightforward when used during development.

However, it becomes complex when translating from SQL to jOOQ.

Amount of code

Since jOOQ is about SQL, it requires importing several functions.

This translates into creating a large amount of code.

How does jOOQ compare to SPL?

  • Even though jOOQ supports some object-oriented features, it's inconvenient to use them. SPL, however, has a more elegant syntax.

  • SPL is an interpreted language. The performance is slower than jOOQ, but it has stronger computing power.

  • SPL has built-in data processing functions, allowing higher development efficiency and lower time complexity.

  • SPL has an IDE suitable for data processing.

  • SPL has a more relaxed learning curve since it aims to simplify Java or SQL code.

  • SPL is less verbose than jOOQ.

Related: SPL: A Faster and Easier Alternative to SQL

Examples

Here are some examples of jOOQ syntax compared to SPL:

Read data from the database

// jOOQ
java.sql.Connection conn = DriverManager.getConnection(url, userName, password);
DSLContext context = DSL.using(conn, SQLDialect.MYSQL);
Result<OrdersRecord> R1=context.select().from(ORDERS).fetchInto(ORDERS);

// SPL
=conn=connect("mysql8")
=conn.query("select * from Orders")
=conn.query("select SellerID,Client,Amount from Orders")

Enter fullscreen mode Exit fullscreen mode

Write data to the database

// jOOQ
r.setValue(ORDERS.AMOUNT,r.getValue(ORDERS.AMOUNT).doubleValue()+100);
r.update();

// SPL
conn.update(NT:T,orders)

Enter fullscreen mode Exit fullscreen mode

Access a field

// jOOQ
R1.get(0).getClient();
R1.get(0).get(ORDERS.CLIENT);

// SPL
T(1).Client
T(1).field(2)
T(1).field("Client")

Enter fullscreen mode Exit fullscreen mode

Grouping and aggregating

// jOOQ
context.select(ORDERS.CLIENT,year(ORDERS.ORDERDATE).as("y"),sum(ORDERS.AMOUNT).as("amt"),count(one()).as("cnt"))
.from(ORDERS)
.groupBy(ORDERS.CLIENT,year(ORDERS.ORDERDATE))
.having(field("amt").lessThan(20000)).fetch();

// SPL
Orders.groups(Client,year(OrderDate):y;sum(Amount):amt,count(1):cnt)
.select(amt<20000)

Enter fullscreen mode Exit fullscreen mode

Select the top 3 elements in each group

// jOOQ
WindowDefinition CA = name("CA").as(partitionBy(ORDERS.CLIENT).orderBy(ORDERS.AMOUNT));
context.select().from(select(ORDERS.ORDERID,ORDERS.CLIENT,ORDERS.SELLERID,ORDERS.AMOUNT,ORDERS.ORDERDATE,rowNumber().over(CA).as("rn")).from(ORDERS).window(CA) ).where(field("rn").lessOrEqual(3)).fetch();

// SPL
Orders.group(Client).(~.top(3;Amount)).conj()

Enter fullscreen mode Exit fullscreen mode

Calculate the maximum consecutive days that a stock keeps rising

// jOOQ
WindowDefinition woDay1 = name("woDay").as(orderBy(APPL.DAY));

Table<?>T0=table(select(APPL.DAY.as("DAY"),when(APPL.PRICE.greaterThan(lag(APPL.PRICE).over(woDay1)),0). otherwise(1).as("risingflag")).from(APPL).window(woDay1)).as("T0");

WindowDefinition woDay2 = name("woDay1").as(orderBy(T0.field("DAY")));

Table<?>T1=table(select(sum(T0.field("risingflag").cast(java.math.BigDecimal.class)).over(woDay2). as("norisingdays")).from(T0).window(woDay2)).as("T1");

Table<?>T2=table(select(count(one()).as("continuousdays")).from(T1).groupBy(T1.field("norisingdays"))).as("T2");

Result<?> result=context.select(max(T2.field("continuousdays"))).from(T2).fetch();

// SPL
APPL.sort(day).group@i(price<price[-1]).max(~.count())

Enter fullscreen mode Exit fullscreen mode

P.S: in this example, jOOQ needs to calculate the number of days where the stock doesn't increase first. Then, it marks each record with a flag (risingflag) in chronological order.

Calculate bonus according to rules

// jOOQ
Orders.forEach(r->{
     Double amount=r.getValue(ORDERS.AMOUNT);
     if (amount>10000) {
         r.setValue(ORDERS.BONUS), amount * 0.05);
     }else if(amount>=5000 && amount<10000){
         r.setValue(ORDERS.BONUS),amount*0.03);
     }else if(amount>=2000 && amount<5000){
         r.setValue(ORDERS.BONUS),amount*0.02);
     }
});

// SPL
Orders.(Bonus=if(Amount>10000,Amount*0.05,
     if(Amount>5000 && Amount<10000, Amount*0.03,
     if(Amount>=2000 && Amount<5000, Amount*0.02)
)))

Enter fullscreen mode Exit fullscreen mode

Key Takeaways

In this article, you learned about the following:

  • What jOOQ is.

  • The language features of jOOQ.

  • Some disadvantages of jOOQ.

  • jOOQ VS SPL.

  • How SPL syntax is simpler than jOOQ.

If you enjoyed this article, you'll definitely benefit from subscribing to my FREE weekly newsletter, where I talk about software engineering, career development, and more. I hope to see you there.

Until next time!

🙋🏾

Further Reading:

. . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
Terabox Video Player