com.delcyon.capo.Configuration.java Source code

Java tutorial

Introduction

Here is the source code for com.delcyon.capo.Configuration.java

Source

/**
Copyright (C) 2012  Delcyon, Inc.
    
This program is free software: you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation, either version 3 of the License, or
(at your option) any later version.
    
This program 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 General Public License for more details.
    
You should have received a copy of the GNU General Public License
along with this program.  If not, see <http://www.gnu.org/licenses/>.
 */
package com.delcyon.capo;

import java.io.File;
import java.io.FileOutputStream;
import java.util.Map.Entry;
import java.util.Set;
import java.util.Vector;
import java.util.concurrent.ConcurrentHashMap;
import java.util.logging.Level;
import java.util.prefs.BackingStoreException;
import java.util.prefs.Preferences;

import javax.xml.parsers.DocumentBuilder;
import javax.xml.parsers.DocumentBuilderFactory;
import javax.xml.transform.OutputKeys;
import javax.xml.transform.Transformer;
import javax.xml.transform.TransformerFactory;
import javax.xml.transform.dom.DOMSource;
import javax.xml.transform.stream.StreamResult;

import org.apache.commons.cli.CommandLine;
import org.apache.commons.cli.CommandLineParser;
import org.apache.commons.cli.GnuParser;
import org.apache.commons.cli.HelpFormatter;
import org.apache.commons.cli.OptionBuilder;
import org.apache.commons.cli.Options;
import org.w3c.dom.Document;
import org.w3c.dom.Element;
import org.w3c.dom.NodeList;

import com.delcyon.capo.CapoApplication.Location;
import com.delcyon.capo.annotations.DefaultDocumentProvider;
import com.delcyon.capo.annotations.DirectoyProvider;
import com.delcyon.capo.preferences.Preference;
import com.delcyon.capo.preferences.PreferenceProvider;
import com.delcyon.capo.server.CapoServer;
import com.delcyon.capo.xml.XPath;
import com.delcyon.capo.xml.cdom.CDocument;

/**
 * @author jeremiah
 */
@DirectoyProvider(preferenceName = "CONFIG_DIR", preferences = Configuration.PREFERENCE.class, canUseRepository = false)
@DefaultDocumentProvider(directoryPreferenceName = "CONFIG_DIR", preferences = Configuration.PREFERENCE.class, name = "config.xml,repository.xml")
public class Configuration {

    private static final String CONFIG_FILENAME = "config.xml";

