/** * Copyright (C) 2009 STMicroelectronics * * This file is part of "Mind Compiler" is free software: you can redistribute * it and/or modify it under the terms of the GNU Lesser 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 Lesser General Public License for more * details. * * You should have received a copy of the GNU Lesser General Public License * along with this program. If not, see <http://www.gnu.org/licenses/>. * * Contact: mind@ow2.org * * Authors: Ali Erdem Ozcan * Contributors: */ package org.ow2.mind.cli; import java.util.ArrayList; import java.util.Collection; import java.util.Collections; import java.util.HashMap; import java.util.HashSet; import java.util.LinkedHashMap; import java.util.List; import java.util.Map; import java.util.Set; import org.objectweb.fractal.adl.CompilerError; import org.objectweb.fractal.adl.error.GenericErrors; import org.ow2.mind.plugin.ConfigurationElement; import org.ow2.mind.plugin.PluginManager; import com.google.common.collect.ArrayListMultimap; import com.google.common.collect.Multimap; public final class CommandLineOptionExtensionHelper { public static final String COMMAND_LINE_OPTIONS_EXTENSION = "org.ow2.mind.mindc.command-line-options"; protected static Map<String, CmdOption> cmdOptions; protected static Map<String, List<String>> preconditions; protected static Collection<Set<String>> exclusiveGroups; protected static Multimap<CmdOption, CommandOptionHandler> handlerMap; private CommandLineOptionExtensionHelper() { } /** * Returns the collection of {@link CmdOption} objects that defined by loaded * the plugins. * * @param pluginManagerItf the plugin manager component to be used for loading * plugins. * @return the collection of {@link CmdOption} objects that defined by loaded * the plugins. */ public static Collection<CmdOption> getCommandOptions( final PluginManager pluginManagerItf) { if (cmdOptions == null) { initRegistry(pluginManagerItf); } return Collections.unmodifiableCollection(cmdOptions.values()); } /** * Accessor method for getting the command option handler objects which are * registered for the cmdOption. * * @param pluginManagerItf the plugin manager component to be used for loading * plugins. * @param cmdOption the option object which the handler is associated to. * @return Collection of the handler object. Returns an empty list if no * handler is regirstered. */ public static Collection<CommandOptionHandler> getHandler( final CmdOption cmdOption, final PluginManager pluginManagerItf) { if (handlerMap == null) initRegistry(pluginManagerItf); final Collection<CommandOptionHandler> handlers = handlerMap.get(cmdOption); return (handlers == null) ? Collections.<CommandOptionHandler> emptyList() : handlers; } /** * Returns the identifiers of the command options that must be processed * before the given option. * * @param cmdOption an option. * @param pluginManagerItf the plugin manager component to be used for loading * plugins. * @return the identifiers of the command options that must be processed * before the given option. */ public static List<String> getPrecedenceIds(final CmdOption cmdOption, final PluginManager pluginManagerItf) { if (preconditions == null) initRegistry(pluginManagerItf); final List<String> l = preconditions.get(cmdOption.getId()); return (l == null) ? Collections.<String> emptyList() : Collections .unmodifiableList(l); } /** * Returns the exclusive groups * * @param pluginManagerItf the plugin manager component to be used for loading * plugins. * @return the exclusive groups */ public static Collection<Set<String>> getExclusiveGroups( final PluginManager pluginManagerItf) { if (exclusiveGroups == null) initRegistry(pluginManagerItf); return Collections.unmodifiableCollection(exclusiveGroups); } private static final String ID = "id"; private static final String SHORT_NAME = "shortName"; private static final String LONG_NAME = "longName"; private static final String DESCRIPTION = "description"; private static final String DEFAULT_VALUE = "defaultValue"; private static final String ALLOW_MULTIPLE = "allowMultiple"; private static final String ARG_DESC = "argDesc"; private static final String HANDLER = "handler"; private static final String SEPARATOR = "separator"; private static final String ARG_NAME_DESC = "argNameDesc"; private static final String ARG_VALUE_DESC = "argValueDesc"; private static final String FLAG = "cmdFlag"; private static final String PROPERTIES = "cmdProperties"; private static final String ARGUMENT = "cmdArgument"; private static final String APPEND_OPTION = "cmdAppendOption"; private static final String PATH_OPTION = "cmdPathOption"; private static final String PROCESS_AFTER = "processAfter"; private static final String PROCESS_BEFORE = "processBefore"; private static final String EXCLUSIVE_GROUP = "exclusiveGroup"; // Parses the command-line extensions and initializes the option and handler // collections. // Supported elements are: cmdFlag, cmdProperties, cmdArgument, // cmdAppendOption and cmdPathOption. private static void initRegistry(final PluginManager pluginManagerItf) { cmdOptions = new LinkedHashMap<String, CmdOption>(); handlerMap = ArrayListMultimap.create(); for (final ConfigurationElement element : pluginManagerItf .getConfigurationElements(COMMAND_LINE_OPTIONS_EXTENSION)) { if (element.getName().equals(EXCLUSIVE_GROUP)) continue; CmdOption cmdOption; if (element.getName().equals(FLAG)) { cmdOption = new CmdFlag(element.getAttribute(ID), element.getAttribute(SHORT_NAME), element.getAttribute(LONG_NAME), element.getAttribute(DESCRIPTION)); } else if (element.getName().equals(PROPERTIES)) { cmdOption = new CmdProperties(element.getAttribute(ID), element.getAttribute(SHORT_NAME), element.getAttribute(DESCRIPTION), element.getAttribute(ARG_NAME_DESC), element.getAttribute(ARG_VALUE_DESC)); } else if (element.getName().equals(ARGUMENT)) { final boolean allowMultiple = element.getAttribute(ALLOW_MULTIPLE) != null ? new Boolean(element.getAttribute(ALLOW_MULTIPLE)).booleanValue() : false; cmdOption = new CmdArgument(element.getAttribute(ID), element.getAttribute(SHORT_NAME), element.getAttribute(LONG_NAME), element.getAttribute(DESCRIPTION), element.getAttribute(ARG_DESC), element.getAttribute(DEFAULT_VALUE), allowMultiple); } else if (element.getName().equals(APPEND_OPTION)) { final String separator = element.getAttribute(SEPARATOR) != null ? element.getAttribute(SEPARATOR) : " "; cmdOption = new CmdAppendOption(element.getAttribute(ID), element.getAttribute(SHORT_NAME), element.getAttribute(LONG_NAME), element.getAttribute(DESCRIPTION), element.getAttribute(ARG_DESC), element.getAttribute(DEFAULT_VALUE), separator); } else if (element.getName().equals(PATH_OPTION)) { cmdOption = new CmdPathOption(element.getAttribute(ID), element.getAttribute(SHORT_NAME), element.getAttribute(LONG_NAME), element.getAttribute(DESCRIPTION), element.getAttribute(ARG_DESC)); } else { throw new CompilerError(GenericErrors.GENERIC_ERROR, "Unknown plugin element '" + element.getName() + "'."); } final CmdOption prevOpt = cmdOptions.put(cmdOption.getId(), cmdOption); if (prevOpt != null) { throw new CompilerError(GenericErrors.GENERIC_ERROR, "Invalid command line option Id: '" + cmdOption.getId() + "' is already used."); } final CommandOptionHandler handler = element.createInstance(HANDLER, CommandOptionHandler.class); if (handler != null) { handlerMap.put(cmdOption, handler); } } // initialize preconditions. preconditions = new HashMap<String, List<String>>(); for (final ConfigurationElement element : pluginManagerItf .getConfigurationElements(COMMAND_LINE_OPTIONS_EXTENSION)) { final String id = element.getAttribute(ID); List<String> precondition = preconditions.get(id); if (precondition == null) { precondition = new ArrayList<String>(); preconditions.put(id, precondition); } for (final ConfigurationElement processAfter : element .getChildren(PROCESS_AFTER)) { final String afterId = processAfter.getAttribute(ID); if (!cmdOptions.containsKey(afterId)) { throw new CompilerError(GenericErrors.GENERIC_ERROR, "Unknown option Id: '" + afterId + "'."); } precondition.add(afterId); } for (final ConfigurationElement processBefore : element .getChildren(PROCESS_BEFORE)) { final String beforeId = processBefore.getAttribute(ID); if (!cmdOptions.containsKey(beforeId)) { throw new CompilerError(GenericErrors.GENERIC_ERROR, "Unknown option Id: '" + beforeId + "'."); } List<String> l = preconditions.get(beforeId); if (l == null) { l = new ArrayList<String>(); preconditions.put(beforeId, l); } l.add(id); } } // initialize exclusiveGroups exclusiveGroups = new ArrayList<Set<String>>(); for (final ConfigurationElement element : pluginManagerItf .getConfigurationElements(COMMAND_LINE_OPTIONS_EXTENSION, EXCLUSIVE_GROUP)) { final Set<String> exclusiveGroup = new HashSet<String>(); for (final ConfigurationElement child : element.getChildren()) { exclusiveGroup.add(child.getAttribute(ID)); } exclusiveGroups.add(Collections.unmodifiableSet(exclusiveGroup)); } } }