From 24476cef14d977263d901394132a69c6bd8e94df Mon Sep 17 00:00:00 2001 From: simonbrandhof Date: Thu, 16 Dec 2010 11:41:17 +0000 Subject: [PATCH] SONAR-2016 Sonar plugins and so extensions are not accessible from the Sonar Maven plugin --- .../src/main/java/org/sonar/batch/Batch.java | 28 +++--- .../java/org/sonar/batch/ProjectBatch.java | 1 + .../org/sonar/batch/RemoteClassLoader.java | 69 --------------- .../BatchPluginRepository.java | 16 ++-- .../batch/bootstrap/BootstrapClassLoader.java | 53 +++++++++++ .../batch/bootstrap/ExtensionDownloader.java | 69 +++++++++++++++ .../batch/bootstrap/TempDirectories.java | 82 +++++++++++++++++ .../BatchPluginRepositoryTest.java | 3 +- .../BootstrapClassLoaderTest.java} | 12 +-- .../bootstrap/ExtensionDownloaderTest.java | 68 ++++++++++++++ .../batch/bootstrap/TempDirectoriesTest.java | 83 ++++++++++++++++++ .../BootstrapClassLoaderTest}/foo.jar | Bin 12 files changed, 392 insertions(+), 92 deletions(-) delete mode 100644 sonar-batch/src/main/java/org/sonar/batch/RemoteClassLoader.java rename sonar-batch/src/main/java/org/sonar/batch/{ => bootstrap}/BatchPluginRepository.java (90%) create mode 100644 sonar-batch/src/main/java/org/sonar/batch/bootstrap/BootstrapClassLoader.java create mode 100644 sonar-batch/src/main/java/org/sonar/batch/bootstrap/ExtensionDownloader.java create mode 100644 sonar-batch/src/main/java/org/sonar/batch/bootstrap/TempDirectories.java rename sonar-batch/src/test/java/org/sonar/batch/{ => bootstrap}/BatchPluginRepositoryTest.java (97%) rename sonar-batch/src/test/java/org/sonar/batch/{RemoteClassLoaderTest.java => bootstrap/BootstrapClassLoaderTest.java} (77%) create mode 100644 sonar-batch/src/test/java/org/sonar/batch/bootstrap/ExtensionDownloaderTest.java create mode 100644 sonar-batch/src/test/java/org/sonar/batch/bootstrap/TempDirectoriesTest.java rename sonar-batch/src/test/resources/org/sonar/batch/{RemoteClassLoaderTest => bootstrap/BootstrapClassLoaderTest}/foo.jar (100%) diff --git a/sonar-batch/src/main/java/org/sonar/batch/Batch.java b/sonar-batch/src/main/java/org/sonar/batch/Batch.java index d6c5c6a8bd6..91e981e41ac 100644 --- a/sonar-batch/src/main/java/org/sonar/batch/Batch.java +++ b/sonar-batch/src/main/java/org/sonar/batch/Batch.java @@ -29,6 +29,10 @@ import org.sonar.api.resources.Project; import org.sonar.api.utils.HttpDownloader; import org.sonar.api.utils.IocContainer; import org.sonar.api.utils.ServerHttpClient; +import org.sonar.batch.bootstrap.BatchPluginRepository; +import org.sonar.batch.bootstrap.BootstrapClassLoader; +import org.sonar.batch.bootstrap.ExtensionDownloader; +import org.sonar.batch.bootstrap.TempDirectories; import org.sonar.batch.index.*; import org.sonar.core.components.CacheMetricFinder; import org.sonar.core.components.CacheRuleFinder; @@ -58,7 +62,7 @@ public class Batch { try { container = buildPicoContainer(); container.start(); - analyzeProjects(container); + analyzeModules(container); } finally { if (container != null) { @@ -67,10 +71,9 @@ public class Batch { } } - private void analyzeProjects(MutablePicoContainer container) { + private void analyzeModules(MutablePicoContainer container) { // a child container is built to ensure database connector is up MutablePicoContainer batchContainer = container.makeChildContainer(); - batchContainer.as(Characteristics.CACHE).addComponent(ServerMetadata.class); batchContainer.as(Characteristics.CACHE).addComponent(ProjectTree.class); batchContainer.as(Characteristics.CACHE).addComponent(DefaultResourceCreationLock.class); batchContainer.as(Characteristics.CACHE).addComponent(DefaultIndex.class); @@ -86,7 +89,6 @@ public class Batch { batchContainer.as(Characteristics.CACHE).addComponent(BatchPluginRepository.class); batchContainer.as(Characteristics.CACHE).addComponent(Plugins.class); batchContainer.as(Characteristics.CACHE).addComponent(ServerHttpClient.class); - batchContainer.as(Characteristics.CACHE).addComponent(HttpDownloader.class); batchContainer.as(Characteristics.CACHE).addComponent(MeasuresDao.class); batchContainer.as(Characteristics.CACHE).addComponent(CacheRuleFinder.class); batchContainer.as(Characteristics.CACHE).addComponent(CacheMetricFinder.class); @@ -94,7 +96,7 @@ public class Batch { ProjectTree projectTree = batchContainer.getComponent(ProjectTree.class); DefaultIndex index = batchContainer.getComponent(DefaultIndex.class); - analyzeProject(batchContainer, index, projectTree.getRootProject()); + analyzeModule(batchContainer, index, projectTree.getRootProject()); // batchContainer is stopped by its parent } @@ -103,11 +105,17 @@ public class Batch { MutablePicoContainer container = IocContainer.buildPicoContainer(); register(container, configuration); - URLClassLoader fullClassloader = RemoteClassLoader.createForJdbcDriver(configuration).getClassLoader(); + register(container, ServerMetadata.class);// registered here because used by BootstrapClassLoader + register(container, TempDirectories.class);// registered here because used by BootstrapClassLoader + register(container, HttpDownloader.class);// registered here because used by BootstrapClassLoader + register(container, ExtensionDownloader.class);// registered here because used by BootstrapClassLoader + register(container, BootstrapClassLoader.class); + + URLClassLoader bootstrapClassLoader = container.getComponent(BootstrapClassLoader.class).getClassLoader(); // set as the current context classloader for hibernate, else it does not find the JDBC driver. - Thread.currentThread().setContextClassLoader(fullClassloader); + Thread.currentThread().setContextClassLoader(bootstrapClassLoader); - register(container, new DriverDatabaseConnector(configuration, fullClassloader)); + register(container, new DriverDatabaseConnector(configuration, bootstrapClassLoader)); register(container, ThreadLocalDatabaseSessionFactory.class); container.as(Characteristics.CACHE).addAdapter(new DatabaseSessionProvider()); for (Object component : components) { @@ -120,9 +128,9 @@ public class Batch { container.as(Characteristics.CACHE).addComponent(component); } - private void analyzeProject(MutablePicoContainer container, DefaultIndex index, Project project) { + private void analyzeModule(MutablePicoContainer container, DefaultIndex index, Project project) { for (Project module : project.getModules()) { - analyzeProject(container, index, module); + analyzeModule(container, index, module); } LOG.info("------------- Analyzing {}", project.getName()); diff --git a/sonar-batch/src/main/java/org/sonar/batch/ProjectBatch.java b/sonar-batch/src/main/java/org/sonar/batch/ProjectBatch.java index 104f7eb0660..afccb16fdda 100644 --- a/sonar-batch/src/main/java/org/sonar/batch/ProjectBatch.java +++ b/sonar-batch/src/main/java/org/sonar/batch/ProjectBatch.java @@ -35,6 +35,7 @@ import org.sonar.api.resources.Project; import org.sonar.api.rules.DefaultRulesManager; import org.sonar.api.utils.IocContainer; import org.sonar.api.utils.SonarException; +import org.sonar.batch.bootstrap.BatchPluginRepository; import org.sonar.batch.index.DefaultIndex; import org.sonar.batch.index.DefaultResourcePersister; import org.sonar.batch.phases.Phases; diff --git a/sonar-batch/src/main/java/org/sonar/batch/RemoteClassLoader.java b/sonar-batch/src/main/java/org/sonar/batch/RemoteClassLoader.java deleted file mode 100644 index 31f0611d88e..00000000000 --- a/sonar-batch/src/main/java/org/sonar/batch/RemoteClassLoader.java +++ /dev/null @@ -1,69 +0,0 @@ -/* - * Sonar, open source software quality management tool. - * Copyright (C) 2009 SonarSource SA - * mailto:contact AT sonarsource DOT com - * - * Sonar is free software; you can redistribute it and/or - * modify it under the terms of the GNU Lesser General Public - * License as published by the Free Software Foundation; either - * version 3 of the License, or (at your option) any later version. - * - * Sonar is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU - * Lesser General Public License for more details. - * - * You should have received a copy of the GNU Lesser General Public - * License along with Sonar; if not, write to the Free Software - * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02 - */ -package org.sonar.batch; - -import org.apache.commons.configuration.Configuration; - -import java.net.MalformedURLException; -import java.net.URL; -import java.net.URLClassLoader; -import java.util.Collection; - -/** - * Create classloader from remote URLs. - * - * IMPORTANT : it generates URLClassLoaders, which use the parent first delegation mode. It finds classes in the parent classloader THEN - * in the plugin classloader. - * Using a child-first delegation mode can avoid some conflicts with API dependencies (xml-api, antlr). It's - * not possible for now, but it would be simple to implement by replacing the URLClassLoader by - * the class ChildFirstClassLoader (see http://articles.qos.ch/classloader.html) - */ -public class RemoteClassLoader { - - private URLClassLoader classLoader; - - public RemoteClassLoader(URL[] urls, ClassLoader parent) { - ClassLoader parentClassLoader = (parent==null ? RemoteClassLoader.class.getClassLoader() : parent); - classLoader = URLClassLoader.newInstance(urls, parentClassLoader); - } - - public RemoteClassLoader(URL[] urls) { - this(urls, null); - } - - public RemoteClassLoader(Collection urls, ClassLoader parent) { - this(urls.toArray(new URL[urls.size()]), parent); - } - - public URLClassLoader getClassLoader() { - return classLoader; - } - - public static RemoteClassLoader createForJdbcDriver(Configuration conf) { - String baseUrl = ServerMetadata.getURL(conf); - String url = baseUrl + "/deploy/jdbc-driver.jar"; - try { - return new RemoteClassLoader(new URL[]{new URL(url)}); - - } catch (MalformedURLException e) { - throw new RuntimeException("Fail to download the JDBC driver from server: " + url, e); - } - } -} diff --git a/sonar-batch/src/main/java/org/sonar/batch/BatchPluginRepository.java b/sonar-batch/src/main/java/org/sonar/batch/bootstrap/BatchPluginRepository.java similarity index 90% rename from sonar-batch/src/main/java/org/sonar/batch/BatchPluginRepository.java rename to sonar-batch/src/main/java/org/sonar/batch/bootstrap/BatchPluginRepository.java index 63e3a957e05..6588cfc0f70 100644 --- a/sonar-batch/src/main/java/org/sonar/batch/BatchPluginRepository.java +++ b/sonar-batch/src/main/java/org/sonar/batch/bootstrap/BatchPluginRepository.java @@ -17,7 +17,7 @@ * License along with Sonar; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02 */ -package org.sonar.batch; +package org.sonar.batch.bootstrap; import com.google.common.collect.Lists; import org.apache.commons.configuration.Configuration; @@ -39,6 +39,7 @@ import org.sonar.core.plugin.JpaPlugin; import org.sonar.core.plugin.JpaPluginDao; import org.sonar.core.plugin.JpaPluginFile; +import java.io.File; import java.net.MalformedURLException; import java.net.URL; import java.util.List; @@ -47,14 +48,14 @@ public class BatchPluginRepository extends AbstractPluginRepository { private static final Logger LOG = LoggerFactory.getLogger(BatchPluginRepository.class); - private String baseUrl; private JpaPluginDao dao; private ClassLoadersCollection classLoaders; + private ExtensionDownloader extensionDownloader; - public BatchPluginRepository(JpaPluginDao dao, ServerMetadata server) { + public BatchPluginRepository(JpaPluginDao dao, ExtensionDownloader extensionDownloader) { this.dao = dao; - this.baseUrl = server.getURL() + "/deploy/plugins/"; + this.extensionDownloader = extensionDownloader; } /** @@ -70,11 +71,12 @@ public class BatchPluginRepository extends AbstractPluginRepository { String key = pluginMetadata.getKey(); List urls = Lists.newArrayList(); for (JpaPluginFile pluginFile : pluginMetadata.getFiles()) { + File file = extensionDownloader.downloadExtension(pluginFile); try { - URL url = new URL(baseUrl + pluginFile.getPath()); - urls.add(url); + urls.add(file.toURI().toURL()); + } catch (MalformedURLException e) { - throw new SonarException("Can not build the classloader of the plugin " + pluginFile.getPluginKey(), e); + throw new SonarException("Can not get the URL of: " + file, e); } } if (LOG.isDebugEnabled()) { diff --git a/sonar-batch/src/main/java/org/sonar/batch/bootstrap/BootstrapClassLoader.java b/sonar-batch/src/main/java/org/sonar/batch/bootstrap/BootstrapClassLoader.java new file mode 100644 index 00000000000..ee91b71c595 --- /dev/null +++ b/sonar-batch/src/main/java/org/sonar/batch/bootstrap/BootstrapClassLoader.java @@ -0,0 +1,53 @@ +/* + * Sonar, open source software quality management tool. + * Copyright (C) 2009 SonarSource SA + * mailto:contact AT sonarsource DOT com + * + * Sonar is free software; you can redistribute it and/or + * modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation; either + * version 3 of the License, or (at your option) any later version. + * + * Sonar is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General Public + * License along with Sonar; if not, write to the Free Software + * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02 + */ +package org.sonar.batch.bootstrap; + +import org.sonar.api.utils.SonarException; + +import java.io.File; +import java.net.MalformedURLException; +import java.net.URL; +import java.net.URLClassLoader; + +/** + * ClassLoader extended with the JDBC Driver hosted on the server-side. + */ +public class BootstrapClassLoader { + + private URLClassLoader classLoader; + + public BootstrapClassLoader(ExtensionDownloader extensionDownloader) { + this(extensionDownloader.downloadJdbcDriver()); + } + + BootstrapClassLoader(File jdbcDriver) { + try { + ClassLoader parentClassLoader = BootstrapClassLoader.class.getClassLoader(); + classLoader = URLClassLoader.newInstance(new URL[]{jdbcDriver.toURI().toURL()}, parentClassLoader); + + } catch (MalformedURLException e) { + throw new SonarException("Fail to get URL of : " + jdbcDriver.getAbsolutePath(), e); + } + } + + public URLClassLoader getClassLoader() { + return classLoader; + } +} diff --git a/sonar-batch/src/main/java/org/sonar/batch/bootstrap/ExtensionDownloader.java b/sonar-batch/src/main/java/org/sonar/batch/bootstrap/ExtensionDownloader.java new file mode 100644 index 00000000000..ee6d1a0f108 --- /dev/null +++ b/sonar-batch/src/main/java/org/sonar/batch/bootstrap/ExtensionDownloader.java @@ -0,0 +1,69 @@ +/* + * Sonar, open source software quality management tool. + * Copyright (C) 2009 SonarSource SA + * mailto:contact AT sonarsource DOT com + * + * Sonar is free software; you can redistribute it and/or + * modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation; either + * version 3 of the License, or (at your option) any later version. + * + * Sonar is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General Public + * License along with Sonar; if not, write to the Free Software + * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02 + */ +package org.sonar.batch.bootstrap; + +import org.slf4j.LoggerFactory; +import org.sonar.api.utils.HttpDownloader; +import org.sonar.api.utils.SonarException; +import org.sonar.batch.ServerMetadata; +import org.sonar.core.plugin.JpaPluginFile; + +import java.io.File; +import java.net.URI; +import java.net.URISyntaxException; + +public final class ExtensionDownloader { + + private HttpDownloader httpDownloader; + private TempDirectories workingDirectories; + private String baseUrl; + + public ExtensionDownloader(HttpDownloader httpDownloader, TempDirectories workingDirectories, ServerMetadata server) { + this.httpDownloader = httpDownloader; + this.workingDirectories = workingDirectories; + this.baseUrl = server.getURL(); + } + + public File downloadJdbcDriver() { + String url = baseUrl + "/deploy/jdbc-driver.jar"; + try { + File jdbcDriver = new File(workingDirectories.getRoot(), "jdbc-driver.jar"); + LoggerFactory.getLogger(getClass()).debug("Download JDBC Driver from " + url + " to " + jdbcDriver.getAbsolutePath()); + httpDownloader.download(new URI(url), jdbcDriver); + return jdbcDriver; + + } catch (URISyntaxException e) { + throw new SonarException("Fail to download the JDBC driver from : " + url, e); + } + } + + public File downloadExtension(JpaPluginFile extension) { + File targetFile = new File(workingDirectories.getDir(extension.getPluginKey()), extension.getFilename()); + String url = baseUrl + "/deploy/plugins/" + extension.getPluginKey() + "/" + extension.getFilename(); + LoggerFactory.getLogger(getClass()).debug("Download " + url + " to " + targetFile.getAbsolutePath()); + try { + httpDownloader.download(new URI(url), targetFile); + return targetFile; + + } catch (URISyntaxException e) { + throw new SonarException("Can not download extension: " + url, e); + } + } +} diff --git a/sonar-batch/src/main/java/org/sonar/batch/bootstrap/TempDirectories.java b/sonar-batch/src/main/java/org/sonar/batch/bootstrap/TempDirectories.java new file mode 100644 index 00000000000..25b33c14a45 --- /dev/null +++ b/sonar-batch/src/main/java/org/sonar/batch/bootstrap/TempDirectories.java @@ -0,0 +1,82 @@ +/* + * Sonar, open source software quality management tool. + * Copyright (C) 2009 SonarSource SA + * mailto:contact AT sonarsource DOT com + * + * Sonar is free software; you can redistribute it and/or + * modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation; either + * version 3 of the License, or (at your option) any later version. + * + * Sonar is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General Public + * License along with Sonar; if not, write to the Free Software + * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02 + */ +package org.sonar.batch.bootstrap; + +import com.google.common.collect.Maps; +import org.apache.commons.io.FileUtils; +import org.apache.commons.lang.StringUtils; +import org.slf4j.LoggerFactory; +import org.sonar.api.utils.SonarException; +import org.sonar.api.utils.TempFileUtils; + +import java.io.File; +import java.io.IOException; +import java.util.Map; + +public final class TempDirectories { + + private File rootDir; + private Map directoriesByKey = Maps.newHashMap(); + + public TempDirectories() throws IOException { + this.rootDir = TempFileUtils.createTempDirectory("sonar-batch"); + LoggerFactory.getLogger(getClass()).debug("Temporary directory: " + rootDir.getAbsolutePath()); + } + + public File getRoot() { + return rootDir; + } + + /** + * Get or create a working directory + */ + public File getDir(String key) { + if (StringUtils.isBlank(key)) { + return rootDir; + } + + File dir = directoriesByKey.get(key); + if (dir == null) { + dir = new File(rootDir, key); + try { + FileUtils.forceMkdir(dir); + directoriesByKey.put(key, dir); + + } catch (IOException e) { + throw new SonarException("Can not create the temp directory: " + dir, e); + } + } + return dir; + } + + public File getFile(String directoryKey, String filename) { + File dir = getDir(directoryKey); + return new File(dir, filename); + } + + /** + * This method is executed by picocontainer during shutdown. + */ + public void stop() { + directoriesByKey.clear(); + LoggerFactory.getLogger(getClass()).debug("Delete temporary directory: " + rootDir.getAbsolutePath()); + FileUtils.deleteQuietly(rootDir); + } +} diff --git a/sonar-batch/src/test/java/org/sonar/batch/BatchPluginRepositoryTest.java b/sonar-batch/src/test/java/org/sonar/batch/bootstrap/BatchPluginRepositoryTest.java similarity index 97% rename from sonar-batch/src/test/java/org/sonar/batch/BatchPluginRepositoryTest.java rename to sonar-batch/src/test/java/org/sonar/batch/bootstrap/BatchPluginRepositoryTest.java index dacd396b820..7d5abcac22e 100644 --- a/sonar-batch/src/test/java/org/sonar/batch/BatchPluginRepositoryTest.java +++ b/sonar-batch/src/test/java/org/sonar/batch/bootstrap/BatchPluginRepositoryTest.java @@ -17,7 +17,7 @@ * License along with Sonar; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02 */ -package org.sonar.batch; +package org.sonar.batch.bootstrap; import static org.hamcrest.core.Is.is; import static org.junit.Assert.assertThat; @@ -32,6 +32,7 @@ import org.sonar.api.batch.AbstractCoverageExtension; import org.sonar.api.resources.Java; import org.sonar.api.resources.Project; import org.sonar.api.utils.IocContainer; +import org.sonar.batch.bootstrap.BatchPluginRepository; public class BatchPluginRepositoryTest { diff --git a/sonar-batch/src/test/java/org/sonar/batch/RemoteClassLoaderTest.java b/sonar-batch/src/test/java/org/sonar/batch/bootstrap/BootstrapClassLoaderTest.java similarity index 77% rename from sonar-batch/src/test/java/org/sonar/batch/RemoteClassLoaderTest.java rename to sonar-batch/src/test/java/org/sonar/batch/bootstrap/BootstrapClassLoaderTest.java index f79d4535a0e..30ab9900ae3 100644 --- a/sonar-batch/src/test/java/org/sonar/batch/RemoteClassLoaderTest.java +++ b/sonar-batch/src/test/java/org/sonar/batch/bootstrap/BootstrapClassLoaderTest.java @@ -17,25 +17,27 @@ * License along with Sonar; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02 */ -package org.sonar.batch; +package org.sonar.batch.bootstrap; import org.junit.Test; +import java.io.File; +import java.net.URISyntaxException; import java.net.URL; import java.util.Arrays; import static junit.framework.Assert.assertNotNull; import static junit.framework.Assert.assertNull; -public class RemoteClassLoaderTest { +public class BootstrapClassLoaderTest { @Test - public void testClassLoader() { + public void testClassLoader() throws URISyntaxException { /* foo.jar has just one file /foo/foo.txt */ assertNull(getClass().getClassLoader().getResource("foo/foo.txt")); - URL url = getClass().getResource("/org/sonar/batch/RemoteClassLoaderTest/foo.jar"); - RemoteClassLoader classloader = new RemoteClassLoader(Arrays.asList(url), null); + URL url = getClass().getResource("/org/sonar/batch/bootstrap/BootstrapClassLoaderTest/foo.jar"); + BootstrapClassLoader classloader = new BootstrapClassLoader(new File(url.toURI())); assertNotNull(classloader.getClassLoader()); assertNotNull(classloader.getClassLoader().getResource("foo/foo.txt")); diff --git a/sonar-batch/src/test/java/org/sonar/batch/bootstrap/ExtensionDownloaderTest.java b/sonar-batch/src/test/java/org/sonar/batch/bootstrap/ExtensionDownloaderTest.java new file mode 100644 index 00000000000..3094860d388 --- /dev/null +++ b/sonar-batch/src/test/java/org/sonar/batch/bootstrap/ExtensionDownloaderTest.java @@ -0,0 +1,68 @@ +/* + * Sonar, open source software quality management tool. + * Copyright (C) 2009 SonarSource SA + * mailto:contact AT sonarsource DOT com + * + * Sonar is free software; you can redistribute it and/or + * modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation; either + * version 3 of the License, or (at your option) any later version. + * + * Sonar is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General Public + * License along with Sonar; if not, write to the Free Software + * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02 + */ +package org.sonar.batch.bootstrap; + +import org.junit.Test; +import org.sonar.api.utils.HttpDownloader; +import org.sonar.batch.ServerMetadata; +import org.sonar.core.plugin.JpaPlugin; +import org.sonar.core.plugin.JpaPluginFile; + +import java.io.File; +import java.io.IOException; +import java.net.URI; +import java.net.URISyntaxException; + +import static org.junit.Assert.assertNotNull; +import static org.mockito.Mockito.*; + +public class ExtensionDownloaderTest { + + @Test + public void shouldDownloadJdbcDriver() throws IOException, URISyntaxException { + ServerMetadata server = mock(ServerMetadata.class); + when(server.getURL()).thenReturn("http://sonar:8000"); + + HttpDownloader httpDownloader = mock(HttpDownloader.class); + TempDirectories workingDirectories = new TempDirectories(); + + ExtensionDownloader downloader = new ExtensionDownloader(httpDownloader, workingDirectories, server); + File jdbcDriver = downloader.downloadJdbcDriver(); + + assertNotNull(jdbcDriver); + verify(httpDownloader).download(new URI("http://sonar:8000/deploy/jdbc-driver.jar"), jdbcDriver); + } + + @Test + public void shouldDownloadExtension() throws IOException, URISyntaxException { + ServerMetadata server = mock(ServerMetadata.class); + when(server.getURL()).thenReturn("http://sonar:8000"); + + HttpDownloader httpDownloader = mock(HttpDownloader.class); + TempDirectories workingDirectories = new TempDirectories(); + + ExtensionDownloader downloader = new ExtensionDownloader(httpDownloader, workingDirectories, server); + JpaPluginFile extension = new JpaPluginFile(new JpaPlugin("findbugs"), "bcel.jar"); + File bcel = downloader.downloadExtension(extension); + + assertNotNull(bcel); + verify(httpDownloader).download(new URI("http://sonar:8000/deploy/plugins/findbugs/bcel.jar"), bcel); + } +} diff --git a/sonar-batch/src/test/java/org/sonar/batch/bootstrap/TempDirectoriesTest.java b/sonar-batch/src/test/java/org/sonar/batch/bootstrap/TempDirectoriesTest.java new file mode 100644 index 00000000000..08128992195 --- /dev/null +++ b/sonar-batch/src/test/java/org/sonar/batch/bootstrap/TempDirectoriesTest.java @@ -0,0 +1,83 @@ +/* + * Sonar, open source software quality management tool. + * Copyright (C) 2009 SonarSource SA + * mailto:contact AT sonarsource DOT com + * + * Sonar is free software; you can redistribute it and/or + * modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation; either + * version 3 of the License, or (at your option) any later version. + * + * Sonar is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General Public + * License along with Sonar; if not, write to the Free Software + * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02 + */ +package org.sonar.batch.bootstrap; + +import org.junit.After; +import org.junit.Before; +import org.junit.Test; + +import java.io.File; +import java.io.IOException; + +import static org.hamcrest.CoreMatchers.is; +import static org.junit.Assert.assertNotNull; +import static org.junit.Assert.assertThat; + +public class TempDirectoriesTest { + + private TempDirectories tempDirectories; + + @Before + public void before() throws IOException { + tempDirectories = new TempDirectories(); + } + + @After + public void after() throws IOException { + if (tempDirectories != null) { + tempDirectories.stop(); + } + } + + @Test + public void shouldCreateRoot() throws IOException { + assertNotNull(tempDirectories.getRoot()); + assertThat(tempDirectories.getRoot().exists(), is(true)); + assertThat(tempDirectories.getRoot().isDirectory(), is(true)); + } + + @Test + public void shouldCreateDirectory() throws IOException { + File findbugsDir = tempDirectories.getDir("findbugs"); + assertNotNull(findbugsDir); + assertThat(findbugsDir.exists(), is(true)); + assertThat(findbugsDir.getParentFile(), is(tempDirectories.getRoot())); + assertThat(findbugsDir.getName(), is("findbugs")); + } + + @Test + public void shouldStopAndDeleteDirectory() throws IOException { + File root = tempDirectories.getRoot(); + File findbugsDir = tempDirectories.getDir("findbugs"); + assertThat(findbugsDir.exists(), is(true)); + + tempDirectories.stop(); + + assertThat(root.exists(), is(false)); + assertThat(findbugsDir.exists(), is(false)); + } + + @Test + public void shouldCreateDirectoryWhenGettingFile() { + File file = tempDirectories.getFile("findbugs", "bcel.jar"); + assertNotNull(file); + assertThat(file.getParentFile().getName(), is("findbugs")); + } +} diff --git a/sonar-batch/src/test/resources/org/sonar/batch/RemoteClassLoaderTest/foo.jar b/sonar-batch/src/test/resources/org/sonar/batch/bootstrap/BootstrapClassLoaderTest/foo.jar similarity index 100% rename from sonar-batch/src/test/resources/org/sonar/batch/RemoteClassLoaderTest/foo.jar rename to sonar-batch/src/test/resources/org/sonar/batch/bootstrap/BootstrapClassLoaderTest/foo.jar -- 2.39.5