    public enum PREFERENCE implements Preference {
        RETAIN("r", "retain", "overwrite values in configuration file with option from command line", null,
                null), DISABLE_CONFIG_AUTOSYNC("DISABLE_CONFIG_AUTOSYNC", "DISABLE_CONFIG_AUTOSYNC",
                        "Turns off Automaticaly syncing new preferences to filesystem or creating default directories. Useful for testing only!",
                        null, null), PORT("port", "port", "port to listen on", "2442",
                                new String[] { "portNumber" }), SERVER_PORT("sp", "SERVER_PORT",
                                        "server port to connect to. default 2442", "2442",
                                        new String[] { "portNumber" }), SERVER_LIST("sl", "SERVER_LIST",
                                                "server addresses. comma seperated. default 127.0.0.1", "127.0.0.1",
                                                new String[] { "address" }), HELP("h", "help", "print usage", null,
                                                        null), BUFFER_SIZE("bs", "BUFFER_SIZE",
                                                                "Stream buffer size, default is 4096. ", "4096",
                                                                new String[] { "int" }), RESOURCE_MANAGER("rm",
                                                                        "RESOURCE_MANAGER",
                                                                        "class to use as a resource manager (default is com.delcyon.capo.resourcemanager.ResourceManager)",
                                                                        "com.delcyon.capo.resourcemanager.ResourceManager",
                                                                        new String[] {
                                                                                "class name" }), DATA_MANAGER_ARGUMENTS(
                                                                                        "dma",
                                                                                        "DATA_MANAGER_ARGUMENTS",
                                                                                        "arguments to pass to data manager, like location of the file store or url of an xml server",
                                                                                        "capo-data",
                                                                                        new String[] {
                                                                                                "uri" }), CAPO_DIR(
                                                                                                        "CAPO_DIR",
                                                                                                        "CAPO_DIR",
                                                                                                        "main capo directory on local machine",
                                                                                                        "capo",
                                                                                                        new String[] {
                                                                                                                "dir" }), CONFIG_DIR(
                                                                                                                        "CONFIG_DIR",
                                                                                                                        "CONFIG_DIR",
                                                                                                                        "directory where main config is stored, relative to root data dir",
                                                                                                                        "config",
                                                                                                                        new String[] {
                                                                                                                                "dir" }), STATUS_DIR(
                                                                                                                                        "STATUS_DIR",
                                                                                                                                        "STATUS_DIR",
                                                                                                                                        "directory where status information is stored, relative to root data dir",
                                                                                                                                        "status",
                                                                                                                                        new String[] {
                                                                                                                                                "dir" }), WEB_DIR(
                                                                                                                                                        "WEB_DIR",
                                                                                                                                                        "WEB_DIR",
                                                                                                                                                        "directory where public web accessable files are stored, relative to root data dir",
                                                                                                                                                        "public",
                                                                                                                                                        new String[] {
                                                                                                                                                                "dir" }), MODULE_DIR(
                                                                                                                                                                        "MODULE_DIR",
                                                                                                                                                                        "MODULE_DIR",
                                                                                                                                                                        "directory where modules are stored, relative to root data dir",
                                                                                                                                                                        "modules",
                                                                                                                                                                        new String[] {
                                                                                                                                                                                "dir" }), RESOURCE_DIR(
                                                                                                                                                                                        "RESOURCE_DIR",
                                                                                                                                                                                        "RESOURCE_DIR",
                                                                                                                                                                                        "directory where misc resources are stored, relative to root data dir",
                                                                                                                                                                                        "resources",
                                                                                                                                                                                        new String[] {
                                                                                                                                                                                                "dir" }), CONTROLLER_DIR(
                                                                                                                                                                                                        "CONTROLLER_DIR",
                                                                                                                                                                                                        "CONTROLLER_DIR",
                                                                                                                                                                                                        "directory where controller scripts are stored, relative to root data dir",
                                                                                                                                                                                                        "controller",
                                                                                                                                                                                                        new String[] {
                                                                                                                                                                                                                "dir" }), RESPONSE_DIR(
                                                                                                                                                                                                                        "RESPONSE_DIR",
                                                                                                                                                                                                                        "RESPONSE_DIR",
                                                                                                                                                                                                                        "directory where responses to requests are stored, relative to root data dir, server only",
                                                                                                                                                                                                                        "responses",
                                                                                                                                                                                                                        new String[] {
                                                                                                                                                                                                                                "dir" }), KEYSTORE(
                                                                                                                                                                                                                                        "KEYSTORE",
                                                                                                                                                                                                                                        "KEYSTORE",
                                                                                                                                                                                                                                        "location of java keystore default = keystore",
                                                                                                                                                                                                                                        "keystore",
                                                                                                                                                                                                                                        new String[] {
                                                                                                                                                                                                                                                "file" }), KEYSTORE_PASSWORD(
                                                                                                                                                                                                                                                        "KEYSTORE_PASSWORD",
                                                                                                                                                                                                                                                        "KEYSTORE_PASSWORD",
                                                                                                                                                                                                                                                        "password for java keystore. default is 'password'",
                                                                                                                                                                                                                                                        "password",
                                                                                                                                                                                                                                                        new String[] {
                                                                                                                                                                                                                                                                "password" }), CLIENT_VERIFICATION_PASSWORD(
                                                                                                                                                                                                                                                                        "CLIENT_VERIFICATION_PASSWORD",
                                                                                                                                                                                                                                                                        "CLIENT_VERIFICATION_PASSWORD",
                                                                                                                                                                                                                                                                        "Initial password for unknown clients to use. If left blank a random password will be generated for each client. default is blank",
                                                                                                                                                                                                                                                                        "",
                                                                                                                                                                                                                                                                        new String[] {
                                                                                                                                                                                                                                                                                "password" }), MODE(
                                                                                                                                                                                                                                                                                        "m",
                                                                                                                                                                                                                                                                                        "MODE",
                                                                                                                                                                                                                                                                                        "mode to run capo in client, server, hybrid. default 'client'",
                                                                                                                                                                                                                                                                                        "client",
                                                                                                                                                                                                                                                                                        new String[] {
                                                                                                                                                                                                                                                                                                "mode" }), CLIENT_MODE(
                                                                                                                                                                                                                                                                                                        "cm",
                                                                                                                                                                                                                                                                                                        "CLIENT_MODE",
                                                                                                                                                                                                                                                                                                        "what kind of client connection to use, persistant or dynamic. default is dynamic",
                                                                                                                                                                                                                                                                                                        "dynamic",
                                                                                                                                                                                                                                                                                                        new String[] {
                                                                                                                                                                                                                                                                                                                "client_mode" }), STARTUP_SCRIPT(
                                                                                                                                                                                                                                                                                                                        "STARTUP_SCRIPT",
                                                                                                                                                                                                                                                                                                                        "STARTUP_SCRIPT",
                                                                                                                                                                                                                                                                                                                        "Capo formatted XML file, relative to CONFIG_DIR, containing controls to run at startup, before server becomes available.",
                                                                                                                                                                                                                                                                                                                        "startup.xml",
                                                                                                                                                                                                                                                                                                                        new String[] {
                                                                                                                                                                                                                                                                                                                                "file" }), UPDATE_SCRIPT(
                                                                                                                                                                                                                                                                                                                                        "UPDATE_SCRIPT",
                                                                                                                                                                                                                                                                                                                                        "UPDATE_SCRIPT",
                                                                                                                                                                                                                                                                                                                                        "Capo formatted XML file, relative to CONFIG_DIR, containing controls to run an update, before client control processing.",
                                                                                                                                                                                                                                                                                                                                        "update.xml",
                                                                                                                                                                                                                                                                                                                                        new String[] {
                                                                                                                                                                                                                                                                                                                                                "file" }), LOGGING_LEVEL(
                                                                                                                                                                                                                                                                                                                                                        "l",
                                                                                                                                                                                                                                                                                                                                                        "LOGGING_LEVEL",
                                                                                                                                                                                                                                                                                                                                                        "Java Logging level to use. Can be Standard Java Logging Name, or a number",
                                                                                                                                                                                                                                                                                                                                                        "INFO",
                                                                                                                                                                                                                                                                                                                                                        new String[] {
                                                                                                                                                                                                                                                                                                                                                                "level" }),;

