mirror of
https://github.com/BentoBoxWorld/BentoBox.git
synced 2025-03-12 06:42:49 +01:00
Postgres implementation (#1142)
* WIP for https://github.com/BentoBoxWorld/BentoBox/issues/1093 * JSON based PostGresql * Completes PostgreSQL suport * Changed Postgres connector comments * Put back rest of Postgres jdbc URL * Update PostgreSQLDatabaseHandler.java
This commit is contained in:
parent
ac850907cc
commit
5ab5954f47
7
pom.xml
7
pom.xml
@ -221,6 +221,11 @@
|
|||||||
<artifactId>mongodb-driver</artifactId>
|
<artifactId>mongodb-driver</artifactId>
|
||||||
<version>${mongodb.version}</version>
|
<version>${mongodb.version}</version>
|
||||||
</dependency>
|
</dependency>
|
||||||
|
<dependency>
|
||||||
|
<groupId>postgresql</groupId>
|
||||||
|
<artifactId>postgresql</artifactId>
|
||||||
|
<version>9.1-901-1.jdbc4</version>
|
||||||
|
</dependency>
|
||||||
<!-- Vault: as their maven repo is down, we need to get it from jitpack -->
|
<!-- Vault: as their maven repo is down, we need to get it from jitpack -->
|
||||||
<!-- See https://github.com/MilkBowl/VaultAPI/issues/69 -->
|
<!-- See https://github.com/MilkBowl/VaultAPI/issues/69 -->
|
||||||
<dependency>
|
<dependency>
|
||||||
@ -345,7 +350,7 @@
|
|||||||
<failOnError>false</failOnError>
|
<failOnError>false</failOnError>
|
||||||
<additionalJOption>-Xdoclint:none</additionalJOption>
|
<additionalJOption>-Xdoclint:none</additionalJOption>
|
||||||
<!-- To compile with Java 11, this tag may be required -->
|
<!-- To compile with Java 11, this tag may be required -->
|
||||||
<!-- <javadocExecutable>${java.home}/bin/javadoc</javadocExecutable>-->
|
<!-- <javadocExecutable>${java.home}/bin/javadoc</javadocExecutable> -->
|
||||||
</configuration>
|
</configuration>
|
||||||
<executions>
|
<executions>
|
||||||
<execution>
|
<execution>
|
||||||
|
@ -51,17 +51,18 @@ public class Settings implements ConfigObject {
|
|||||||
private boolean useEconomy = true;
|
private boolean useEconomy = true;
|
||||||
|
|
||||||
// Database
|
// Database
|
||||||
@ConfigComment("JSON, MYSQL, MARIADB, MONGODB, SQLITE and YAML(deprecated).")
|
@ConfigComment("JSON, MYSQL, MARIADB, MONGODB, SQLITE, POSTGRESQL and YAML(deprecated).")
|
||||||
@ConfigComment("Transition database options are:")
|
@ConfigComment("Transition database options are:")
|
||||||
@ConfigComment(" YAML2JSON, YAML2MARIADB, YAML2MYSQL, YAML2MONGODB, YAML2SQLITE")
|
@ConfigComment(" YAML2JSON, YAML2MARIADB, YAML2MYSQL, YAML2MONGODB, YAML2SQLITE")
|
||||||
@ConfigComment(" JSON2MARIADB, JSON2MYSQL, JSON2MONGODB, JSON2SQLITE,")
|
@ConfigComment(" JSON2MARIADB, JSON2MYSQL, JSON2MONGODB, JSON2SQLITE, JSON2POSTGRESQL")
|
||||||
@ConfigComment(" MYSQL2JSON, MARIADB2JSON, MONGODB2JSON, SQLITE2JSON")
|
@ConfigComment(" MYSQL2JSON, MARIADB2JSON, MONGODB2JSON, SQLITE2JSON, POSTGRES2JSON")
|
||||||
@ConfigComment("If you need others, please make a feature request.")
|
@ConfigComment("If you need others, please make a feature request.")
|
||||||
@ConfigComment("Minimum required versions:")
|
@ConfigComment("Minimum required versions:")
|
||||||
@ConfigComment(" MySQL versions 5.7 or later")
|
@ConfigComment(" MySQL versions 5.7 or later")
|
||||||
@ConfigComment(" MariaDB versions 10.2.3 or later")
|
@ConfigComment(" MariaDB versions 10.2.3 or later")
|
||||||
@ConfigComment(" MongoDB versions 3.6 or later")
|
@ConfigComment(" MongoDB versions 3.6 or later")
|
||||||
@ConfigComment(" SQLite versions 3.28 or later")
|
@ConfigComment(" SQLite versions 3.28 or later")
|
||||||
|
@ConfigComment(" PostgreSQL versions 9.4 or later")
|
||||||
@ConfigComment("Transition options enable migration from one database type to another. Use /bbox migrate.")
|
@ConfigComment("Transition options enable migration from one database type to another. Use /bbox migrate.")
|
||||||
@ConfigComment("YAML and JSON are file-based databases.")
|
@ConfigComment("YAML and JSON are file-based databases.")
|
||||||
@ConfigComment("MYSQL might not work with all implementations: if available, use a dedicated database type (e.g. MARIADB).")
|
@ConfigComment("MYSQL might not work with all implementations: if available, use a dedicated database type (e.g. MARIADB).")
|
||||||
|
@ -1,6 +1,7 @@
|
|||||||
package world.bentobox.bentobox.database.sql.postgresql;
|
package world.bentobox.bentobox.database.sql.postgresql;
|
||||||
|
|
||||||
import org.eclipse.jdt.annotation.NonNull;
|
import org.eclipse.jdt.annotation.NonNull;
|
||||||
|
import org.postgresql.Driver;
|
||||||
|
|
||||||
import world.bentobox.bentobox.database.DatabaseConnectionSettingsImpl;
|
import world.bentobox.bentobox.database.DatabaseConnectionSettingsImpl;
|
||||||
import world.bentobox.bentobox.database.sql.SQLDatabaseConnector;
|
import world.bentobox.bentobox.database.sql.SQLDatabaseConnector;
|
||||||
@ -11,6 +12,17 @@ import world.bentobox.bentobox.database.sql.SQLDatabaseConnector;
|
|||||||
*/
|
*/
|
||||||
public class PostgreSQLDatabaseConnector extends SQLDatabaseConnector {
|
public class PostgreSQLDatabaseConnector extends SQLDatabaseConnector {
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Ensure the driver is loaded as JDBC Driver might be invisible to Java's ServiceLoader.
|
||||||
|
* Usually, this is not required as {@link DriverManager} detects JDBC drivers
|
||||||
|
* via {@code META-INF/services/java.sql.Driver} entries. However there might be cases when the driver
|
||||||
|
* is located at the application level classloader, thus it might be required to perform manual
|
||||||
|
* registration of the driver.
|
||||||
|
*/
|
||||||
|
static {
|
||||||
|
new Driver();
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Class for PostgreSQL database connections using the settings provided
|
* Class for PostgreSQL database connections using the settings provided
|
||||||
* @param dbSettings - database settings
|
* @param dbSettings - database settings
|
||||||
|
@ -1,7 +1,13 @@
|
|||||||
package world.bentobox.bentobox.database.sql.postgresql;
|
package world.bentobox.bentobox.database.sql.postgresql;
|
||||||
|
|
||||||
|
import java.sql.PreparedStatement;
|
||||||
|
import java.sql.SQLException;
|
||||||
|
|
||||||
|
import com.google.gson.Gson;
|
||||||
|
|
||||||
import world.bentobox.bentobox.BentoBox;
|
import world.bentobox.bentobox.BentoBox;
|
||||||
import world.bentobox.bentobox.database.DatabaseConnector;
|
import world.bentobox.bentobox.database.DatabaseConnector;
|
||||||
|
import world.bentobox.bentobox.database.objects.DataObject;
|
||||||
import world.bentobox.bentobox.database.sql.SQLConfiguration;
|
import world.bentobox.bentobox.database.sql.SQLConfiguration;
|
||||||
import world.bentobox.bentobox.database.sql.SQLDatabaseHandler;
|
import world.bentobox.bentobox.database.sql.SQLDatabaseHandler;
|
||||||
|
|
||||||
@ -9,8 +15,8 @@ import world.bentobox.bentobox.database.sql.SQLDatabaseHandler;
|
|||||||
*
|
*
|
||||||
* @param <T>
|
* @param <T>
|
||||||
*
|
*
|
||||||
* @since 1.6.0
|
* @since 1.11.0
|
||||||
* @author tastybento, Poslovitch
|
* @author tastybento
|
||||||
*/
|
*/
|
||||||
public class PostgreSQLDatabaseHandler<T> extends SQLDatabaseHandler<T> {
|
public class PostgreSQLDatabaseHandler<T> extends SQLDatabaseHandler<T> {
|
||||||
|
|
||||||
@ -23,7 +29,50 @@ public class PostgreSQLDatabaseHandler<T> extends SQLDatabaseHandler<T> {
|
|||||||
* @param databaseConnector Contains the settings to create a connection to the database
|
* @param databaseConnector Contains the settings to create a connection to the database
|
||||||
*/
|
*/
|
||||||
PostgreSQLDatabaseHandler(BentoBox plugin, Class<T> type, DatabaseConnector databaseConnector) {
|
PostgreSQLDatabaseHandler(BentoBox plugin, Class<T> type, DatabaseConnector databaseConnector) {
|
||||||
super(plugin, type, databaseConnector, new SQLConfiguration(type.getCanonicalName()));
|
super(plugin, type, databaseConnector, new SQLConfiguration(type.getCanonicalName())
|
||||||
|
// Set uniqueid as the primary key (index). Postgresql convention is to use lower case field names
|
||||||
|
// Postgresql also uses double quotes (") instead of (`) around tables names with dots.
|
||||||
|
.schema("CREATE TABLE IF NOT EXISTS \"" + type.getCanonicalName() + "\" (uniqueid VARCHAR PRIMARY KEY, json jsonb NOT NULL)")
|
||||||
|
.loadObject("SELECT * FROM \"" + type.getCanonicalName() + "\" WHERE uniqueid = ? LIMIT 1")
|
||||||
|
.deleteObject("DELETE FROM \"" + type.getCanonicalName() + "\" WHERE uniqueid = ?")
|
||||||
|
// uniqueId has to be added into the row explicitly so we need to override the saveObject method
|
||||||
|
// The json value is a string but has to be cast to json when done in Java
|
||||||
|
.saveObject("INSERT INTO \"" + type.getCanonicalName() + "\" (uniqueid, json) VALUES (?, cast(? as json)) "
|
||||||
|
// This is the Postgresql version of UPSERT.
|
||||||
|
+ "ON CONFLICT (uniqueid) "
|
||||||
|
+ "DO UPDATE SET json = cast(? as json)")
|
||||||
|
.loadObjects("SELECT json FROM \"" + type.getCanonicalName() + "\"")
|
||||||
|
// Postgres exists function returns true or false natively
|
||||||
|
.objectExists("SELECT EXISTS(SELECT * FROM \"" + type.getCanonicalName() + "\" WHERE uniqueid = ?)")
|
||||||
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/* (non-Javadoc)
|
||||||
|
* @see world.bentobox.bentobox.database.sql.SQLDatabaseHandler#saveObject(java.lang.Object)
|
||||||
|
*/
|
||||||
|
@Override
|
||||||
|
public void saveObject(T instance) {
|
||||||
|
// Null check
|
||||||
|
if (instance == null) {
|
||||||
|
plugin.logError("Postgres database request to store a null. ");
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
if (!(instance instanceof DataObject)) {
|
||||||
|
plugin.logError("This class is not a DataObject: " + instance.getClass().getName());
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
Gson gson = getGson();
|
||||||
|
String toStore = gson.toJson(instance);
|
||||||
|
String uniqueId = ((DataObject)instance).getUniqueId();
|
||||||
|
processQueue.add(() -> {
|
||||||
|
try (PreparedStatement preparedStatement = getConnection().prepareStatement(getSqlConfig().getSaveObjectSQL())) {
|
||||||
|
preparedStatement.setString(1, uniqueId); // INSERT
|
||||||
|
preparedStatement.setString(2, toStore); // INSERT
|
||||||
|
preparedStatement.setString(3, toStore); // ON CONFLICT
|
||||||
|
preparedStatement.execute();
|
||||||
|
} catch (SQLException e) {
|
||||||
|
plugin.logError("Could not save object " + instance.getClass().getName() + " " + e.getMessage());
|
||||||
|
}
|
||||||
|
});
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
@ -29,17 +29,18 @@ general:
|
|||||||
# If there is no economy plugin present anyway, money will be automatically disabled.
|
# If there is no economy plugin present anyway, money will be automatically disabled.
|
||||||
use-economy: true
|
use-economy: true
|
||||||
database:
|
database:
|
||||||
# JSON, MYSQL, MARIADB, MONGODB, SQLITE and YAML(deprecated).
|
# JSON, MYSQL, MARIADB, MONGODB, SQLITE, POSTGRESQL and YAML(deprecated).
|
||||||
# Transition database options are:
|
# Transition database options are:
|
||||||
# YAML2JSON, YAML2MARIADB, YAML2MYSQL, YAML2MONGODB, YAML2SQLITE
|
# YAML2JSON, YAML2MARIADB, YAML2MYSQL, YAML2MONGODB, YAML2SQLITE
|
||||||
# JSON2MARIADB, JSON2MYSQL, JSON2MONGODB, JSON2SQLITE,
|
# JSON2MARIADB, JSON2MYSQL, JSON2MONGODB, JSON2SQLITE, JSON2POSTGRESQL
|
||||||
# MYSQL2JSON, MARIADB2JSON, MONGODB2JSON, SQLITE2JSON
|
# MYSQL2JSON, MARIADB2JSON, MONGODB2JSON, SQLITE2JSON, POSTGRESQL2JSON
|
||||||
# If you need others, please make a feature request.
|
# If you need others, please make a feature request.
|
||||||
# Minimum required versions:
|
# Minimum required versions:
|
||||||
# MySQL versions 5.7 or later
|
# MySQL versions 5.7 or later
|
||||||
# MariaDB versions 10.2.3 or later
|
# MariaDB versions 10.2.3 or later
|
||||||
# MongoDB versions 3.6 or later
|
# MongoDB versions 3.6 or later
|
||||||
# SQLite versions 3.28 or later
|
# SQLite versions 3.28 or later
|
||||||
|
# PostgreSQL versions 9.4 or later
|
||||||
# Transition options enable migration from one database type to another. Use /bbox migrate.
|
# Transition options enable migration from one database type to another. Use /bbox migrate.
|
||||||
# YAML and JSON are file-based databases.
|
# YAML and JSON are file-based databases.
|
||||||
# MYSQL might not work with all implementations: if available, use a dedicated database type (e.g. MARIADB).
|
# MYSQL might not work with all implementations: if available, use a dedicated database type (e.g. MARIADB).
|
||||||
|
Loading…
Reference in New Issue
Block a user