Skip to content

Commit 89b6f36

Browse files
committed
Introduces SQL Database and configuration.
1 parent 8f04ee5 commit 89b6f36

File tree

9 files changed

+310
-21
lines changed

9 files changed

+310
-21
lines changed

java-admin-web/src/java/net/compsoc/ox/web/admin/AdminServlet.java

Lines changed: 21 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -8,7 +8,10 @@
88
import javax.servlet.http.HttpServletResponse;
99

1010
import net.compsoc.ox.database.Database;
11-
import net.compsoc.ox.database.impl.dummy.DummyDatabase;
11+
import net.compsoc.ox.database.config.CompSocConfig;
12+
import net.compsoc.ox.database.config.CompSocYAMLConfig;
13+
import net.compsoc.ox.database.util.exceptions.ConfigurationException;
14+
import net.compsoc.ox.database.util.exceptions.DatabaseInitialisationException;
1215
import net.compsoc.ox.web.admin.sections.RootSection;
1316
import net.compsoc.ox.web.admin.sections.Section;
1417
import net.compsoc.ox.web.admin.util.PageBuilder;
@@ -25,7 +28,22 @@ public class AdminServlet extends HttpServlet {
2528

2629
public AdminServlet() {
2730
// Create Database
28-
database = new DummyDatabase();
31+
Database database = null;
32+
try {
33+
database = Database.fromConfig(loadConfig());
34+
} catch (ConfigurationException e) {
35+
System.out.print("Could not start, configuration error: ");
36+
System.out.println(e.getMessage());
37+
System.exit(1);
38+
} catch (DatabaseInitialisationException e) {
39+
e.printStackTrace();
40+
System.exit(1);
41+
}
42+
this.database = database;
43+
}
44+
45+
private CompSocConfig loadConfig() throws ConfigurationException {
46+
return new CompSocYAMLConfig(null);
2947
}
3048

3149
@Override
@@ -51,7 +69,7 @@ private void handle(HttpServletRequest request, HttpServletResponse response)
5169
response.setHeader("Location", e.location);
5270
} catch (StatusException e) {
5371
response.sendError(e.code);
54-
} catch (Exception e){
72+
} catch (Exception e) {
5573
e.printStackTrace();
5674
throw e;
5775
}

java-core/pom.xml

Lines changed: 32 additions & 18 deletions
Original file line numberDiff line numberDiff line change
@@ -1,19 +1,33 @@
1-
<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
2-
<modelVersion>4.0.0</modelVersion>
3-
<groupId>net.compsoc.ox</groupId>
4-
<artifactId>database-core</artifactId>
5-
<version>0.0.1-SNAPSHOT</version>
6-
<build>
7-
<sourceDirectory>src</sourceDirectory>
8-
<plugins>
9-
<plugin>
10-
<artifactId>maven-compiler-plugin</artifactId>
11-
<version>3.1</version>
12-
<configuration>
13-
<source>1.7</source>
14-
<target>1.7</target>
15-
</configuration>
16-
</plugin>
17-
</plugins>
18-
</build>
1+
<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
2+
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
3+
<modelVersion>4.0.0</modelVersion>
4+
<groupId>net.compsoc.ox</groupId>
5+
<artifactId>database-core</artifactId>
6+
<version>0.0.1-SNAPSHOT</version>
7+
<build>
8+
<sourceDirectory>src</sourceDirectory>
9+
<plugins>
10+
<plugin>
11+
<artifactId>maven-compiler-plugin</artifactId>
12+
<version>3.1</version>
13+
<configuration>
14+
<source>1.7</source>
15+
<target>1.7</target>
16+
</configuration>
17+
</plugin>
18+
</plugins>
19+
</build>
20+
<dependencies>
21+
<dependency>
22+
<groupId>org.yaml</groupId>
23+
<artifactId>snakeyaml</artifactId>
24+
<version>1.15</version>
25+
</dependency>
26+
<dependency>
27+
<groupId>org.postgresql</groupId>
28+
<artifactId>postgresql</artifactId>
29+
<version>9.4-1201-jdbc41</version>
30+
</dependency>
31+
32+
</dependencies>
1933
</project>
Lines changed: 31 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,9 +1,40 @@
11
package net.compsoc.ox.database;
22