        private String option;
        private String longOption;
        private boolean hasArgument;
        private String description;
        private String defaultValue;
        private String[] arguments;

        PREFERENCE(String option, String longOption, String description, String defaultValue, String[] arguments) {
            this.option = option;
            this.longOption = longOption;
            if (arguments != null && arguments.length > 0) {
                this.hasArgument = true;
            } else {
                this.hasArgument = false;
            }
            this.description = description;
            this.defaultValue = defaultValue;
            this.arguments = arguments;
        }

        @Override
        public String toString() {
            return getLongOption();
        }

        public String getOption() {
            return option;
        }

        public String getLongOption() {
            return longOption;
        }

        public boolean hasArgument() {
            return hasArgument;
        }

        public String getDescription() {
            return description;
        }

        public String getDefaultValue() {
            //see if there is a default value stored in the java preferences system, 
            //and use that otherwise use the default value if any.           
            return Preferences.systemNodeForPackage(CapoApplication.getApplication().getClass()).get(longOption,
                    defaultValue);
        }

        public String[] getArguments() {
            return arguments;
        }

        @Override
        public Location getLocation() {
            return Location.BOTH;
        }

    }

    private CommandLine commandLine;
    private Options options;
    private Document configDocument;
    private DocumentBuilder documentBuilder;
    private File capoConfigFile;
    private ConcurrentHashMap<String, String> preferenceValueHashMap = new ConcurrentHashMap<String, String>();
    private ConcurrentHashMap<String, Preference> preferenceHashMap = new ConcurrentHashMap<String, Preference>();
    private boolean disableAutoSync;

    public Configuration() throws Exception {
        this(new String[] {});
    }

