/* Copyright 2015 CrushPaper.com. This file is part of CrushPaper. CrushPaper is free software: you can redistribute it and/or modify it under the terms of version 3 of the GNU Affero General Public License as published by the Free Software Foundation. CrushPaper is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Affero General Public License for more details. You should have received a copy of the GNU Affero General Public License along with CrushPaper. If not, see <http://www.gnu.org/licenses/>. */ package com.crushpaper; import java.io.File; import java.io.FileInputStream; import java.io.FileNotFoundException; import java.io.IOException; import java.util.Properties; import java.util.regex.Pattern; /** * This class loads configuration from a properties file. It validates * individual properties as they are read. It is responsible for printing error * messages. */ public class Configuration { private Properties properties; /** Loads the file. Returns false if it could not be loaded. */ public boolean load(File configFile) { FileInputStream fileInput; try { fileInput = new FileInputStream(configFile); } catch (FileNotFoundException e) { System.err.println("crushpaper: Sorry, the configuration file `" + configFile.getAbsolutePath() + "` could not be imported because it does not exist."); return false; } properties = new Properties(); try { properties.load(fileInput); } catch (IOException e) { System.err.println("crushpaper: Sorry, the configuration file `" + configFile.getAbsolutePath() + "` could not be imported because `" + e.getMessage() + "`."); return false; } return true; } /** * Returns the name of the key that indicates if the server allows users to * save notes even if they are not signed in. */ public String getAllowSaveIfNotLoggedInKey() { return "allowSaveIfNotSignedIn"; } /** * Returns true if the server allows users to save notes even if they are * not signed in. */ public Boolean getAllowSaveIfNotSignedIn() { return getBooleanHelper(getAllowSaveIfNotLoggedInKey()); } /** * Returns the name of the key that indicates if the server consider * connections over the loopback address to be admins. */ public String getLoopbackIsAdminKey() { return "loopbackIsAdmin"; } /** * Returns true if the server consider connections over the loopback address * to be admins. */ public Boolean getLoopbackIsAdmin() { return getBooleanHelper(getLoopbackIsAdminKey()); } /** * Returns true if the server is the official crushpaper.com site. */ public Boolean getIsOfficialSite() { Boolean value = getBooleanHelper("isOfficialSite"); if (value == null) { return false; } return value; } /** * Returns the name of the key that indicates if the server allows users to * save notes even if they are not logged in. */ public String getAllowSelfSignUpKey() { return "allowSelfSignUp"; } /** * Returns true if the server allows users to save notes even if they are * not logged in. */ public Boolean getAllowSelfSignUp() { return getBooleanHelper(getAllowSelfSignUpKey()); } /** Helper function. */ private Boolean getBooleanHelper(String key) { String value = properties.getProperty(key, "false"); if (value != null && !value.equals("true") && !value.equals("false")) { System.err.println("crushpaper: Sorry, the value `" + value + "` for property `" + key + "` is not true or false."); System.exit(1); } return Boolean.valueOf(value); } /** * Returns the name of the key that indicates if the server is in single * user mode. */ public String getSingleUserKey() { return "singleUser"; } /** * Returns the username if the server is in single user mode or null if the * server is not in single user mode. */ public String getSingleUserName() { return properties.getProperty(getSingleUserKey(), null); } /** * Returns the name of the key for the HTTP port that the server should * listen on. */ public String getHttpPortKey() { return "http.port"; } /** Returns the HTTP port that the server should listen on. */ public Integer getHttpPort() { return getPort(getHttpPortKey(), "8080"); } /** * Returns the name of the key for the HTTPS port that the server should * listen on. */ public String getHttpsPortKey() { return "https.port"; } /** * Returns the name of the key for the HTTPS port that is being proxied to the server's HTTPS port. */ public String getHttpsProxiedPortKey() { return "https.proxiedPort"; } /** Returns the HTTPS port that the server should listen on. */ public Integer getHttpsPort() { return getPort(getHttpsPortKey(), null); } /** Returns the HTTPS port that is being proxied to the server's HTTPS port. */ public Integer getHttpsProxiedPort() { return getPort(getHttpsProxiedPortKey(), null); } /** Returns the name of the key for the key store file used for SSL. */ public String getKeyStoreKey() { return "https.keystore"; } /** Returns the key store file used for SSL. */ public File getKeyStoreFile() { return getFileThatExists(getKeyStoreKey(), null); } /** Returns the key store password for the key store file. */ public String getKeyStorePassword() { return properties.getProperty("https.keystorePassword"); } /** Returns the key manager password for the key store file. */ public String getKeyManagerPassword() { return properties.getProperty("https.keymanagerPassword"); } /** * Returns the name of the key for the file containing extra HTML header * data. */ public String getExtraHeaderKey() { return "http.extraHeader"; } /** Returns the file containing extra HTML header data. */ public File getExtraHeaderFile() { return getFileThatExists(getExtraHeaderKey(), null); } /** * Returns the name of the key for the directory used to store the database. */ public String getDatabaseDirectoryKey() { return "database.directory"; } /** Returns the directory used to store the database. */ public File getDatabaseDirectory() { return getDirectory(getDatabaseDirectoryKey(), null); } /** Returns the directory in which sessions are persisted. */ public File getSessionStoreDirectory() { return getDirectory("sessionStore.directory", null); } /** * Returns the name of the key for the directory used to store the log * files. */ public String getLogDirectoryKey() { return "logs.directory"; } /** Returns the directory used to store the log files.. */ public File getLogDirectory() { return getDirectory(getLogDirectoryKey(), null); } /** Returns the directory used to store temporary files. */ public File getTemporaryDirectory() { return getDirectory("temporary.directory", null); } /** A helper method that validates that a property value is a port. */ private Integer getPort(String key, String defaultValue) { String stringValue = properties.getProperty(key, defaultValue); if (stringValue == null) { return null; } if (!Pattern.compile("^[0-9]+$").matcher(stringValue).find()) { System.err.println("crushpaper: Sorry, the value `" + stringValue + "` for property `" + key + "` is not a number."); System.exit(1); } int intValue = Integer.parseInt(stringValue); if (intValue < 1 || intValue > 256 * 256) { System.err.println("crushpaper: Sorry, the value `" + stringValue + "` for property `" + key + "` is not a port number."); System.exit(1); } return intValue; } /** * A helper method that validates that a property value is a path that * exists. */ private File getPathThatExists(String key, String defaultValue) { String value = properties.getProperty(key, defaultValue); if (value == null) return null; File file = new File(value); if (!file.exists()) { System.err.println("crushpaper: Sorry, the path `" + value + "` for property `" + key + "` does not exist in the file system."); System.exit(1); } return file; } /** * A helper method that validates that a property value is a directory that * exists. */ private File getDirectory(String key, String defaultValue) { String value = properties.getProperty(key, defaultValue); if (value == null) { return null; } File file = new File(value); if (file.exists() && !file.isDirectory()) { System.err.println("crushpaper: Sorry, the path `" + file.getAbsolutePath() + "` for property `" + key + "` is not a directory."); System.exit(1); } return file; } /** * A helper method that validates that a property value is a file that * exists. */ private File getFileThatExists(String key, String defaultValue) { File file = getPathThatExists(key, defaultValue); if (file == null) return null; if (!file.isFile()) { System.err.println("crushpaper: Sorry, the path `" + file.getAbsolutePath() + "` for property `" + key + "` is not a file."); System.exit(1); } return file; } }