3+
import net.compsoc.ox.database.config.CompSocConfig;
34
import net.compsoc.ox.database.iface.events.Events;
5+
import net.compsoc.ox.database.impl.dummy.DummyDatabase;
6+
import net.compsoc.ox.database.impl.sql.PostgresDatabase;
7+
import net.compsoc.ox.database.util.exceptions.ConfigurationException;
8+
import net.compsoc.ox.database.util.exceptions.DatabaseInitialisationException;
49

510
public abstract class Database {
611

712
public abstract Events<?, ?> events();
813

14+
public static Database fromConfig(CompSocConfig config) throws DatabaseInitialisationException,
15+
ConfigurationException {
16+
CompSocConfig.DatabaseConfig dbConf = config.database();
17+
if (dbConf == null) {
18+
throw new ConfigurationException("Configuration does not include database information");
19+
}
20+
21+
switch (dbConf.type()) {
22+
case "dummy":
23+
return new DummyDatabase();
24+
case "postgres":
25+
return postgresDatabase(dbConf);
26+
default:
27+
throw new ConfigurationException("Invalid Database Type: " + dbConf.type());
28+
29+
}
30+
}
31+
32+
private static Database postgresDatabase(CompSocConfig.DatabaseConfig dbConf)
33+
throws DatabaseInitialisationException {
34+
35+
return new PostgresDatabase(dbConf.host(), dbConf.port(), dbConf.name(), dbConf.username(),
36+
dbConf.password());
37+
38+
}
39+
940
}
Lines changed: 59 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,59 @@
1+
package net.compsoc.ox.database.config;
2+
3+
public abstract class CompSocConfig {
4+
5+
protected DatabaseConfig database;
6+
7+
public DatabaseConfig database() {
8+
return database;
9+
}
10+
11+
public static abstract class DatabaseConfig {
12+
13+
private final String type;
14+
protected String host;
15+
protected int port = -1;
16+
protected String username;
17+
protected String password;
18+
protected String name;
19+
20+
protected DatabaseConfig(String type) {
21+
if (type == null)
22+
throw new NullPointerException();
23+
this.type = type;
24+
}
25+
26+
/**
27+
* @return the type of the database (never null)
28+
*/
29+
public String type() {
30+
return type;
31+
}
32+
33+
public String host() {
34+
return host;
35+
}
36+
37+
/**
38+
* @return -1 if one is not specified (default) otherwise the number
39+
* specified
40+
*/
41+
public int port() {
42+
return port;
43+
}
44+
45+
public String username() {
46+
return username;
47+
}
48+
49+
public String password() {
50+
return password;
51+
}
52+
53+
public String name() {
54+
return name;
55+
}
56+
57+
}
58+
59+
}
Lines changed: 74 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,74 @@
1+
package net.compsoc.ox.database.config;
2+
3+
import java.io.InputStream;
4+
import java.util.Map;
5+
6+
import net.compsoc.ox.database.util.exceptions.ConfigurationException;
7+
8+
import org.yaml.snakeyaml.Yaml;
9+
10+
public class CompSocYAMLConfig extends CompSocConfig {
11+
12+
public CompSocYAMLConfig(InputStream is) throws ConfigurationException {
13+
Yaml yaml = new Yaml();
14+
15+
String document = "";
16+
document += "database:\n";
17+
document += " type: postgres\n";
18+
document += " host: localhost\n";
19+
document += " port: 60001\n";
20+
document += " user: username\n";
21+
document += " pass: password\n";
22+
document += " name: db_name\n";
23+
24+
Object config = yaml.load(document);
25+
setupConfig(prepareMap(config, "yaml file"));
26+
27+
}
28+
29+
private void setupConfig(Map<String, Object> config) throws ConfigurationException {
30+
Object dbConfig = config.get("database");
31+
if(dbConfig != null)
32+
setupDatabase(prepareMap(dbConfig, "database"));
33+
34+
}
35+
36+
private void setupDatabase(Map<String, Object> config) throws ConfigurationException {
37+
String type = getValue(config, "type", String.class, "database type");
38+
if(type == null){
39+
throw new ConfigurationException("database needs a type");
40+
}
41+
this.database = new DatabaseConfig(type){};
42+
this.database.host = getValue(config, "host", String.class, "database host");
43+
Integer port = getValue(config, "port", Integer.class, "database port");
44+
this.database.port = port == null ? -1 : port;
45+
this.database.username = getValue(config, "user", String.class, "database user");
46+
this.database.password = getValue(config, "pass", String.class, "database pass");
47+
this.database.name = getValue(config, "name", String.class, "database name");
48+
}
49+
50+
// Helper Methods
51+
52+
@SuppressWarnings("unchecked")
53+
private static Map<String, Object> prepareMap(Object object, String name)
54+
throws ConfigurationException {
55+
try {
56+
return (Map<String, Object>) object;
57+
} catch (ClassCastException e) {
58+
throw new ConfigurationException(name
59+
+ " is not a set of key,value pairs (YAML Associated Array)");
60+
}
61+
}
62+
63+
private static <T> T getValue(Map<String, Object> map, String key, Class<T> cls, String name)
64+
throws ConfigurationException {
65+
try {
66+
return cls.cast(map.get(key));
67+
} catch(ClassCastException e){
68+
throw new ConfigurationException("Invalid type for " + name);
69+
}
70+
}
71+
72+
73+
74+
}
Lines changed: 42 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,42 @@
1+
package net.compsoc.ox.database.impl.sql;
2+
3+
import java.sql.DriverManager;
4+
import java.sql.SQLException;
5+
6+
import net.compsoc.ox.database.iface.events.Events;
7+
import net.compsoc.ox.database.util.exceptions.DatabaseInitialisationException;
8+
9+
public class PostgresDatabase extends SQLDatabase {
10+
11+
public PostgresDatabase(String host, int port, String database, String username, String password)
12+
throws DatabaseInitialisationException {
13+
try {
14+
Class.forName("org.postgresql.Driver");
15+
} catch (ClassNotFoundException e) {
16+
throw new DatabaseInitialisationException(e);
17+
}
18+
19+
// Construct URL
20+
String url;
21+
if (host == null)
22+
url = String.format("jdbc:postgresql:%s", database);
23+
else if (port == -1)
24+
url = String.format("jdbc:postgresql://%s/%s", host, database);
25+
else
26+
url = String.format("jdbc:postgresql://%s:%d/%s", host, port, database);
27+
28+
System.out.println("Connecting to POSTGRESQL Server using URL: " + url);
29+
30+
try {
31+
setupConnection(DriverManager.getConnection(url, username, password));
32+
} catch (SQLException e) {
33+
throw new DatabaseInitialisationException(e);
34+
}
35+
}
36+
37+
@Override
38+
public Events<?, ?> events() {
39+
return null;
40+
}
41+
42+
}
Lines changed: 37 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,37 @@
1+
package net.compsoc.ox.database.impl.sql;
2+
3+
import java.sql.Connection;
4+
import java.sql.SQLException;
5+
6+
import net.compsoc.ox.database.Database;
7+
8+
public abstract class SQLDatabase extends Database {
9+
10+
private Connection connection;
11+
12+
public SQLDatabase() {
13+
Runtime.getRuntime().addShutdownHook(new Thread() {
14+
public void run() {
15+
System.out.println("Shutting down any SQL Database Connections");
16+
if (connection != null)
17+
try {
18+
connection.close();
19+
} catch (SQLException e) {
20+
e.printStackTrace();
21+
}
22+
}
23+
});
24+
}
25+
26+
protected void setupConnection(Connection connection) {
27+
if (connection != null)
28+
try {
29+
connection.close();
30+
} catch (SQLException e) {
31+
e.printStackTrace();
32+
}
33+
this.connection = connection;
34+
35+
}
36+
37+
}
Lines changed: 7 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,7 @@
1+
package net.compsoc.ox.database.util.exceptions;
2+
3+
public class ConfigurationException extends Exception {
4+
public ConfigurationException(String message){
5+
super(message);
6+
}
7+
}
Lines changed: 7 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,7 @@
1+
package net.compsoc.ox.database.util.exceptions;
2+
3+
public class DatabaseInitialisationException extends Exception {
4+
public DatabaseInitialisationException(Throwable throwable) {
5+
super(throwable);
6+
}
7+
}

0 commit comments

Comments
 (0)