    @SuppressWarnings({ "unchecked", "static-access" })
    public Configuration(String... programArgs) throws Exception {

        DocumentBuilderFactory documentBuilderFactory = DocumentBuilderFactory.newInstance();
        documentBuilderFactory.setNamespaceAware(true);
        documentBuilder = documentBuilderFactory.newDocumentBuilder();

        options = new Options();
        // the enum this is a little complicated, but it gives us a nice
        // centralized place to put all of the system parameters
        // and lets us iterate of the list of options and preferences
        PREFERENCE[] preferences = PREFERENCE.values();
        for (PREFERENCE preference : preferences) {
            // not the most elegant, but there is no default constructor, but
            // the has arguments value is always there
            OptionBuilder optionBuilder = OptionBuilder.hasArg(preference.hasArgument);
            if (preference.hasArgument == true) {
                String[] argNames = preference.arguments;
                for (String argName : argNames) {
                    optionBuilder = optionBuilder.withArgName(argName);
                }
            }

            optionBuilder = optionBuilder.withDescription(preference.getDescription());
            optionBuilder = optionBuilder.withLongOpt(preference.getLongOption());
            options.addOption(optionBuilder.create(preference.getOption()));

            preferenceHashMap.put(preference.toString(), preference);
        }

        //add dynamic options

        Set<String> preferenceProvidersSet = CapoApplication.getAnnotationMap()
                .get(PreferenceProvider.class.getCanonicalName());
        if (preferenceProvidersSet != null) {
            for (String className : preferenceProvidersSet) {
                Class preferenceClass = Class.forName(className).getAnnotation(PreferenceProvider.class)
                        .preferences();
                if (preferenceClass.isEnum()) {
                    Object[] enumObjects = preferenceClass.getEnumConstants();
                    for (Object enumObject : enumObjects) {

                        Preference preference = (Preference) enumObject;
                        //filter out any preferences that don't belong on this server or client.
                        if (preference.getLocation() != Location.BOTH) {
                            if (CapoApplication.isServer() == true && preference.getLocation() == Location.CLIENT) {
                                continue;
                            } else if (CapoApplication.isServer() == false
                                    && preference.getLocation() == Location.SERVER) {
                                continue;
                            }
                        }
                        preferenceHashMap.put(preference.toString(), preference);
                        boolean hasArgument = false;
                        if (preference.getArguments() == null || preference.getArguments().length == 0) {
                            hasArgument = false;
                        } else {
                            hasArgument = true;
                        }

                        OptionBuilder optionBuilder = OptionBuilder.hasArg(hasArgument);
                        if (hasArgument == true) {
                            String[] argNames = preference.getArguments();
                            for (String argName : argNames) {
                                optionBuilder = optionBuilder.withArgName(argName);
                            }
                        }

                        optionBuilder = optionBuilder.withDescription(preference.getDescription());
                        optionBuilder = optionBuilder.withLongOpt(preference.getLongOption());
                        options.addOption(optionBuilder.create(preference.getOption()));
                    }

                }
            }
        }

        // create parser
        CommandLineParser commandLineParser = new GnuParser();
        this.commandLine = commandLineParser.parse(options, programArgs);

        Preferences systemPreferences = Preferences
                .systemNodeForPackage(CapoApplication.getApplication().getClass());
        String capoDirString = null;
        while (true) {
            capoDirString = systemPreferences.get(PREFERENCE.CAPO_DIR.longOption, null);
            if (capoDirString == null) {

                systemPreferences.put(PREFERENCE.CAPO_DIR.longOption, PREFERENCE.CAPO_DIR.defaultValue);
                capoDirString = PREFERENCE.CAPO_DIR.defaultValue;
                try {
                    systemPreferences.sync();
                } catch (BackingStoreException e) {
                    //e.printStackTrace();            
                    if (systemPreferences.isUserNode() == false) {
                        System.err.println("Problem with System preferences, trying user's");
                        systemPreferences = Preferences
                                .userNodeForPackage(CapoApplication.getApplication().getClass());
                        continue;
                    } else //just bail out
                    {
                        throw e;
                    }

                }
            }
            break;
        }

        disableAutoSync = hasOption(PREFERENCE.DISABLE_CONFIG_AUTOSYNC);

        File capoDirFile = new File(capoDirString);
        if (capoDirFile.exists() == false) {
            if (disableAutoSync == false) {
                capoDirFile.mkdirs();
            }
        }
        File configDir = new File(capoDirFile, PREFERENCE.CONFIG_DIR.defaultValue);
        if (configDir.exists() == false) {
            if (disableAutoSync == false) {
                configDir.mkdirs();
            }
        }

        if (disableAutoSync == false) {
            capoConfigFile = new File(configDir, CONFIG_FILENAME);
            if (capoConfigFile.exists() == false) {

                Document configDocument = CapoApplication.getDefaultDocument("config.xml");

                FileOutputStream configFileOutputStream = new FileOutputStream(capoConfigFile);
                TransformerFactory tFactory = TransformerFactory.newInstance();
                Transformer transformer = tFactory.newTransformer();
                transformer.setOutputProperty(OutputKeys.INDENT, "yes");
                transformer.transform(new DOMSource(configDocument), new StreamResult(configFileOutputStream));
                configFileOutputStream.close();
            }

            configDocument = documentBuilder.parse(capoConfigFile);
        } else //going memory only, because of disabled auto sync
        {
            configDocument = CapoApplication.getDefaultDocument("config.xml");
        }
        if (configDocument instanceof CDocument) {
            ((CDocument) configDocument).setSilenceEvents(true);
        }
        loadPreferences();
        preferenceValueHashMap.put(PREFERENCE.CAPO_DIR.longOption, capoDirString);
        //print out preferences
        //this also has the effect of persisting all of the default values if a values doesn't already exist
        for (PREFERENCE preference : preferences) {
            if (getValue(preference) != null) {
                CapoApplication.logger.log(Level.CONFIG, preference.longOption + "='" + getValue(preference) + "'");
            }
        }

        CapoApplication.logger.setLevel(Level.parse(getValue(PREFERENCE.LOGGING_LEVEL)));
    }

