Skip to content

Commit

Permalink
Update geogig plugin to have less reliance on a filesystem-backed res…
Browse files Browse the repository at this point in the history
…ource store.

Signed-off-by: Johnathan Garrett <jd@prominentedge.com>
  • Loading branch information
jdgarrett authored and Erik Merkle committed May 25, 2017
1 parent e1c38bb commit 72009d3
Show file tree
Hide file tree
Showing 11 changed files with 392 additions and 159 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -11,7 +11,6 @@
import static com.google.common.collect.Iterators.transform;
import static com.google.common.collect.Lists.newArrayList;

import java.io.File;
import java.io.FileNotFoundException;
import java.io.IOException;
import java.io.InputStreamReader;
Expand All @@ -32,7 +31,6 @@
import org.geoserver.platform.resource.Paths;
import org.geoserver.platform.resource.Resource;
import org.geoserver.platform.resource.ResourceStore;
import org.geoserver.platform.resource.Resources;
import org.geotools.util.logging.Logging;

import com.google.common.base.Charsets;
Expand Down Expand Up @@ -94,7 +92,7 @@ private static class CachedInfo {
public ConfigStore(ResourceStore resourceLoader) {
checkNotNull(resourceLoader, "resourceLoader");
this.resourceLoader = resourceLoader;
if (null == Resources.directory(resourceLoader.get(CONFIG_DIR_NAME), true)) {
if (resourceLoader.get(CONFIG_DIR_NAME) == null) {
throw new IllegalStateException("Unable to create config directory " + CONFIG_DIR_NAME);
}
this.lock = new ReentrantReadWriteLock();
Expand Down Expand Up @@ -204,9 +202,8 @@ private Resource whitelistResource() {
}

private static List<WhitelistRule> loadWhitelist(Resource input) throws IOException {
File parent = input.parent().dir();
File f = new File(parent, input.name());
if (!(parent.exists() && f.exists())) {
Resource parent = input.parent();
if (!(parent.getType().equals(Resource.Type.DIRECTORY) && input.getType().equals(Resource.Type.RESOURCE))) {
return newArrayList();
}
try (Reader reader = new InputStreamReader(input.in(), Charsets.UTF_8)) {
Expand Down Expand Up @@ -260,11 +257,9 @@ public RepositoryInfo get(final String id) throws IOException {
}

private static RepositoryInfo load(Resource input) throws IOException {
// make an explicit check here because FileSystemResource.file() creates an empty file
File parent = input.parent().dir();
File f = new File(parent, input.name());
if (!(parent.exists() && f.exists())) {
throw new FileNotFoundException("File not found: " + f.getAbsolutePath());
Resource parent = input.parent();
if (!(parent.getType().equals(Resource.Type.DIRECTORY) && input.getType().equals(Resource.Type.RESOURCE))) {
throw new FileNotFoundException("File not found: " + input.path());
}
RepositoryInfo info;
try (Reader reader = new InputStreamReader(input.in(), Charsets.UTF_8)) {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -12,13 +12,9 @@
import static org.geogig.geoserver.config.LogStoreInitializer.runScript;
import static org.geogig.geoserver.config.LogStoreInitializer.saveConfig;

import java.io.File;
import java.io.FileInputStream;
import java.io.FileNotFoundException;
import java.io.IOException;
import java.io.InputStream;
import java.net.MalformedURLException;
import java.net.URL;
import java.sql.Connection;
import java.sql.PreparedStatement;
import java.sql.ResultSet;
Expand Down Expand Up @@ -80,7 +76,7 @@ public class LogStore implements GeoServerLifecycleHandler, InitializingBean {

private Logger LOGBACKLOGGER;

private File configFile;
private Resource configResource;

private DataSource dataSource;

Expand Down Expand Up @@ -138,59 +134,54 @@ void destroy() {
DataSource dataSource = this.dataSource;
this.dataSource = null;
this.LOGBACKLOGGER = null;
this.configFile = null;
this.configResource = null;
LogStoreInitializer.dispose(dataSource);
}
}

private void init() {
try {
this.configFile = findOrCreateConfigFile();
this.configResource = findOrCreateConfigResource();
} catch (IOException e) {
throw Throwables.propagate(e);
}
Properties properties = new Properties();
try (InputStream in = new FileInputStream(configFile)) {
try (InputStream in = configResource.in()) {
properties.load(in);
} catch (FileNotFoundException e) {
throw new IllegalArgumentException("properties file does not exist: " + configFile);
throw new IllegalArgumentException("properties file does not exist: " + configResource.path());
} catch (IOException e) {
throw new RuntimeException("Error loading properties file " + configFile, e);
throw new RuntimeException("Error loading properties file " + configResource.path(), e);
}

boolean enabled = Boolean.valueOf(properties.getProperty(PROP_ENABLED));
if (enabled) {
dataSource = newDataSource(properties, configFile);
dataSource = newDataSource(properties, configResource);
boolean runScript = Boolean.valueOf(properties.getProperty(PROP_RUN_SCRIPT));
if (runScript) {
String scriptProp = properties.getProperty(PROP_SCRIPT);
URL script = resolveScript(scriptProp, configFile);
Resource script = resolveScript(scriptProp, configResource);
runScript(dataSource, script);
// all good, lets disable the script for the next runs
properties.setProperty(PROP_RUN_SCRIPT, "false");
saveConfig(properties, configFile);
saveConfig(properties, configResource);
}

LOGBACKLOGGER = createLogger(dataSource);
}
this.enabled = enabled;
}

private URL resolveScript(String scriptProp, File configFile) {
File scriptFile = new File(scriptProp);
if (scriptFile.isAbsolute()) {
checkArgument(scriptFile.exists(), "Script file %s does not exist", scriptFile);
private Resource resolveScript(String scriptProp, Resource configResource) {
Resource scriptResource = resourceStore.get(scriptProp);

if (scriptResource.getType().equals(Resource.Type.UNDEFINED)) {
scriptResource = configResource.parent().get(scriptProp);
checkArgument(scriptResource.getType().equals(Resource.Type.RESOURCE), "Script file %s does not exist",
scriptResource.path());
}
// find it relative to config file
scriptFile = new File(configFile.getParentFile(), scriptProp);
checkArgument(scriptFile.exists(), "Script file %s does not exist",
scriptFile.getAbsolutePath());

try {
return scriptFile.toURI().toURL();
} catch (MalformedURLException e) {
throw Throwables.propagate(e);
}
return scriptResource;
}

public void debug(@Nullable String repoUrl, @Nullable CharSequence message) {
Expand Down Expand Up @@ -344,22 +335,21 @@ private static String user() {
return name;
}

private File findOrCreateConfigFile() throws IOException {
private Resource findOrCreateConfigResource() throws IOException {
Resource dirResource = resourceStore.get(CONFIG_DIR_NAME);
File dir = dirResource.dir();
File configFile = new File(dir, CONFIG_FILE_NAME);

copySampleInitSript(dir, "mysql.sql");
copySampleInitSript(dir, "postgresql.sql");
copySampleInitSript(dir, "postgresql.properties");
copySampleInitSript(dir, "sqlite.sql");
copySampleInitSript(dir, "hsqldb.sql");
copySampleInitSript(dir, "hsqldb.properties");

if (!configFile.exists()) {
createDefaultConfig(configFile);
Resource configResource = dirResource.get(CONFIG_FILE_NAME);

copySampleInitSript(dirResource, "mysql.sql");
copySampleInitSript(dirResource, "postgresql.sql");
copySampleInitSript(dirResource, "postgresql.properties");
copySampleInitSript(dirResource, "sqlite.sql");
copySampleInitSript(dirResource, "hsqldb.sql");
copySampleInitSript(dirResource, "hsqldb.properties");

if (configResource.getType().equals(Resource.Type.UNDEFINED)) {
createDefaultConfig(configResource);
}
return configFile;
return configResource;
}

private static Logger createLogger(DataSource dataSource) {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -15,18 +15,15 @@
import static org.geogig.geoserver.config.LogStore.PROP_URL;
import static org.geogig.geoserver.config.LogStore.PROP_USER;

import java.io.ByteArrayOutputStream;
import java.io.File;
import java.io.FileOutputStream;
import java.io.IOException;
import java.io.OutputStream;
import java.io.OutputStreamWriter;
import java.io.PrintWriter;
import java.io.StringReader;
import java.io.StringWriter;
import java.io.Writer;
import java.lang.reflect.InvocationHandler;
import java.lang.reflect.Method;
import java.net.URL;
import java.sql.Connection;
import java.sql.DriverManager;
import java.sql.SQLException;
Expand All @@ -39,6 +36,8 @@

import javax.sql.DataSource;

import org.apache.commons.io.IOUtils;
import org.geoserver.platform.resource.Resource;
import org.geotools.util.logging.Logging;

import com.google.common.base.Charsets;
Expand Down Expand Up @@ -72,9 +71,9 @@ static void dispose(DataSource dataSource) {
}
}

static DataSource newDataSource(final Properties properties, final File configFile) {
static DataSource newDataSource(final Properties properties, final Resource configResource) {
final String driverName = properties.getProperty(PROP_DRIVER_CLASS);
checkNotNull(driverName, "driverName not provided in properties file %s", configFile);
checkNotNull(driverName, "driverName not provided in properties resource %s", configResource.path());
try {
Class.forName(driverName);
} catch (ClassNotFoundException e) {
Expand All @@ -83,7 +82,7 @@ static DataSource newDataSource(final Properties properties, final File configFi
}

final String jdbcUrl = properties.getProperty(PROP_URL);
checkArgument(jdbcUrl != null, "url not provided in properties file %s", configFile);
checkArgument(jdbcUrl != null, "url not provided in properties resource %s", configResource.path());
final String username = properties.getProperty(PROP_USER);
final String password = properties.getProperty(PROP_PASSWORD);
final String maxConnectionsProp = properties.getProperty(PROP_MAX_CONNECTIONS);
Expand Down Expand Up @@ -121,16 +120,16 @@ static DataSource newDataSource(final Properties properties, final File configFi
return dataSource;
}

static void createDefaultConfig(final File propertiesFile) throws IOException {
final File configDirectory = propertiesFile.getParentFile();
final File dbFile = new File(configDirectory, "securitylogs.db");
static void createDefaultConfig(final Resource propertiesResource) throws IOException {
final Resource configDirectory = propertiesResource.parent();
final Resource dbFile = configDirectory.get("securitylogs.db");
final String driverClassName = "org.sqlite.JDBC";
final String jdbcUrl = "jdbc:sqlite:" + dbFile.getAbsolutePath();
final String jdbcUrl = "jdbc:sqlite:" + dbFile.file().getAbsolutePath();

createDefaultPropertiesFile(propertiesFile, driverClassName, jdbcUrl);
createDefaultPropertiesFile(propertiesResource, driverClassName, jdbcUrl);
}

private static void createDefaultPropertiesFile(final File propertiesFile,
private static void createDefaultPropertiesFile(final Resource propertiesResource,
final String driverClassName, final String jdbcUrl) {
Properties props = new Properties();
props.setProperty(PROP_ENABLED, "true");
Expand All @@ -141,19 +140,14 @@ private static void createDefaultPropertiesFile(final File propertiesFile,
props.setProperty(PROP_MAX_CONNECTIONS, "1");
props.setProperty(PROP_SCRIPT, "sqlite.sql");
props.setProperty(PROP_RUN_SCRIPT, "true");
try {
propertiesFile.createNewFile();
} catch (IOException e) {
throw Throwables.propagate(e);
}

saveConfig(props, propertiesFile);
saveConfig(props, propertiesResource);
}

static void saveConfig(Properties props, File propertiesFile) {
static void saveConfig(Properties props, Resource propertiesResource) {
String comments = configComments();

try (Writer writer = new OutputStreamWriter(new FileOutputStream(propertiesFile),
try (Writer writer = new OutputStreamWriter(propertiesResource.out(),
Charsets.UTF_8)) {
props.store(writer, comments);
} catch (IOException e) {
Expand Down Expand Up @@ -187,23 +181,22 @@ private static String configComments() {
return comments;
}

static void copySampleInitSript(File configDirectory, String scriptName) throws IOException {
File file = new File(configDirectory, scriptName);
if (file.exists()) {
static void copySampleInitSript(Resource configDirectory, String scriptName) throws IOException {
Resource resource = configDirectory.get(scriptName);
if (!resource.getType().equals(Resource.Type.UNDEFINED)) {
return;
}
file.createNewFile();
try (OutputStream out = new FileOutputStream(file)) {
try (OutputStream out = resource.out()) {
Resources.copy(LogStoreInitializer.class.getResource(scriptName), out);
}
}

static void runScript(DataSource ds, URL script) {
static void runScript(DataSource ds, Resource script) {
List<String> statements = parseStatements(script);

try {
try (Connection connection = ds.getConnection()) {
LOGGER.info("Running script " + script.getFile());
LOGGER.info("Running script " + script.name());
for (String sql : statements) {
try (Statement st = connection.createStatement()) {
LOGGER.fine(sql);
Expand All @@ -218,12 +211,12 @@ static void runScript(DataSource ds, URL script) {
}
}

private static List<String> parseStatements(URL script) {
private static List<String> parseStatements(Resource script) {
List<String> lines;
try {
OutputStream to = new ByteArrayOutputStream();
Resources.copy(script, to);
String scriptContents = to.toString();
StringWriter sw = new StringWriter();
IOUtils.copy(script.in(), sw);
String scriptContents = sw.toString();
lines = CharStreams.readLines(new StringReader(scriptContents));
} catch (IOException e) {
throw Throwables.propagate(e);
Expand Down

0 comments on commit 72009d3

Please sign in to comment.