3131
3232package org .scijava .plugin ;
3333
34+ import java .util .ArrayList ;
3435import java .util .HashMap ;
3536import java .util .List ;
37+ import java .util .regex .Pattern ;
38+ import java .util .regex .PatternSyntaxException ;
3639
3740import org .scijava .annotations .Index ;
3841import org .scijava .annotations .IndexItem ;
@@ -51,6 +54,8 @@ public class DefaultPluginFinder implements PluginFinder {
5154 /** Class loader to use when querying the annotation indexes. */
5255 private final ClassLoader customClassLoader ;
5356
57+ private final PluginBlacklist blacklist ;
58+
5459 // -- Constructors --
5560
5661 public DefaultPluginFinder () {
@@ -59,6 +64,7 @@ public DefaultPluginFinder() {
5964
6065 public DefaultPluginFinder (final ClassLoader classLoader ) {
6166 customClassLoader = classLoader ;
67+ blacklist = new SysPropBlacklist ();
6268 }
6369
6470 // -- PluginFinder methods --
@@ -77,6 +83,7 @@ public HashMap<String, Throwable> findPlugins(
7783
7884 // create a PluginInfo object for each item in the index
7985 for (final IndexItem <Plugin > item : annotationIndex ) {
86+ if (blacklist .contains (item .className ())) continue ;
8087 try {
8188 final PluginInfo <?> info = createInfo (item , classLoader );
8289 plugins .add (info );
@@ -109,4 +116,47 @@ private ClassLoader getClassLoader() {
109116 return Thread .currentThread ().getContextClassLoader ();
110117 }
111118
119+ // -- Helper classes --
120+
121+ private interface PluginBlacklist {
122+ boolean contains (String className );
123+ }
124+
125+ /**
126+ * A blacklist defined by the {@code scijava.plugin.blacklist} system
127+ * property, formatted as a colon-separated list of regexes.
128+ * <p>
129+ * If a plugin class matches any of the regexes, it is excluded from the
130+ * plugin index.
131+ * </p>
132+ */
133+ private class SysPropBlacklist implements PluginBlacklist {
134+ private final List <Pattern > patterns ;
135+
136+ public SysPropBlacklist () {
137+ final String sysProp = System .getProperty ("scijava.plugin.blacklist" );
138+ final String [] regexes = //
139+ sysProp == null ? new String [0 ] : sysProp .split (":" );
140+ patterns = new ArrayList <Pattern >(regexes .length );
141+ for (final String regex : regexes ) {
142+ try {
143+ patterns .add (Pattern .compile (regex ));
144+ }
145+ catch (final PatternSyntaxException exc ) {
146+ // NB: Ignore this malformed pattern.
147+ }
148+ }
149+ }
150+
151+ // -- PluginBlacklist methods --
152+
153+ @ Override
154+ public boolean contains (final String className ) {
155+ for (final Pattern pattern : patterns ) {
156+ if (pattern .matcher (className ).matches ()) return true ;
157+ }
158+ return false ;
159+ }
160+ }
161+
112162}
0 commit comments