    public boolean hasOption(Preference preference) {
        return commandLine.hasOption(preference.getOption());
    }

    /**
     * command line values take precedence over saved preferences 
     * @param preference
     * @return
     */
    public String getValue(Preference preference) {
        if (commandLine.hasOption(preference.getOption())) {
            //if the retain flag is specified persist the option or if the option exists and there is a default value, but no value in the preferences
            if (hasOption(PREFERENCE.RETAIN) || (getPref(preference.getLongOption(), null) == null
                    && preference.getDefaultValue() != null)) {
                putPref(preference.getLongOption(), commandLine.getOptionValue(preference.getOption()));
                try {
                    sync();
                } catch (BackingStoreException e) {
                    e.printStackTrace();
                }
            }
            return commandLine.getOptionValue(preference.getOption());
        } else {
            //if there isn't a preference set and there is a default value then store the default in the preferences
            //this is how we save the initial configuration
            if (getPref(preference.getLongOption(), null) == null && preference.getDefaultValue() != null) {
                putPref(preference.getLongOption(), preference.getDefaultValue());
                try {
                    sync();
                } catch (BackingStoreException e) {
                    e.printStackTrace();
                }
            }
            return getPref(preference.getLongOption(), null);
        }
    }

    public void printHelp() {
        HelpFormatter formatter = new HelpFormatter();
        formatter.setWidth(200);
        formatter.printHelp("CapoServer", options);
    }

    public int getIntValue(Preference preference) {
        return Integer.parseInt(getValue(preference));

    }

    public boolean getBooleanValue(Preference preference) {
        return Boolean.parseBoolean(getValue(preference));

    }

    public long getLongValue(Preference preference) {
        return Long.parseLong(getValue(preference));
    }

    /**
     * Encapsulation of XML preferences
     * @param key
     * @param defaultValue
     * @return null, on no value
     * @throws BackingStoreException 
     */
    private String getPref(String key, String defaultValue) {
        String returnValue = defaultValue;
        if (preferenceValueHashMap.containsKey(key)) {
            returnValue = preferenceValueHashMap.get(key);
        }
        return returnValue;
    }

    private void putPref(String key, String value) {
        preferenceValueHashMap.put(key, value);
    }

    /**
     * Encapsulation of XML preferences
     * @param key
     * @param value
     * @throws BackingStoreException 
     */
    private void putXmlPref(String key, String value) throws BackingStoreException {
        try {
            synchronized (configDocument) {

                Element entryElement = (Element) XPath.selectSingleNode(configDocument,
                        "//entry[@key = '" + key + "']");
                if (entryElement != null) {
                    entryElement.setAttribute("value", value);
                } else {
                    entryElement = configDocument.createElementNS(null, "entry");
                    entryElement.setAttribute("key", key);
                    entryElement.setAttribute("value", value);
                    configDocument.getDocumentElement().appendChild(entryElement);
                }
            }
        } catch (Exception exception) {
            throw new BackingStoreException(exception.getMessage());
        }
    }

