Browse Source

Implement loading a single plugin archive

pull/6/head
James Moger 11 years ago
parent
commit
de6b7df7a6
  1. 49
      pf4j/src/main/java/ro/fortsoft/pf4j/DefaultExtensionFinder.java
  2. 1258
      pf4j/src/main/java/ro/fortsoft/pf4j/DefaultPluginManager.java
  3. 10
      pf4j/src/main/java/ro/fortsoft/pf4j/ExtensionFinder.java
  4. 9
      pf4j/src/main/java/ro/fortsoft/pf4j/PluginManager.java

49
pf4j/src/main/java/ro/fortsoft/pf4j/DefaultExtensionFinder.java

@ -1,11 +1,11 @@
/* /*
* Copyright 2013 Decebal Suiu * Copyright 2013 Decebal Suiu
* *
* Licensed under the Apache License, Version 2.0 (the "License"); you may not use this work except in compliance with * Licensed under the Apache License, Version 2.0 (the "License"); you may not use this work except in compliance with
* the License. You may obtain a copy of the License in the LICENSE file, or at: * the License. You may obtain a copy of the License in the LICENSE file, or at:
* *
* http://www.apache.org/licenses/LICENSE-2.0 * http://www.apache.org/licenses/LICENSE-2.0
* *
* Unless required by applicable law or agreed to in writing, software distributed under the License is distributed on * Unless required by applicable law or agreed to in writing, software distributed under the License is distributed on
* an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the License for the * an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the License for the
* specific language governing permissions and limitations under the License. * specific language governing permissions and limitations under the License.
@ -29,23 +29,28 @@ import org.slf4j.LoggerFactory;
/** /**
* The default implementation for ExtensionFinder. * The default implementation for ExtensionFinder.
* All extensions declared in a plugin are indexed in a file "META-INF/extensions.idx". * All extensions declared in a plugin are indexed in a file "META-INF/extensions.idx".
* This class lookup extensions in all extensions index files "META-INF/extensions.idx". * This class lookup extensions in all extensions index files "META-INF/extensions.idx".
* *
* @author Decebal Suiu * @author Decebal Suiu
*/ */
public class DefaultExtensionFinder implements ExtensionFinder { public class DefaultExtensionFinder implements ExtensionFinder {
private static final Logger log = LoggerFactory.getLogger(DefaultExtensionFinder.class); private static final Logger log = LoggerFactory.getLogger(DefaultExtensionFinder.class);
private ClassLoader classLoader; private ClassLoader classLoader;
private ExtensionFactory extensionFactory; private ExtensionFactory extensionFactory;
private volatile Set<String> entries; private volatile Set<String> entries;
public DefaultExtensionFinder(ClassLoader classLoader) { public DefaultExtensionFinder(ClassLoader classLoader) {
this.classLoader = classLoader; this.classLoader = classLoader;
this.extensionFactory = createExtensionFactory(); this.extensionFactory = createExtensionFactory();
} }
@Override
public void reset() {
entries = null;
}
@Override @Override
public <T> List<ExtensionWrapper<T>> find(Class<T> type) { public <T> List<ExtensionWrapper<T>> find(Class<T> type) {
log.debug("Checking extension point '{}'", type.getName()); log.debug("Checking extension point '{}'", type.getName());
@ -60,7 +65,7 @@ public class DefaultExtensionFinder implements ExtensionFinder {
if (entries == null) { if (entries == null) {
entries = readIndexFiles(); entries = readIndexFiles();
} }
for (String entry : entries) { for (String entry : entries) {
try { try {
Class<?> extensionType = classLoader.loadClass(entry); Class<?> extensionType = classLoader.loadClass(entry);
@ -76,10 +81,10 @@ public class DefaultExtensionFinder implements ExtensionFinder {
log.warn("'{}' is not an extension for extension point '{}'", extensionType.getName(), type.getName()); log.warn("'{}' is not an extension for extension point '{}'", extensionType.getName(), type.getName());
} }
} catch (ClassNotFoundException e) { } catch (ClassNotFoundException e) {
log.error(e.getMessage(), e); log.error(e.getMessage(), e);
} }
} }
if (entries.isEmpty()) { if (entries.isEmpty()) {
log.debug("No extensions found for extension point '{}'", type.getName()); log.debug("No extensions found for extension point '{}'", type.getName());
} else { } else {
@ -88,21 +93,21 @@ public class DefaultExtensionFinder implements ExtensionFinder {
// sort by "ordinal" property // sort by "ordinal" property
Collections.sort(result); Collections.sort(result);
return result; return result;
} }
/** /**
* Add the possibility to override the ExtensionFactory. * Add the possibility to override the ExtensionFactory.
* The default implementation uses Class.newInstance() method. * The default implementation uses Class.newInstance() method.
*/ */
protected ExtensionFactory createExtensionFactory() { protected ExtensionFactory createExtensionFactory() {
return new ExtensionFactory() { return new ExtensionFactory() {
@Override @Override
public Object create(Class<?> extensionType) { public Object create(Class<?> extensionType) {
log.debug("Create instance for extension '{}'", extensionType.getName()); log.debug("Create instance for extension '{}'", extensionType.getName());
try { try {
return extensionType.newInstance(); return extensionType.newInstance();
} catch (InstantiationException e) { } catch (InstantiationException e) {
@ -110,17 +115,17 @@ public class DefaultExtensionFinder implements ExtensionFinder {
} catch (IllegalAccessException e) { } catch (IllegalAccessException e) {
log.error(e.getMessage(), e); log.error(e.getMessage(), e);
} }
return null; return null;
} }
}; };
} }
private Set<String> readIndexFiles() { private Set<String> readIndexFiles() {
log.debug("Reading extensions index files"); log.debug("Reading extensions index files");
Set<String> entries = new HashSet<String>(); Set<String> entries = new HashSet<String>();
try { try {
Enumeration<URL> indexFiles = classLoader.getResources(ExtensionsIndexer.EXTENSIONS_RESOURCE); Enumeration<URL> indexFiles = classLoader.getResources(ExtensionsIndexer.EXTENSIONS_RESOURCE);
while (indexFiles.hasMoreElements()) { while (indexFiles.hasMoreElements()) {
@ -129,7 +134,7 @@ public class DefaultExtensionFinder implements ExtensionFinder {
} }
} catch (IOException e) { } catch (IOException e) {
log.error(e.getMessage(), e); log.error(e.getMessage(), e);
} }
if (entries.isEmpty()) { if (entries.isEmpty()) {
log.debug("No extensions found"); log.debug("No extensions found");
@ -143,14 +148,14 @@ public class DefaultExtensionFinder implements ExtensionFinder {
private boolean isExtensionPoint(Class type) { private boolean isExtensionPoint(Class type) {
return ExtensionPoint.class.isAssignableFrom(type); return ExtensionPoint.class.isAssignableFrom(type);
} }
/** /**
* Creates an extension instance. * Creates an extension instance.
*/ */
public static interface ExtensionFactory { public static interface ExtensionFactory {
public Object create(Class<?> extensionType); public Object create(Class<?> extensionType);
} }
} }

1258
pf4j/src/main/java/ro/fortsoft/pf4j/DefaultPluginManager.java

File diff suppressed because it is too large Load Diff

10
pf4j/src/main/java/ro/fortsoft/pf4j/ExtensionFinder.java

@ -1,11 +1,11 @@
/* /*
* Copyright 2012 Decebal Suiu * Copyright 2012 Decebal Suiu
* *
* Licensed under the Apache License, Version 2.0 (the "License"); you may not use this work except in compliance with * Licensed under the Apache License, Version 2.0 (the "License"); you may not use this work except in compliance with
* the License. You may obtain a copy of the License in the LICENSE file, or at: * the License. You may obtain a copy of the License in the LICENSE file, or at:
* *
* http://www.apache.org/licenses/LICENSE-2.0 * http://www.apache.org/licenses/LICENSE-2.0
* *
* Unless required by applicable law or agreed to in writing, software distributed under the License is distributed on * Unless required by applicable law or agreed to in writing, software distributed under the License is distributed on
* an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the License for the * an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the License for the
* specific language governing permissions and limitations under the License. * specific language governing permissions and limitations under the License.
@ -20,5 +20,7 @@ import java.util.List;
public interface ExtensionFinder { public interface ExtensionFinder {
public <T> List<ExtensionWrapper<T>> find(Class<T> type); public <T> List<ExtensionWrapper<T>> find(Class<T> type);
public void reset();
} }

9
pf4j/src/main/java/ro/fortsoft/pf4j/PluginManager.java

@ -12,6 +12,7 @@
*/ */
package ro.fortsoft.pf4j; package ro.fortsoft.pf4j;
import java.io.File;
import java.util.List; import java.util.List;
/** /**
@ -47,6 +48,14 @@ public interface PluginManager {
*/ */
public void loadPlugins(); public void loadPlugins();
/**
* Load a plugin.
*
* @param pluginArchiveFile
* @return the pluginId of the installed plugin or null
*/
public String loadPlugin(File pluginArchiveFile);
/** /**
* Start all active plugins. * Start all active plugins.
*/ */

Loading…
Cancel
Save