1 package org.lsst.ccs.command;
2
3 import java.util.Collections;
4 import java.util.LinkedHashSet;
5 import java.util.Set;
6
7 /**
8 * A class which can combine multiple command sets to form one combined command set.
9 * Individual command sets can be dynamically added and removed. Command sets can
10 * be nested, in that one CompositeCommandSet may include another.
11 * @author tonyj
12 */
13 public class CompositeCommandSet implements CommandSet {
14 private final Set<CommandSet> commands = new LinkedHashSet<>();
15 private final CompositeCommandDictionary dict = new CompositeCommandDictionary();
16
17 /**
18 * Add a new command set
19 * @param set The command set to add.
20 */
21 public void add(CommandSet set) {
22 commands.add(set);
23 // TODO: Check for ambigous commands and if found warn
24 dict.add(set.getCommandDictionary());
25 }
26 /**
27 * Remove a command set
28 * @param set The command set to be removed.
29 */
30 public void remove(CommandSet set) {
31 commands.remove(set);
32 dict.remove(set.getCommandDictionary());
33 }
34 /**
35 * Returns the list of command sets.
36 * @return An unmodifiable collection of command sets
37 */
38 public Set<CommandSet> getCommandSets() {
39 return Collections.unmodifiableSet(commands);
40 }
41
42 /**
43 * Get the dictionary associated with this command set. If there are
44 * multiple command sets included in this composite command set the
45 * dictionary will include entries for all of the commands in all of the
46 * included command sets.
47 * @return The combined dictionary
48 */
49 @Override
50 public Dictionary getCommandDictionary() {
51 return dict;
52 }
53
54 /**
55 * Invoke a command included in this command set.
56 * @param command The Command to be invoked
57 * @return The result of executing the command, or <code>null</code> if
58 * the command does not return a result.
59 * @throws CommandInvocationException If the command fails, either because it cannot
60 * be found, the arguments do not match the expected arguments, or the command fails
61 * during invocation.
62 */
63 @Override
64 public Object invoke(BasicCommand command) throws CommandInvocationException {
65 for (CommandSet set : commands) {
66 if (set.getCommandDictionary().containsCommand(command)) {
67 return set.invoke(command);
68 }
69 }
70 throw new CommandInvocationException("Error: No handler found for command %s with %d arguments",command.getCommand(),command.getArgumentCount());
71 }
72 }