1
2
3
4
5
6
7
8
9
10
11 package org.eclipse.jgit.pgm;
12
13 import static java.nio.charset.StandardCharsets.UTF_8;
14
15 import java.io.BufferedReader;
16 import java.io.IOException;
17 import java.io.InputStreamReader;
18 import java.net.URL;
19 import java.util.ArrayList;
20 import java.util.Arrays;
21 import java.util.Collection;
22 import java.util.Enumeration;
23 import java.util.HashMap;
24 import java.util.Map;
25 import java.util.Vector;
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45 public class CommandCatalog {
46 private static final CommandCatalog INSTANCE = new CommandCatalog();
47
48
49
50
51
52
53
54
55
56 public static CommandRef get(String name) {
57 return INSTANCE.commands.get(name);
58 }
59
60
61
62
63
64
65 public static CommandRef[] all() {
66 return toSortedArray(INSTANCE.commands.values());
67 }
68
69
70
71
72
73
74 public static CommandRef[] common() {
75 final ArrayList<CommandRef> common = new ArrayList<>();
76 for (CommandRef c : INSTANCE.commands.values())
77 if (c.isCommon())
78 common.add(c);
79 return toSortedArray(common);
80 }
81
82 private static CommandRef[] toSortedArray(Collection<CommandRef> c) {
83 final CommandRef[] r = c.toArray(new CommandRef[0]);
84 Arrays.sort(r, (CommandRef o1, CommandRef o2) -> o1.getName()
85 .compareTo(o2.getName()));
86 return r;
87 }
88
89 private final ClassLoader ldr;
90
91 private final Map<String, CommandRef> commands;
92
93 private CommandCatalog() {
94 ldr = Thread.currentThread().getContextClassLoader();
95 commands = new HashMap<>();
96
97 final Enumeration<URL> catalogs = catalogs();
98 while (catalogs.hasMoreElements())
99 scan(catalogs.nextElement());
100 }
101
102 private Enumeration<URL> catalogs() {
103 try {
104 final String pfx = "META-INF/services/";
105 return ldr.getResources(pfx + TextBuiltin.class.getName());
106 } catch (IOException err) {
107 return new Vector<URL>().elements();
108 }
109 }
110
111 private void scan(URL cUrl) {
112 try (BufferedReader cIn = new BufferedReader(
113 new InputStreamReader(cUrl.openStream(), UTF_8))) {
114 String line;
115 while ((line = cIn.readLine()) != null) {
116 if (line.length() > 0 && !line.startsWith("#"))
117 load(line);
118 }
119 } catch (IOException e) {
120
121 }
122 }
123
124 private void load(String cn) {
125 final Class<? extends TextBuiltin> clazz;
126 try {
127 clazz = Class.forName(cn, false, ldr).asSubclass(TextBuiltin.class);
128 } catch (ClassNotFoundException | ClassCastException notBuiltin) {
129
130
131 return;
132 }
133
134 final CommandRef cr;
135 final Command a = clazz.getAnnotation(Command.class);
136 if (a != null)
137 cr = new CommandRef(clazz, a);
138 else
139 cr = new CommandRef(clazz);
140
141 commands.put(cr.getName(), cr);
142 }
143 }