    private synchronized void sync() throws BackingStoreException {

        try {
            Set<Entry<String, String>> preferenceEntrySet = preferenceValueHashMap.entrySet();
            for (Entry<String, String> entry : preferenceEntrySet) {
                //do not persist certain preferences
                if (entry.getKey().equals(PREFERENCE.CLIENT_VERIFICATION_PASSWORD.getLongOption())
                        && CapoApplication.isServer() == false) {
                    continue;
                } else {
                    putXmlPref(entry.getKey(), entry.getValue());
                }

            }
            if (disableAutoSync == false) {
                FileOutputStream configFileOutputStream = new FileOutputStream(capoConfigFile);
                TransformerFactory tFactory = TransformerFactory.newInstance();
                Transformer transformer = tFactory.newTransformer();
                transformer.setOutputProperty(OutputKeys.INDENT, "yes");
                transformer.transform(new DOMSource(configDocument), new StreamResult(configFileOutputStream));
                configFileOutputStream.close();
            }
        } catch (Exception exception) {
            CapoApplication.logger.log(Level.WARNING, "Couldn't sync config file", exception);
            throw new BackingStoreException(exception.getMessage());
        }

    }

    private void loadPreferences() throws Exception {
        NodeList entryNodeList = XPath.selectNodes(configDocument, "//entry");
        for (int nodeIndex = 0; nodeIndex < entryNodeList.getLength(); nodeIndex++) {
            Element entryElement = (Element) entryNodeList.item(nodeIndex);
            preferenceValueHashMap.put(entryElement.getAttribute("key"), entryElement.getAttribute("value"));
        }
    }

    @SuppressWarnings("unchecked")
    public Preference[] getDirectoryPreferences() {
        boolean isServer = CapoApplication.getApplication() instanceof CapoServer;
        Vector<Preference> preferenceVector = new Vector<Preference>();
        Set<String> directoryProvidersSet = CapoApplication.getAnnotationMap()
                .get(DirectoyProvider.class.getCanonicalName());
        if (directoryProvidersSet != null) {
            for (String className : directoryProvidersSet) {
                try {
                    Location location = Class.forName(className).getAnnotation(DirectoyProvider.class).location();
                    Class preferenceClass = Class.forName(className).getAnnotation(DirectoyProvider.class)
                            .preferences();
                    String preferenceName = Class.forName(className).getAnnotation(DirectoyProvider.class)
                            .preferenceName();
                    if (location == Location.BOTH) {
                        preferenceVector.add((Preference) Enum.valueOf(preferenceClass, preferenceName));
                    } else if (isServer == true && location == Location.SERVER) {
                        preferenceVector.add((Preference) Enum.valueOf(preferenceClass, preferenceName));
                    } else if (isServer == false && location == Location.CLIENT) {
                        preferenceVector.add((Preference) Enum.valueOf(preferenceClass, preferenceName));
                    }
                } catch (ClassNotFoundException classNotFoundException) {
                    CapoApplication.logger.log(Level.WARNING, "Error getting directory providers",
                            classNotFoundException);
                }
            }
        }
        return preferenceVector.toArray(new Preference[] {});
    }

    public DefaultDocumentProvider[] getDefaultDocumentProviders() {
        Vector<DefaultDocumentProvider> defaultDocumentProviderVector = new Vector<DefaultDocumentProvider>();
        Set<String> defaultDocumentProviderSet = CapoApplication.getAnnotationMap()
                .get(DefaultDocumentProvider.class.getCanonicalName());
        for (String className : defaultDocumentProviderSet) {
            try {
                defaultDocumentProviderVector
                        .add(Class.forName(className).getAnnotation(DefaultDocumentProvider.class));
            } catch (ClassNotFoundException classNotFoundException) {
                CapoApplication.logger.log(Level.WARNING, "Error getting document providers",
                        classNotFoundException);
            }

        }
        return defaultDocumentProviderVector.toArray(new DefaultDocumentProvider[] {});
    }

    public Preference getPreference(String preferenceName) {
        return preferenceHashMap.get(preferenceName);
    }

    public void setValue(Preference preference, String value) {
        putPref(preference.getLongOption(), value);
        try {
            sync();
        } catch (BackingStoreException e) {
            e.printStackTrace();
        }

    }

}