package mykeynote.server.configuration;
import java.io.BufferedReader;
import java.io.File;
import java.io.FileNotFoundException;
import java.io.FileReader;
import java.io.FileWriter;
import java.io.IOException;
import java.util.Properties;
import mykeynote.exceptions.configuration.ConfigurationUnacceptableValue;
import mykeynote.exceptions.configuration.MissingConfigOptionException;
import mykeynote.exceptions.configuration.UniqueFileException;
import mykeynote.exceptions.report.ReportFileCreationException;
import mykeynote.exceptions.report.ReportNotInitializedException;
import mykeynote.misc.FormatConstants;
import mykeynote.server.Report;
/**
* This class loads the server related configuration and makes the loaded values
* available by providing getters. The unique file is loaded as well here and thus
* this class allows us to get the next unique. It allows us as well to save the
* unique value to the unique file.
* @author orlin
*
*/
public class Configuration {
/**
* This method is used to create the default instance, which later can be
* manipulated via setters.
* @param configFile Denotes the file, where the configuration is saved.
* @param reportToConsole If the program should report to the console, then
* set this to <b>true</b>, if the program should be deamonized, then set
* it to <b>false</b>.
* @throws IOException An IOException is thrown if the file is not readable.
* @throws FileNotFoundException A FileNotFoundException is thrown if the
* file specified does not exist.
*/
public Configuration(File configFile, boolean reportToConsole) throws FileNotFoundException, IOException{
this.configFile = configFile;
this.reportToConsole = reportToConsole;
}
/**
* This method is used to end the configuration and all it's sub parts,
* including saving the unique in the specified file and the report files.
* It however does not include the shutdown of the servers.
* @throws IOException An IOException can be hit when the unique file is being
* saved.
*/
public void finalizeConfiguration() throws IOException{
finalizeUnique();
/* Finalize the report at the very end, as we need it
* to report any problems during the shutdown process.
*/
finializeReport();
}
/* Configuration file and reading */
private File configFile;
private Properties config;
/**
* This method reads and applies the configuration, saved in the specified file.
* It also creates the Report utility after it has gathered the needed information
* for it's initialization.
* @throws IOException An IOException is thrown if a file is not readable.
* @throws FileNotFoundException A FileNotFoundException is thrown if the
* file specified does not exist.
* @throws MissingConfigOptionException This exception is thrown if a
* variable in the configuration file is not being set.
* @throws ReportFileCreationException This exception is thrown if a needed report file was not created.
* @throws ConfigurationUnacceptableValue This exception is thrown if an
* unacceptable value was set to a specific variable.
* @throws UniqueFileException This exception is thrown if the unique file was not created or could not be read.
*/
public void readConfigFile() throws FileNotFoundException, IOException,
MissingConfigOptionException, ReportFileCreationException,
ConfigurationUnacceptableValue, UniqueFileException{
//Loading the configuration
LoadConfiguration lc = new LoadConfiguration(configFile);
config = lc.loadConfiguration();
/* logs */
configLog();
/* Log Directory */
configLogDir();
/* Report section */
configReport();
/* ports section */
configPort();
/* unique */
configUnique();
/* KeyNote & MyKeynote section */
configKNMKN();
}
/**
* Gives a detailed look over the environment
* @return Returns the environment, in which the program runs.
*/
public String getEnviroment(){
String answer = getEnvReport();
answer += getEnvUnique();
answer += getEnvPort();
answer += getEnvKNMKN();
return answer;
//old, waiting to be deleted.
/* return String.format("Server Options are:" + "\n\tServer running: %s"
+ "\n\tListening on port: %s"
+ "\n\nLogging options are:" + "\n\tServer Logging is: %s"
+ "\n\tVerbose Logging is: %s" + "\n\tDebug Logging is: %s"
+ "\n\tDirectory for logging is %s" + "\n\tLog format is: %s"
+ "\n\tLogging to console is: %s"
+ "\n\nKeynote configuration part:"
+ "\n\tThe path to keynote is: %s"
+ "\n\tThe path to an external keynote library is: %s"
+ "\n\tPath to public key directory is: %s"
+ "\n\tPath to private key directory is: %s"
+ "\n\tUsing keynote command line: %s"
+ "\n\tAssertion format is: %s"
+ "\n\tTemporary Directory is: %s"
+ "\n\n\tCurrent unique is: %d", started, port, serverLog, verbouseLog , debugLog, logDir,
FormatConstants.LOGFORMAT, reportToConsole, pathToKeynote, pathToKNLib, publicKeyDir,
privateKeyDir, useCL, FormatConstants.ASSERTIONFORMAT, tempDir, unique);
*/
}
/**
* Checks the environment if all needed files are accessible, if there is a
* read rights on the needed files, etc. This step should be used after
* {@link #readConfigFile()} and before starting anything to run.
* @throws ConfigurationUnacceptableValue This exception is thrown if
* a value, that is being set, is not acceptable.
* @throws FileNotFoundException This exception is thrown when a certain file
* was not found, for example the keynote library or the keynote executable.
*/
public void checkEnvironment() throws ConfigurationUnacceptableValue, FileNotFoundException{
checkReport();
checkPort();
checkUnique();
checkKNMKN();
}
/*
* Here we define the configuration options and for each one of them the setter/getter
* in their own section
*/
/* Log section */
private boolean debugLog;
/**
* A getter for the debug Log
* @return Returns <b>true</b> when the debug logging is enabled,
* else returns <b>false</b>.
*/
public boolean getDebugLog(){
return debugLog;
}
private boolean verbouseLog;
/**
* A getter for the verbose Log
* @return Returns <b>true</b> when the verbose logging is enabled,
* else returns <b>false</b>.
*/
public boolean getVerbouseLog(){
return verbouseLog;
}
private boolean serverLog;
/**
* A getter for the server Log
* @return Returns <b>true</b> when the server logging is enabled,
* else returns <b>false</b>.
*/
public boolean getServerLog(){
return serverLog;
}
/**
* Reads the configuration, which is relevant for the log section,
* excluding the log directories.
* @throws ConfigurationUnacceptableValue This exception is thrown if an
* unacceptable value was set to a specific variable.
* @throws MissingConfigOptionException This exception is thrown a specific
* option in the configuration file was not set.
*/
private void configLog() throws ConfigurationUnacceptableValue, MissingConfigOptionException{
String temp;
if ((temp = config.getProperty("setLogLevel")) == null){
throw new MissingConfigOptionException("The option setLogLoevel was not set");
}else {
if (temp.compareTo("server") == 0) {
serverLog = true;
verbouseLog = false;
debugLog = false;
} else if (temp.compareTo("verbose") == 0) {
serverLog = true;
verbouseLog = true;
debugLog = false;
} else if (temp.compareTo("debug") == 0) {
serverLog = true;
verbouseLog = true;
debugLog = true;
} else {
throw new ConfigurationUnacceptableValue(
"In the configuration file there was a set un unkown option "
+ temp + " for the option setLogLevel");
}
}
}
/* Log directory */
private File logDir;
/**
* A getter for the log directory
* @return Returns the directory, where the logs reside.
*/
public File getLogDir(){
return logDir;
}
/**
* This method reads the configuration file for the log directory.
* @throws MissingConfigOptionException This exception is thrown a specific
* option in the configuration file was not set.
*/
private void configLogDir() throws MissingConfigOptionException{
String temp;
if ((temp = config.getProperty("logDir")) != null){
logDir = new File(temp);
} else {
throw new MissingConfigOptionException("The option setLogLoevel was not set");
}
}
/* Report section */
private boolean reportToConsole;
/**
* A getter for the status of the report to console variable.
* @return Returns <b>true</b> if we should report to the console, else
* returns <b>false</b>.
*/
public boolean getReportToConsole(){
return reportToConsole;
}
private Report report;
private String reportNotInitializedException = "A report was never initialized";
/**
* This method returns the instance of the report file, that is being
* initiated by the {@link #initializeReport()}, which normally is invoked by
* the {@link #configReport()}, which itself is invoked by the {@link #readConfigFile()} method.
* @return
* @throws ReportNotInitializedException This exception is thrown when the report
* is not initialized, which can be the case if the report was not initialized,
* or if the report was closed (using for example the {@link #finializeReport()} method.
*/
public Report getReport() throws ReportNotInitializedException{
if(report == null)
throw new ReportNotInitializedException(reportNotInitializedException);
return report;
}
/**
* This method is used to initialize the report files and is automatically
* executed after the report initialization step, which is handled by {@link #finializeReport()}.
* @throws ReportFileCreationException This exception is thrown if for some
* reason the report files could not be created.
*/
private void initializeReport() throws ReportFileCreationException{
report = new Report(logDir, FormatConstants.LOGFORMAT, this);
}
public boolean isDemonizied(){
return reportToConsole;
}
/**
* This method finilizes the report and closes the report files.
* @throws IOException
*/
private void finializeReport() throws IOException {
report.finish();
}
/**
* Reads the configuration, which is relevant for the report section,
* it creates as well the actual Report instance.
* @throws ReportFileCreationException This exception is thrown, when a report file
* does not exist, yet we were unable to create such one.
* @throws ConfigurationUnacceptableValue This error indicates that an
* unacceptable value was set for the reportToConsole option.
*/
private void configReport() throws ReportFileCreationException, ConfigurationUnacceptableValue{
String temp;
if(reportToConsole){
if ((temp = config.getProperty("reportToConsole")) != null){
if (temp.compareTo("true") == 0) {
reportToConsole = true;
} else if (temp.compareTo("false") == 0) {
reportToConsole = false;
} else
throw new ConfigurationUnacceptableValue(
"In the configuration file there was a set un unkown option "
+ temp + " for the option reportToConsole");
}
}
initializeReport();
}
private void checkReport(){
/* Not really needed, if the directory does not exist, then
files would have not been created in the initialization step.
if(!logDir.exists()){
throw new ConfigurationUnacceptableValue(String.format("The log directory %s does not exist.", logDir.getAbsoluteFile()));
}*/
}
/**
* This method returns a String of the logging related options, such as
* log directory and logging granulate (server, verbouse, debug).
* This output is included in the {@link #getEnviroment()} method.
* @return Returns a String of the logging related options.
*/
public String getEnvReport(){
String answer = "Logging related information:\n";
answer += "\tCurrent report level is ";
if(debugLog){
answer += "debug level.\n";
} else if(verbouseLog){
answer += "verbouse level.\n";
}else {
answer += "server level.\n";
}
answer += "\tReporting to the console is currently ";
if(isDemonizied()){
answer += "enabled.";
} else {
answer += "disabled.\n";
}
answer += "\tCurrent report directory is " + logDir.getAbsolutePath() + "\n";
return answer;
}
/* Statistic relevant section *
* it holds the number of the connected clients as well as the number
* of the (not) successful requests */
private int success = 0;
/**
* This method return the number of transactions, that were successfully completed.<br>
* A successful transaction means that there were no errors while executing it,
* it does not mean that the client request was approved.
* @return Return the number of successfully completed transactions.
*/
public int getSuccess(){
return success;
}
/**
* This method is used to denote that a transaction was successful. <br>
* A successful transaction means that there were no errors while executing it,
* it does not mean that the client request was approved.
*/
public synchronized void increaseSuccess(){
success++;
}
private int nosuccess = 0;
/**
* This method returns the number of transactions, during which execution an
* error was encountered.
* @return The number of not successfully completed transactions.
*/
public int getNoSuccess(){
return nosuccess;
}
/**
* This method is used to denote that a transaction was not successful.
*/
public synchronized void increaseNoSuccess(){
nosuccess++;
}
/* Connected clients */
private int currentlyConnectedClients = 0;
private int currentlyConnectedPC = 0; //Persistent Clients
private Object cccso = new Object(); //an object for sync purpose for the normal clients
private Object ccpcso = new Object(); //for the persistent clients
/**
* A getter for the currently connected non persistent clients.
* @return Returns the number of the currently connected non persistent clients.
*/
public int getCurrentlyConnectedClients(){
return currentlyConnectedClients;
}
/**
* A getter for the currently connected persistent clients.
* @return Returns the number of the currently connected persistent clients.
*/
public int getCurrentlyConnectedPC(){
return currentlyConnectedPC;
}
/**
* This method is used to increase the number of the currently
* connected non persistent clients.
* @return Returns <b>true</b> if we can accept a new non persistent client,
* returns <b>false</b> if the maximum allowed connected non persistent clients
* is reached and a connection should not be accepted.
*/
public boolean increaseCurrentlyConnectedClients(){
synchronized(cccso){
//maxAllowedConnectedClients = 0 means no limit, so accept all
if(maxAllowedConnectedClients == 0){
currentlyConnectedClients++;
return true;
} else if(currentlyConnectedClients >= maxAllowedConnectedClients)
return false;
currentlyConnectedClients++;
}
return true;
}
/**
* This method is used to decrease the number of the currently connected
* non persistent clients.
*/
public void decreaseCurrentlyConnectedClients(){
synchronized (cccso) {
currentlyConnectedClients--;
}
}
/**
* This method is used to increase the number of the currently
* connected persistent clients.
* @return Returns <b>true</b> if we can accept a new persistent client,
* returns <b>false</b> if the maximum allowed connected persistent clients
* is reached and a connection should not be accepted.
*/
public boolean increaseCurrentlyConnectedPC(){
synchronized (ccpcso) {
//if maxAllowedConnectedPC equals 0, then there is no limit
if(maxAllowedConnectedPC == 0){
currentlyConnectedPC++;
return true;
}
if(currentlyConnectedPC >= maxAllowedConnectedPC)
return false;
currentlyConnectedPC++;
}
return true;
}
/**
* This method is used to decrease the number of the currently connected
* persistent clients.
*/
public void decreaseCurrentlyConnectedPC(){
synchronized (ccpcso) {
currentlyConnectedPC--;
}
}
private int unique;
File uniqueFile;
/**
* This method returns the next unique number, which is allocated to
* each new connection.
* @return Returns the next unique number.
*/
public synchronized int getNextUnique(){
return ++unique;
}
/**
* This method returns the current unique value for the purpose of statistics.
* When getting the unique for the use in a server, logging, etc, please use the
* {@link #getNextUnique()} method.
* @return Returns the current unique value.
*/
public int getCurrentUnique(){
return unique;
}
/**
* This method is used to read the unique number from the unique file.
* The unique file is located in the configuration directory and has the
* name <b>.unique</b>. The method reads the first line and handles it as an
* Integer. If a problem occurs, then the system is to be stopped.
* @throws UniqueFileException This exception is thrown if the unique file was not created or could not be read.
* @throws ConfigurationUnacceptableValue This exception is thrown if the first line of the unique file is not a parsable integer.
*/
private void configUnique() throws UniqueFileException, ConfigurationUnacceptableValue, IOException{
uniqueFile = new File(configFile.getParentFile(),".unique");
if(uniqueFile == null){
report.reportErrorLog("localhost", "Unable to get the parent directory" +
" of the configuration file: " + uniqueFile.getParent());
System.exit(1);
}
if(!uniqueFile.exists()){
//the unique file does not exist. maybe first run?
report.reportDebugLog("localhost", "The unique file is missing, creating a new one: " + uniqueFile.getAbsolutePath());
try {
if(!uniqueFile.createNewFile()){
report.reportErrorLog("localhost","Unable to create the unique file.");
throw new UniqueFileException("Unable to create the unique file.");
} else {
return;
}
} catch (IOException e) {
report.reportVerbouseLog("locahost", e.getMessage());
throw new UniqueFileException("IOException hit while creating the unique file.");
}
}
if(!uniqueFile.canRead()){
report.reportErrorLog("localhost", "Unable to read the unique file: "
+ uniqueFile.getAbsolutePath());
throw new UniqueFileException("Unique file not readable.");
}
if(!uniqueFile.canWrite()){
report.reportErrorLog("localhost", "Unable to write to the unique file: "
+ uniqueFile.getAbsolutePath());
throw new UniqueFileException("Unique file not writable.");
}
BufferedReader br = null;
try {
br = new BufferedReader(new FileReader(uniqueFile));
if(!br.ready()){
report.reportErrorLog("localhost", "It seems that the unique file is empty: "
+ uniqueFile.getAbsolutePath());
throw new UniqueFileException(String.format("Unique file %s not readable.", uniqueFile.getAbsolutePath()));
}
unique = Integer.parseInt(br.readLine());
} catch (FileNotFoundException e) {
report.reportErrorLog("localhost", "The unique file was not found: "
+ uniqueFile.getAbsolutePath());
throw new UniqueFileException("The Unique file could not be found.");
} catch (IOException e){
report.reportErrorLog("localhost", "IOException hit while reading the unique file: "
+ uniqueFile.getAbsolutePath());
throw new UniqueFileException("IOException hit while reading the unique file.");
} catch (NumberFormatException e){
report.reportErrorLog("localhost", "The first line of the unique file is not a parsable integer: "
+ uniqueFile.getAbsolutePath());
throw new ConfigurationUnacceptableValue("The first line of the unique file is not a parsable integer.");
}
try {
br.close();
} catch (IOException e) {
report.reportErrorLog("localhost", "Unable to close the file reader for the" +
" unique file.");
throw e;
}
}
/**
* This method saves the current unique to the unique file. Note that the
* original file is truncated, thus only the new unique will be in the
* saved file.
* @throws IOException Throws an IOException if such is encountered during
* the execution of the method.
*/
private void finalizeUnique() throws IOException{
FileWriter write;
try {
write = new FileWriter(uniqueFile, false);
} catch(IOException e){
report.reportErrorLog("localhost", "IOException hit while opening the unique file for saving the new value.");
throw e;
}
write.write(unique +"\n"); //we need to convert unique to String
write.flush();
write.close();
}
/**
* This method checks if the unique value is acceptable (at least 1).
* @throws ConfigurationUnacceptableValue This exception is thrown if
* the unique value is not acceptable.
*/
private void checkUnique() throws ConfigurationUnacceptableValue{
if(unique < 1){
throw new ConfigurationUnacceptableValue(String.format(
"The unique value should be at least 1, but is %d", unique));
}
}
/**
* This method returns the unique value and unique absolute file path,
* formated as a String, which is used for example by
* the {@link #getEnviroment()} method.
* @return Returns the unique value and unique absolute file path,
* formated as a String.
*/
public String getEnvUnique(){
String answer = "Unique related information:\n";
answer += "\tThe current unique is: " + unique + ".\n";
answer += "\tThe unique file is: " + uniqueFile.getAbsolutePath() +"\n";
return answer;
}
/* Server ports, status, max allowed clients and so linger timeout */
private int port;
private static final int MAXPORT = 65*1024; //maximum port number, which is available
/**
* A getter for the port, on which the non persistent server is running.
* @return The port, on which the non persistent server is running
*/
public int getPort(){
return port;
}
private int persistentPort;
/**
* A getter for the port, on which the persistent server is running.
* @return The port, on which the persistent server is running
*/
public int getPersistentPort(){
return persistentPort;
}
private boolean useServer;
/**
* A getter for if the non persistent server is being used.
* @return Returns <b>true</b> if it is allowed to have a non persistent server
* running, else returns <b>false</b>.
*/
public boolean getUseServer(){
return useServer;
}
private boolean usePServer;
/**
* A getter for if the persistent server is being used.
* @return Returns <b>true</b> if it is allowed to have a persistent server
* running, else returns <b>false</b>.
*/
public boolean getUsePServer(){
return usePServer;
}
private boolean acceptNP;
/**
* A getter for if the persistent server is allowed to receive non persistent client connections.
* @return Returns <b>true</b> if persistent server is allowed to receive non persistent
* client connections, else returns <b>false</b>.
*/
public boolean getAcceptNP(){
return acceptNP;
}
private int solingertimeout;
/**
* A getter for the so linger timeout, which will be used from the non
* persistent server.
* @return the so linger timeout for the non persistent server.
*/
public int getSolingertimeout(){
return solingertimeout;
}
private int sotimeout;
/**
* A getter for the so timeout, which will be used from the non
* persistent server.
* @return the so timeout for the non persistent server.
*/
public int getSotimeout(){
return sotimeout;
}
private int maxAllowedConnectedClients;
/**
* A getter for the maximum allowed simultaneous non persistent connections.
* @return Returns the number of maximum allowed simultaneous non persistent connections.
*/
public int getMaxAllowedConnectedClients(){
return maxAllowedConnectedClients;
}
private int maxAllowedConnectedPC;
/**
* A getter for the maximum allowed simultaneous persistent connections.
* @return Returns the number of maximum allowed simultaneous persistent connections.
*/
public int getMaxAllowedConnectedPC(){
return maxAllowedConnectedPC;
}
/**
* Reads the configuration, which is relevant for the port section.
* @throws MissingConfigOptionException This exception is thrown when a
* variable is not set.
*/
private void configPort() throws MissingConfigOptionException{
String temp;
String whatarewelookingfor;
whatarewelookingfor = "port";
if ((temp = config.getProperty(whatarewelookingfor)) != null){
port = Integer.parseInt(temp);
} else {
throw new MissingConfigOptionException(String.format("Option %s missing.", whatarewelookingfor));
}
whatarewelookingfor = "np_server";
if ((temp = config.getProperty(whatarewelookingfor)) != null){
useServer = Boolean.parseBoolean(temp);
} else {
throw new MissingConfigOptionException(String.format("Option %s missing.", whatarewelookingfor));
}
whatarewelookingfor = "p_server_npc";
if ((temp = config.getProperty(whatarewelookingfor)) != null){
acceptNP = Boolean.parseBoolean(temp);
} else {
throw new MissingConfigOptionException(String.format("Option %s missing.", whatarewelookingfor));
}
whatarewelookingfor = "maxClients";
if ((temp = config.getProperty(whatarewelookingfor)) != null){
maxAllowedConnectedClients = Integer.parseInt(temp);
} else {
throw new MissingConfigOptionException(String.format("Option %s missing.", whatarewelookingfor));
}
whatarewelookingfor = "persistent_server";
if ((temp = config.getProperty(whatarewelookingfor)) != null){
usePServer = Boolean.parseBoolean(temp);
} else {
throw new MissingConfigOptionException(String.format("Option %s missing.", whatarewelookingfor));
}
whatarewelookingfor = "persistent_port";
if ((temp = config.getProperty(whatarewelookingfor)) != null) {
persistentPort = Integer.parseInt(temp);
} else {
throw new MissingConfigOptionException(String.format("Option %s missing.", whatarewelookingfor));
}
whatarewelookingfor = "maxPClients";
if ((temp = config.getProperty(whatarewelookingfor)) != null){
maxAllowedConnectedPC = Integer.parseInt(temp);
} else {
throw new MissingConfigOptionException(String.format("Option %s missing.", whatarewelookingfor));
}
whatarewelookingfor = "solingertimeout";
if((temp = config.getProperty(whatarewelookingfor)) != null){
solingertimeout = Integer.parseInt(temp);
} else {
throw new MissingConfigOptionException(String.format("Option %s missing.", whatarewelookingfor));
}
}
/**
* Checks if the setting for the port configuration, as well as the
* maximum allowed connected persistent and not persistent clients,
* so linger timeout and so timeout are acceptable.
* @throws ConfigurationUnacceptableValue This exception is thrown if
* a value, that is being set, is not acceptable.
*/
private void checkPort() throws ConfigurationUnacceptableValue{
if(solingertimeout < 1){
throw new ConfigurationUnacceptableValue(String.format("So linger timeout is" +
"set to %d, where it should be atleast 0. Aborting.", solingertimeout));
}
if(sotimeout < 1){
throw new ConfigurationUnacceptableValue(String.format("So timeout is" +
"set to %d, where it should be atleast 0. Aborting.", sotimeout));
}
if(useServer){
if(port < 1 && port > MAXPORT){
throw new ConfigurationUnacceptableValue(String.format("The port given for " +
"the non persistent server is %d, which is more than the " +
"allowed maximum of %d", port, MAXPORT));
}
if(maxAllowedConnectedClients < 0){
throw new ConfigurationUnacceptableValue(String.format("The maximum allowed connected clients " +
"is %d, where it is allowed to be minimum 0.", maxAllowedConnectedClients));
}
}
if(usePServer){
if(persistentPort < 1 && persistentPort > MAXPORT){
throw new ConfigurationUnacceptableValue(String.format("The port given for " +
"the persistent server is %d, which is more than the " +
"allowed maximum of %d", persistentPort, MAXPORT));
}
if(maxAllowedConnectedPC < 0){
throw new ConfigurationUnacceptableValue(String.format("The maximum allowed connected persistent clients " +
"is %d, where it is allowed to be minimum 0.", maxAllowedConnectedPC));
}
}
if(useServer && usePServer){
if(port == persistentPort){
throw new ConfigurationUnacceptableValue(String.format("The persistent server and the non persistent one are" +
"expected to run on the same port %d, but this is not possible. Aborting", port));
}
if(acceptNP){
throw new ConfigurationUnacceptableValue("You are not allowed to have both servers running and" +
"still allow the persistent one to recieve non persistent connections.");
}
}
}
/**
* This method returns a String of the port related options, such as
* ports on which the server(s) run and the value of the so linger timeout.
* This output is included in the {@link #getEnviroment()} method.
* @return Returns a String of the port related options.
*/
public String getEnvPort(){
String answer = "Server related information:\n";
if(useServer){
answer += String.format("\tThe non persistent server is running on port %d.\n" +
"\tMaximum allowed connected non persistent clients are %d.\n" +
"\tCurrently connected clients are %d.\n", port, maxAllowedConnectedClients, currentlyConnectedClients);
}
if(usePServer){
answer += String.format("\tThe non persistent server is running on port %d.\n" +
"\tMaximum allowed connected persistent clients are %d.\n" +
"\tCurrently connected clients are %d.\n", port, maxAllowedConnectedPC, currentlyConnectedPC);
}
answer += String.format("\tSotimeout is: %d.\n" +
"\tSolingertimeout is: %d.\n", sotimeout, solingertimeout);
return answer;
}
/* KeyNote & MyKeynote section */
private File pathToKeynote;
/**
* A getter for the path to the keynote executable.
* @return Return the the path to the keynote executable.
*/
public File getPathToKeynote(){
return pathToKeynote;
}
private File pathToKNLib;
/**
* A getter for the path to the keynote library.
* @return Return the the path to the keynote library.
*/
public File getPathToKNLib(){
return pathToKNLib;
}
private File publicKeyDir;
/**
* A getter for the path to the directory, where all public keys are.
* @return Return the the path to the directory, where all public keys are.
*/
public File getPublicKeyDir(){
return publicKeyDir;
}
private File privateKeyDir;
/**
* A getter for the path to the directory, where all private keys are.
* @return Return the the path to the directory, where all private keys are.
*/
public File getPrivateKeyDir(){
return privateKeyDir;
}
private File nokeyfile;
/**
* A getter for the path to the directory, where all public keys are.
* @return Return the the path to the directory, where all public keys are.
*/
public File getNoKeyFile(){
return nokeyfile;
}
private boolean useCL;
/**
* This is a getter for the useCL
* @return Returns <b>true</b> if we should report to the command line,
* else returns <b>false</b>.
*/
public boolean getUseCL(){
return useCL;
}
private File tempDir;
/**
* This is a getter for the temporary directory.
* @return Returns where the temp directory is.
*/
public File getTempDir(){
return tempDir;
}
/**
* Reads the configuration, which is relevant for the keynote section.
* @throws MissingConfigOptionException This exception is thrown when a
* variable is not set.
*/
private void configKNMKN() throws MissingConfigOptionException{
String temp;
String whatarewelookingfor;
whatarewelookingfor = "pathToKeyNote";
if ((temp = config.getProperty(whatarewelookingfor)) != null) {
pathToKeynote = new File(temp);
} else {
throw new MissingConfigOptionException(String.format("Option %s missing.", whatarewelookingfor));
}
/*whatarewelookingfor = "pathToKNLib";
if ((temp = config.getProperty(whatarewelookingfor)) != null) {
pathToKNLib = new File(temp);
} else {
throw new MissingConfigOptionException(String.format("Option %s missing.", whatarewelookingfor));
}
*/
whatarewelookingfor = "publicKeyDir";
if ((temp = config.getProperty(whatarewelookingfor)) != null) {
publicKeyDir = new File(temp);
nokeyfile = new File(publicKeyDir,"nokey" + FormatConstants.KEYFORMAT);
} else {
throw new MissingConfigOptionException(String.format("Option %s missing.", whatarewelookingfor));
}
whatarewelookingfor = "privateKeyDir";
if ((temp = config.getProperty(whatarewelookingfor)) != null) {
privateKeyDir = new File(temp);
} else {
throw new MissingConfigOptionException(String.format("Option %s missing.", whatarewelookingfor));
}
whatarewelookingfor = "useCL";
if ((temp = config.getProperty(whatarewelookingfor)) != null) {
useCL = Boolean.parseBoolean(temp);
} else {
throw new MissingConfigOptionException(String.format("Option %s missing.", whatarewelookingfor));
}
whatarewelookingfor = "tempDir";
if ((temp = config.getProperty(whatarewelookingfor)) != null) {
tempDir = new File(temp);
} else {
throw new MissingConfigOptionException(String.format("Option %s missing.", whatarewelookingfor));
}
}
/**
* Checks if the setting for the keynote relevant configuration is acceptable.
* @throws ConfigurationUnacceptableValue This exception is thrown if
* a value, that is being set, is not acceptable.
* @throws FileNotFoundException This exception is thrown if a file, or directory
* was not found.
*/
private void checkKNMKN() throws FileNotFoundException, ConfigurationUnacceptableValue{
if(useCL){
if(!pathToKeynote.exists())
throw new FileNotFoundException(String.format(
"The file %s was not found!", pathToKeynote.getAbsoluteFile()));
if(!pathToKeynote.canExecute())
throw new ConfigurationUnacceptableValue("The given Keynote file is not executable.");
} else {
throw new ConfigurationUnacceptableValue("The JNI keynote is not ready yet.");
}
}
/**
* This method returns a String of the keynote related options, such as
* are we using the CLI or the JNI option, the path to the executable/library, etc.
* This output is included in the {@link #getEnviroment()} method.
* @return Returns a String of the keynote related options.
*/
public String getEnvKNMKN(){
String answer = "KeyNote/MyKeyNote related information:\n";
answer += "\tCurrently using the ";
if(useCL){
answer += "command line KeyNote.\n";
answer += "\tThe executable is situated in " + pathToKeynote.getAbsolutePath() + ".\n" ;
} else {
answer += "KeyNote library.\n";
answer += "\tThe library is situated in " + pathToKNLib.getAbsolutePath() + ".\n" ;
}
answer += "\tThe public key directory is " + publicKeyDir.getAbsolutePath() + ".\n";
answer += "\tThe private key directory is " + privateKeyDir.getAbsolutePath() + ".\n";
answer += "\tThe no key file is " + nokeyfile.getAbsolutePath() + ".\n";
answer += "\tThe temporary directory is " + tempDir.getAbsolutePath() +".\n";
return answer;
}
}