-
Notifications
You must be signed in to change notification settings - Fork 0
Database
Groundbreaking edited this page Jan 30, 2026
·
1 revision
A modern, type-safe database wrapper for Java with step builder pattern and prepared queries support.
Features:
- ✅ Step Builder Pattern - Compile-time safety prevents invalid query construction
- ✅ Prepared Queries - Build once, execute many times (3-5x performance boost)
- ✅ Auto-managed Connections - Implements AutoCloseable for resource safety
- ✅ HikariCP Support - Optional connection pooling for production environments
- ✅ Multiple Databases - SQLite, MySQL, MariaDB, PostgreSQL, H2
- ✅ Fluent API - Clean, readable query construction
// SQLite (no connection pooling)
Database db = Database.sqlite("app.db");
// MySQL with HikariCP
Database db = Database.builder()
.jdbcUrl(DatabaseUtils.mysql("localhost", "mydb"))
.credentials("user", "password")
.poolSize(4, 16)
.usePooling()
.build();// SELECT
List<User> users = db.select()
.from("users")
.where("age > ?", 18)
.orderBy("created_at DESC")
.limit(10)
.fetch(rs -> new User(
rs.getInt("id"),
rs.getString("username"),
rs.getString("email")
));
// INSERT
db.insert("users")
.value("username", "john")
.value("email", "john@example.com")
.execute();
// UPDATE
db.update("users")
.set("email", "new@example.com")
.where("id = ?", 1)
.execute();
// DELETE
db.delete("users")
.where("inactive = ?", true)
.execute();The step builder pattern ensures type-safe query construction at compile time:
// ❌ This won't compile - missing FROM clause
db.select("*").fetch(mapper);
// ❌ This won't compile - can't use OFFSET without LIMIT
db.select("*").from("users").offset(10).fetch(mapper);
// ✅ Compiler guides you through valid steps
db.select("*")
.from("users") // Required
.where("active = ?", true) // Optional
.orderBy("id DESC") // Optional
.limit(10) // Optional
.offset(20) // Only available after LIMIT
.fetch(mapper);For queries executed multiple times, use prepared queries for better performance:
// Build query once
SelectQuery findUser = db.select()
.from("users")
.where("id = ?")
.prepare();
// Execute many times
User user1 = findUser.fetchFirst(userMapper, 1);
User user2 = findUser.fetchFirst(userMapper, 2);
User user3 = findUser.fetchFirst(userMapper, 3);public class UserRepository {
private final SelectQuery findById;
private final InsertQuery createUser;
private final UpdateQuery updateEmail;
public UserRepository(Database db) {
// Prepare queries once in constructor
this.findById = db.select()
.from("users")
.where("id = ?")
.prepare();
this.createUser = db.insert("users")
.value("username", null)
.value("email", null)
.prepare();
this.updateEmail = db.update("users")
.set("email", null)
.where("id = ?")
.prepare();
}
// Reuse prepared queries
public User findById(int id) throws SQLException {
return findById.fetchFirst(this::mapUser, id);
}
public void create(String username, String email) throws SQLException {
createUser.execute(username, email);
}
public void updateEmail(int id, String email) throws SQLException {
updateEmail.execute(email, id);
}
}Transactions
db.transaction(conn -> {
db.executeUpdate(conn, "INSERT INTO users (name) VALUES (?)", "john");
db.executeUpdate(conn, "INSERT INTO profiles (user_id) VALUES (?)", userId);
// Automatic rollback on exception
});// JOINs
List<Post> posts = db.select("posts.*", "users.username")
.from("posts")
.innerJoin("users", "users.id = posts.user_id")
.where("posts.published = ?", true)
.orderBy("posts.created_at DESC")
.fetch(postMapper);
// GROUP BY & HAVING
List<Stats> stats = db.select("user_id", "COUNT(*) as count")
.from("posts")
.groupBy("user_id")
.having("COUNT(*) > 10")
.fetch(statsMapper);// SQLite
String url = DatabaseUtils.sqlite("database.db");
// MySQL with parameters
String params = DatabaseUtils.mysqlParams()
.useSSL(false)
.serverTimezone("UTC")
.build();
String url = DatabaseUtils.mysql("localhost", "mydb", params);
// PostgreSQL
String url = DatabaseUtils.postgresql("localhost", 5432, "mydb");
// H2
String url = DatabaseUtils.h2Memory("testdb");- Java 17+
- HikariCP (optional, for connection pooling)
- JDBC driver for your database