简体   繁体   English

构建数据库管理 Java 应用程序的正确方法是什么?

[英]What is the correct way to structure a Database Management Java application?

Firstly, forgive me if I don't sound coherent as I am still a beginner and not quite certain how to word some of these things.首先,如果我听起来不连贯,请原谅我,因为我仍然是初学者并且不太确定如何用这些词来表达。

I am creating a Library Management system in JavaFX using SQLite for the database.我正在使用 SQLite 作为数据库在 JavaFX 中创建一个图书馆管理系统。 I have familiarised myself with how SQL queries are handled in Java and my application is functional.我已经熟悉如何在 Java 中处理 SQL 查询并且我的应用程序可以正常运行。 However, I am now restructuring the application to make it follow OOP principles.但是,我现在正在重构应用程序以使其遵循 OOP 原则。 My question is in regard to what approach I should take with methods that involve querying the database.我的问题是关于涉及查询数据库的方法我应该采取什么方法。

In an ordinary application, I think I would write these methods in the relevant Class - say, for instance, a method to view information on a book would be contained in the "Book" class.在一个普通的应用程序中,我想我会在相关的类中编写这些方法 - 例如,一个查看书籍信息的方法将包含在“Book”类中。 But here that would involve creating a new database connection or passing around the current one, and my gut tells me this isn't the right way to do it.但在这里,这将涉及创建一个新的数据库连接或传递当前的连接,我的直觉告诉我这不是正确的方法。 Should I instead have a separate class to store the connection and also handle all database operations?我应该有一个单独的类来存储连接并处理所有数据库操作吗? What is the correct way to go about this?解决这个问题的正确方法是什么?

The problem is, relational tables don't map well to objects.问题是,关系表不能很好地映射到对象。 How does:如何:

SELECT author.name, book.title,
book.lang = author.native_tongue AS nativeWritten
FROM book LEFT JOIN author ON author.id = book.author;

translate to objects?转化为对象?

It doesn't.它没有。

If you want to forego the power of SQL everywhere, or at least in most places, and basically do SELECT * FROM book WHERE unid = 1;如果你想在任何地方,或者至少在大多数地方放弃 SQL 的力量,并且基本上做SELECT * FROM book WHERE unid = 1; and not go much further, you can make the trite oversimplification that there is a class of type Book and it matches both the book table and can reasonably encapsulate all the things you might want to do to the DB that involve books at all, okay, well, you could re-invent the wheel and rewrite all of JPA/Hibernate, or you just use that.不用再进一步了,您可以过分简化,即有一个 Book 类型的类,它与 book 表相匹配,并且可以合理地封装您可能想要对涉及书籍的 DB 执行的所有操作,好吧,好吧,您可以重新发明轮子并重写所有 JPA/Hibernate,或者您只是使用它。

Alternatively, you should look into JDBI or JOOQ which forego the idea that 'table in db == class in java', and are more SQL oriented.或者,您应该查看 JDBI 或 JOOQ,它们放弃了“db 中的表 == java 中的类”的想法,并且更面向 SQL。 These have all sorts of tutorials and guides to show you exactly how to use them.这些有各种各样的教程和指南,可以向您展示如何使用它们。

If you really are insistent on reinventing this wheel: Passing a connection object around is not crazy.如果你真的坚持要重新发明这个轮子:传递一个连接对象并不疯狂。 It's what is needed to perform the stated task.这是执行规定任务所需要的。 Something like:就像是:

public static Book getById(Connection db, int unid) throws SQLException { ... }

is one way.是一种方式。 A slightly more involved way that makes life easier for testing would be something like:一种使测试更轻松的稍微复杂的方法是:

public class DbBridge {
    public Book getById(int unid) throws SQLException { ... }
}

lets you abstract the notion of how to do the job, but.. then it means you're passing a DbBridge object around to everything.让您抽象出如何完成这项工作的概念,但是.. 那么这意味着您将 DbBridge 对象传递给所有内容。

The general principle of 'I have this somewhat complicated, stateful concept that I need in a ton of places, it's almost like a configuration' is a common problem. “我在很多地方都需要这个有点复杂、有状态的概念,它几乎就像一个配置”的一般原则是一个常见问题。 It is what 'dependency injection' frameworks such as dagger are trying to solve.这就是诸如 dagger 之类的“依赖注入”框架试图解决的问题。 You can either reinvent that wheel too, or just one of them.你也可以重新发明那个轮子,或者只是其中一个。 If you want to reinvent, well, have a look at how those projects work so you have an idea of what solutions are available.如果您想重新发明,那么请查看这些项目的工作原理,以便了解可用的解决方案。

NB: If you chose SQLite because it's 'lite', it's not.注意:如果您选择 SQLite 是因为它是“精简版”,那么它不是。 Not from the java perspective: You need a native executable to use it.不是从 java 的角度来看:您需要一个本机可执行文件才能使用它。 A muuch simpler and lighter approach is to use a java-native file-based db engine such as H2 or JavaDB.一种更简单、更轻便的方法是使用基于 Java 原生文件的数据库引擎,例如 H2 或 JavaDB。 Only use SQLite from java if you need that db to be accessible from non-java applications, or you're more or less forced into it, eg because you're writing android apps.如果您需要可以从非 Java 应用程序访问该数据库,或者您或多或少被迫使用它,例如因为您正在编写 android 应用程序,请仅使用 java 中的 SQLite。 Complexity-wise, SQLite is about as complicated as a full blown postgres or whatnot, from the java perspective.在复杂性方面,从 Java 的角度来看,SQLite 与完整的 postgres 或诸如此类的东西一样复杂。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM