package org.ngrinder.infra.plugin.finder; import java.io.IOException; import java.io.Reader; import java.net.URISyntaxException; import java.net.URL; import java.nio.charset.StandardCharsets; import java.nio.file.FileSystem; import java.nio.file.FileSystems; import java.nio.file.FileVisitOption; import java.nio.file.FileVisitResult; import java.nio.file.Files; import java.nio.file.Path; import java.nio.file.Paths; import java.nio.file.SimpleFileVisitor; import java.nio.file.attribute.BasicFileAttributes; import java.util.Collections; import java.util.HashSet; import java.util.LinkedHashMap; import java.util.List; import java.util.Map; import java.util.Set; import ro.fortsoft.pf4j.AbstractExtensionFinder; import ro.fortsoft.pf4j.PluginClassLoader; import ro.fortsoft.pf4j.PluginManager; import ro.fortsoft.pf4j.PluginWrapper; import ro.fortsoft.pf4j.processor.ServiceProviderExtensionStorage; /** * AbstractExtensionFinder extended class. * readPluginsStorages method override. * * @author Gisoo Gwon ,GeunWoo Son * @see https://github.com/decebals/pf4j * @since 3.0 */ public class NGrinderServiceProviderExtensionFinder extends AbstractExtensionFinder { private final String EXTENSIONS_RESOURCE_PATH = "META-INF/extensions.idx"; public NGrinderServiceProviderExtensionFinder(PluginManager pluginManager) { super(pluginManager); } @Override public Map<String, Set<String>> readClasspathStorages() { return new LinkedHashMap<String, Set<String>>(); } @Override public Map<String, Set<String>> readPluginsStorages() { log.debug("Reading extensions storages from plugins"); Map<String, Set<String>> result = new LinkedHashMap<String, Set<String>>(); List<PluginWrapper> plugins = pluginManager.getPlugins(); for (PluginWrapper plugin : plugins) { String pluginId = plugin.getDescriptor().getPluginId(); log.debug("Reading extensions storages for plugin '{}'", pluginId); final Set<String> bucket = new HashSet<String>(); try { URL url = ((PluginClassLoader) plugin.getPluginClassLoader()).findResource(EXTENSIONS_RESOURCE_PATH); if (url != null) { Path extensionPath; if (url.toURI().getScheme().equals("jar")) { FileSystem fileSystem = FileSystems.newFileSystem(url.toURI(), Collections.<String, Object>emptyMap()); extensionPath = fileSystem.getPath(EXTENSIONS_RESOURCE_PATH); } else { extensionPath = Paths.get(url.toURI()); } Files.walkFileTree(extensionPath, Collections.<FileVisitOption>emptySet(), 1, new SimpleFileVisitor<Path>() { @Override public FileVisitResult visitFile(Path file, BasicFileAttributes attrs) throws IOException { log.debug("Read '{}'", file); Reader reader = Files.newBufferedReader(file, StandardCharsets.UTF_8); ServiceProviderExtensionStorage.read(reader, bucket); return FileVisitResult.CONTINUE; } }); } else { log.debug("Cannot find '{}'", EXTENSIONS_RESOURCE_PATH); } if (bucket.isEmpty()) { log.debug("No extensions found"); } else { log.debug("Found possible {} extensions:", bucket.size()); for (String entry : bucket) { log.debug(" " + entry); } } result.put(pluginId, bucket); } catch (IOException e) { log.error(e.getMessage(), e); } catch (URISyntaxException e) { log.error(e.getMessage(), e); } } return result; } }