/src/java/org/eclim/plugin/core/preference/Preferences.java
Java | 431 lines | 248 code | 49 blank | 134 comment | 51 complexity | e60be9107647b97529bf33b74755e683 MD5 | raw file
- /**
- * Copyright (C) 2005 - 2009 Eric Van Dewoestine
- *
- * 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 org.eclim.plugin.core.preference;
- import java.util.ArrayList;
- import java.util.HashMap;
- import java.util.Map;
- import org.eclim.Services;
- import org.eclim.logging.Logger;
- import org.eclipse.core.resources.IProject;
- import org.eclipse.core.resources.ProjectScope;
- import org.eclipse.core.runtime.preferences.IEclipsePreferences;
- import org.eclipse.core.runtime.preferences.InstanceScope;
- import org.eclipse.core.runtime.preferences.IScopeContext;
- /**
- * Class for handling preferences for eclim.
- *
- * This class uses the word 'option' for a built in eclipse options (like the
- * jdt compiler source version), and the word 'preference' for eclim provided
- * key values.
- *
- * @author Eric Van Dewoestine
- */
- public class Preferences
- {
- private static final Logger logger = Logger.getLogger(Preferences.class);
- public static final String USERNAME_PREFERENCE = "org.eclim.user.name";
- public static final String USEREMAIL_PREFERENCE = "org.eclim.user.email";
- public static final String PROJECT_COPYRIGHT_PREFERENCE =
- "org.eclim.project.copyright";
- private static final String NODE_NAME = "org.eclim";
- private static final String CORE = "core";
- private static Preferences instance = new Preferences();
- private static Map<String, OptionHandler> optionHandlers =
- new HashMap<String, OptionHandler>();
- private Map<String, Preference> preferences = new HashMap<String, Preference>();
- private Map<String, Option> options = new HashMap<String, Option>();
- // cache preference values
- private Map<String, Map<String, String>> preferenceValues =
- new HashMap<String, Map<String, String>>();
- // cache option values
- private Map<String, Map<String, String>> optionValues =
- new HashMap<String, Map<String, String>>();
- private Preferences() {}
- /**
- * Gets the Preferences instance.
- *
- * @return The Preferences singleton.
- */
- public static Preferences getInstance()
- {
- return instance;
- }
- /**
- * Adds the supplied OptionHandler to manage eclipse options with the
- * specified prefix.
- *
- * @param prefix The prefix.
- * @param handler The OptionHandler.
- * @return The OptionHandler.
- */
- public static OptionHandler addOptionHandler(
- String prefix, OptionHandler handler)
- {
- optionHandlers.put(prefix, handler);
- return handler;
- }
- /**
- * Adds an eclim preference to be made available.
- *
- * @param preference The preference to add.
- */
- public void addPreference(Preference preference)
- {
- preferences.put(preference.getName(), preference);
- preferenceValues.clear();
- }
- /**
- * Gets an array of configured preference names.
- *
- * @return Array of preference names.
- */
- public String[] getPreferenceNames()
- {
- return preferences.keySet().toArray(new String[0]);
- }
- /**
- * Adds an eclipse option to be configurable via eclim.
- *
- * @param option The option.
- */
- public void addOption(Option option)
- {
- options.put(option.getName(), option);
- optionValues.clear();
- }
- /**
- * Gets an array of configured option names.
- *
- * @return Array of option names.
- */
- public String[] getOptionNames()
- {
- return options.keySet().toArray(new String[0]);
- }
- /**
- * Clear cached option/preference values.
- *
- * @param project The project.
- */
- public void clearProjectValueCache(IProject project)
- {
- preferenceValues.remove(project.getName());
- optionValues.remove(project.getName());
- }
- /**
- * Gets a map of all options/preferences.
- *
- * @param project The current project.
- * @return A map of key values.
- */
- public Map<String, String> getValues(IProject project)
- throws Exception
- {
- // eclim preferences
- Map<String, String> prefVals = preferenceValues.get(project.getName());
- if(prefVals == null){
- prefVals = new HashMap<String, String>();
- preferenceValues.put(project.getName(), prefVals);
- IScopeContext context = new InstanceScope();
- // global
- IEclipsePreferences globalPrefs = context.getNode(NODE_NAME);
- initializeDefaultPreferences(globalPrefs);
- for(String key : globalPrefs.keys()){
- prefVals.put(key, globalPrefs.get(key, null));
- }
- context = new ProjectScope(project);
- // project
- IEclipsePreferences projectPrefs = context.getNode(NODE_NAME);
- for(String key : projectPrefs.keys()){
- prefVals.put(key, projectPrefs.get(key, null));
- }
- }
- // eclipse option
- Map<String, String> optVals = optionValues.get(project.getName());
- if(optVals == null){
- optVals = new HashMap<String, String>();
- optionValues.put(project.getName(), optVals);
- for(OptionHandler handler : optionHandlers.values()){
- String nature = handler.getNature();
- if(CORE.equals(nature) || project.getNature(nature) != null){
- optVals.putAll(handler.getValues(project));
- }
- }
- }
- Map<String, String> all =
- new HashMap<String, String>(preferenceValues.size() + optionValues.size());
- all.putAll(optVals);
- all.putAll(prefVals);
- return all;
- }
- /**
- * Gets the value of a project option/preference.
- *
- * @param project The project.
- * @param name The name of the option/preference.
- * @return The value or null if not found.
- */
- public String getValue(IProject project, String name)
- throws Exception
- {
- return getValues(project).get(name);
- }
- /**
- * Gets the global Option/Preference objects.
- *
- * @return Array of Option.
- */
- public Option[] getOptions()
- throws Exception
- {
- return getOptions(null);
- }
- /**
- * Gets the Option/Preference objects.
- *
- * @param project The project scope or null for global.
- * @return Array of Option.
- */
- public Option[] getOptions(IProject project)
- throws Exception
- {
- ArrayList<OptionInstance> results = new ArrayList<OptionInstance>();
- Map<String, String> options = new HashMap<String, String>();
- // global
- IScopeContext context = new InstanceScope();
- IEclipsePreferences globalPrefs = context.getNode(NODE_NAME);
- initializeDefaultPreferences(globalPrefs);
- for(String key : globalPrefs.keys()){
- options.put(key, globalPrefs.get(key, null));
- }
- // project
- if (project != null){
- context = new ProjectScope(project);
- IEclipsePreferences projectPrefs = context.getNode(NODE_NAME);
- for(String key : projectPrefs.keys()){
- options.put(key, projectPrefs.get(key, null));
- }
- }
- for(OptionHandler handler : optionHandlers.values()){
- String nature = handler.getNature();
- if (CORE.equals(nature) ||
- project == null ||
- project.getNature(nature) != null)
- {
- Map<String, String> ops = project == null ?
- handler.getValues() : handler.getValues(project);
- if (ops != null){
- options.putAll(ops);
- }
- }
- }
- for(String key : options.keySet()){
- String value = options.get(key);
- Option option = this.options.get(key);
- if(option == null){
- option = this.preferences.get(key);
- }
- if(option != null && value != null){
- String nature = option.getNature();
- if (CORE.equals(nature) ||
- project == null ||
- project.getNature(nature) != null){
- OptionInstance instance = new OptionInstance(option, value);
- results.add(instance);
- }
- }
- }
- return results.toArray(new Option[results.size()]);
- }
- /**
- * Sets the supplied option/preference value.
- *
- * @param name The option/preference name.
- * @param value The option/preference value.
- */
- public void setValue(String name, String value)
- throws Exception
- {
- setValue(null, name, value);
- }
- /**
- * Set the supplied value.
- *
- * @param project The project to set the value for or null for global.
- * @param name The name of the option/preference.
- * @param value The value of the option/preference.
- */
- public void setValue(IProject project, String name, String value)
- throws IllegalArgumentException, Exception
- {
- if(name.startsWith(NODE_NAME)){
- setPreference(NODE_NAME, project, name, value);
- }else{
- validateValue(options.get(name), name, value);
- OptionHandler handler = null;
- for(Object k : optionHandlers.keySet()){
- String key = (String)k;
- if(name.startsWith(key)){
- handler = (OptionHandler)optionHandlers.get(key);
- break;
- }
- }
- if(handler != null){
- if (project == null){
- handler.setOption(name, value);
- }else{
- handler.setOption(project, name, value);
- }
- optionValues.clear();
- }else{
- logger.warn("No handler found for option '{}'", name);
- }
- }
- }
- /**
- * Sets an eclim preference value.
- *
- * @param nodeName The name of the preferences node to write the preference
- * to.
- * @param project The project to set the value for or null to set globally.
- * @param name The name of the preference.
- * @param value The value of the preference.
- */
- public void setPreference(
- String nodeName, IProject project, String name, String value)
- throws IllegalArgumentException, Exception
- {
- IScopeContext context = new InstanceScope();
- IEclipsePreferences globalPrefs = context.getNode(nodeName);
- initializeDefaultPreferences(globalPrefs);
- Option pref = preferences.get(name);
- if (pref == null){
- pref = options.get(name);
- }
- // set global
- if (project == null){
- validateValue(pref, name, value);
- globalPrefs.put(name, value);
- globalPrefs.flush();
- }else{
- context = new ProjectScope(project);
- IEclipsePreferences projectPrefs = context.getNode(nodeName);
- // if project value is the same as the global, then remove it.
- if(value.equals(globalPrefs.get(name, null))){
- projectPrefs.remove(name);
- projectPrefs.flush();
- // if project value differs from global, then persist it.
- }else{
- validateValue(pref, name, value);
- projectPrefs.put(name, value);
- projectPrefs.flush();
- }
- }
- preferenceValues.clear();
- }
- /**
- * Initializes the default preferences.
- * Note: should only be run against the global preferences (not project, etc.).
- *
- * @param preferences The eclipse preferences.
- */
- private void initializeDefaultPreferences(IEclipsePreferences preferences)
- throws Exception
- {
- String node = preferences.name();
- for(Preference preference : this.preferences.values()){
- String name = preference.getName();
- if (name.startsWith(node) && preferences.get(name, null) == null){
- preferences.put(preference.getName(), preference.getDefaultValue());
- }
- }
- preferences.flush();
- }
- /**
- * Validates that the supplied value is valid for the specified
- * option/preference.
- *
- * @param option The option/preference instance.
- * @param name The name of the option/preference.
- * @param value The value of the option/preference.
- */
- private void validateValue(Option option, String name, String value)
- throws IllegalArgumentException
- {
- if(option != null){
- if (option.getPattern() == null ||
- option.getPattern().matcher(value).matches()){
- return;
- }else{
- throw new IllegalArgumentException(
- Services.getMessage("setting.invalid",
- name, value, option.getRegex()));
- }
- }
- throw new IllegalArgumentException(
- Services.getMessage("setting.not.found", name));
- }
- }