TL;DR
Detail
At JJUG-CCC (Japan Java Users Group Cross Community Conference) in December 2018 Talking about O / R mapper and DB migration while comparing tools ) Was given the title.
Among the many O / R mappers and DB migration tools, jOOQ was recommended and Flyway was recommended. On the other hand, although it is a story that I hear from blogs and people on the street, it seems that there are many cases where they are used slightly incorrectly. ** What's particularly bad is that there are some cases where jOOQ automatically generated Java source code is versioned as a git commit target. You had better stop it. ** If multiple developers inadvertently add columns to the same table at the same time, a large amount of Java code automatically generated by jOOQ will always cause a conflict.
jOOQ reads the structure of the specified DB schema accurately and incomparably, and automatically generates Java code that makes O / R mapping easier. ** This means that it is the DB schema definition, that is, the so-called DDL statements such as CREATE TABLE and ALTER TABLE, that should be versioned accurately and unmatched. Flyway makes that possible. ** **
Since jOOQ automatically generates Java code, I want to specify the output destination under src / main / java, but that is the pitfall. If you are using gradle, you can compile by specifying the location of the source code after specifying the output destination of the automatically generated code of jOOQ under build /. There is no problem on IntelliJ IDEA. However, I don't know about the ancient weapon called Eclipse.
Just prepare a PC with git, JDK8 or above, docker and execute the following command.
git clone [email protected]:nabedge/jooq-flyway-spboot-sample.git
cd jooq-flyway-spboot-sample
sh setup.sh
sh ./gradlew run -p pj-web
Http in browser://localhost:Open 8080
Let's explain a little more from around.
jooq {
version = "${jooqVersion}"
edition = 'OSS' // if you use oracle, you should pay :-)
// the name "sample" -> task name "generateSampleJooqSchemaSource" . see below.
sample (sourceSets.main) {
jdbc {
driver = "${jdbcDriver}"
url = "${dbUrl}"
user = "${dbUser}"
password = "${dbPassword}"
}
generator {
target {
packageName = "${jooqDestPackage}"
directory = "${jooqDestDir}"
}
strategy {
name = 'com.example.db.jooq.generator.SamplePrefixGeneratorStrategy'
}
database() {
name = 'org.jooq.meta.postgres.PostgresDatabase'
inputSchema = "public"
}
generate() {
daos = true
immutablePojos = true
pojosEqualsAndHashCode = true
}
}
}
}
compileJava {
dependsOn generateSampleJooqSchemaSource
sourceSets.main.java.srcDirs(jooqDestDir)
}
As I mentioned in Around 50 pages of actual O / R mapper and DB migration talked while comparing tools, jOOQ is the table name by default. Will create a Java class with exactly the same name as. ** Custom is highly recommended. ** Class name conflicts can lead to considerable stress during the coding process.
So this part of build.gradle above
strategy {
name = 'com.example.db.jooq.generator.SamplePrefixGeneratorStrategy'
}
Becomes important. This class is the only class in the subproject called pj-db-custom-strategy It is implemented as /src/main/java/com/example/db/jooq/generator/SamplePrefixGeneratorStrategy.java).
import org.jooq.codegen.DefaultGeneratorStrategy;
import org.jooq.meta.Definition;
public class SamplePrefixGeneratorStrategy extends DefaultGeneratorStrategy {
@Override
public String getJavaClassName(final Definition definition, final Mode mode) {
String name = super.getJavaClassName(definition, mode);
switch (mode) {
case POJO:
return name + "Vo";
case DEFAULT:
return 'J' + name;
}
return name;
}
As you can see, all the Java class prefixes automatically generated by jOOQ have "J". This will give you the actual DB access code (https://github.com/nabedge/jooq-flyway-spboot-sample/blob/master/pj-web/src/main/java/com/example/web/ In BookRepository.java)
final JBook jBook = JBook.BOOK;
final List<BookVo> selected = dslContext
.select(
jBook.ISBN,
jBook.TITLE,
jBook.PUBLISH_DATE
)
.from(jBook)
.orderBy(jBook.PUBLISH_DATE)
.fetchInto(BookVo.class);
// .fetchInto(Book.class); // or you can use original class directly !
return selected
.stream()
.map(bookVo -> {
Book book = new Book();
book.setIsbn(bookVo.getIsbn());
book.setTitle(bookVo.getTitle());
book.setPublishDate(bookVo.getPublishDate().toLocalDate());
return book;
})
.collect(Collectors.toList());
in this way,
You will be able to avoid these name conflicts.
If you move the sample while reading each and import it into the IDE, you can see the point. Happy Hacking !
This article is reprinted by the author himself from his own blog. -> https://nabedge.mixer2.org/2019/03/jooq-flyway-sample.html
Recommended Posts