1   package com.atlassian.plugin.osgi;
2   
3   import com.atlassian.plugin.DefaultModuleDescriptorFactory;
4   import com.atlassian.plugin.ModuleDescriptorFactory;
5   import com.atlassian.plugin.PluginAccessor;
6   import com.atlassian.plugin.manager.store.MemoryPluginPersistentStateStore;
7   import com.atlassian.plugin.manager.DefaultPluginManager;
8   import com.atlassian.plugin.hostcontainer.DefaultHostContainer;
9   import com.atlassian.plugin.event.PluginEventManager;
10  import com.atlassian.plugin.event.impl.DefaultPluginEventManager;
11  import com.atlassian.plugin.factories.LegacyDynamicPluginFactory;
12  import com.atlassian.plugin.factories.PluginFactory;
13  import com.atlassian.plugin.loaders.DirectoryPluginLoader;
14  import com.atlassian.plugin.loaders.PluginLoader;
15  import com.atlassian.plugin.loaders.BundledPluginLoader;
16  import com.atlassian.plugin.osgi.container.OsgiContainerManager;
17  import com.atlassian.plugin.osgi.container.PackageScannerConfiguration;
18  import com.atlassian.plugin.osgi.container.OsgiPersistentCache;
19  import com.atlassian.plugin.osgi.container.felix.FelixOsgiContainerManager;
20  import com.atlassian.plugin.osgi.container.impl.DefaultPackageScannerConfiguration;
21  import com.atlassian.plugin.osgi.container.impl.DefaultOsgiPersistentCache;
22  import com.atlassian.plugin.osgi.factory.OsgiPluginFactory;
23  import com.atlassian.plugin.osgi.factory.OsgiBundleFactory;
24  import com.atlassian.plugin.osgi.hostcomponents.ComponentRegistrar;
25  import com.atlassian.plugin.osgi.hostcomponents.HostComponentProvider;
26  import com.atlassian.plugin.osgi.hostcomponents.InstanceBuilder;
27  import com.atlassian.plugin.repositories.FilePluginInstaller;
28  
29  import org.apache.commons.io.FileUtils;
30  import org.apache.commons.io.IOUtils;
31  
32  import java.io.*;
33  import java.util.Arrays;
34  import java.util.zip.ZipOutputStream;
35  import java.util.zip.ZipEntry;
36  
37  import junit.framework.TestCase;
38  
39  /**
40   * Base for in-container unit tests
41   */
42  public abstract class PluginInContainerTestBase extends TestCase
43  {
44      protected OsgiContainerManager osgiContainerManager;
45      protected File tmpDir;
46      protected File cacheDir;
47      protected File pluginsDir;
48      protected ModuleDescriptorFactory moduleDescriptorFactory;
49      protected DefaultPluginManager pluginManager;
50      protected PluginEventManager pluginEventManager;
51  
52      @Override
53      public void setUp() throws Exception
54      {
55          tmpDir = new File("target/plugin-temp").getAbsoluteFile();
56          if (tmpDir.exists())
57          {
58              FileUtils.cleanDirectory(tmpDir);
59          }
60          tmpDir.mkdirs();
61          cacheDir = new File(tmpDir, "cache");
62          cacheDir.mkdir();
63          pluginsDir = new File(tmpDir, "plugins");
64          pluginsDir.mkdir();
65          this.pluginEventManager = new DefaultPluginEventManager();
66      }
67  
68      @Override
69      public void tearDown() throws Exception
70      {
71          if (osgiContainerManager != null)
72          {
73              osgiContainerManager.stop();
74          }
75          FileUtils.deleteDirectory(tmpDir);
76          osgiContainerManager = null;
77          tmpDir = null;
78          pluginsDir = null;
79          moduleDescriptorFactory = null;
80          pluginManager = null;
81          pluginEventManager = null;
82      }
83  
84      protected void initPluginManager() throws Exception
85      {
86          initPluginManager(null, new DefaultModuleDescriptorFactory(new DefaultHostContainer()));
87      }
88  
89      protected void initPluginManager(final HostComponentProvider hostComponentProvider) throws Exception
90      {
91          initPluginManager(hostComponentProvider, new DefaultModuleDescriptorFactory(new DefaultHostContainer()));
92      }
93  
94      protected void initPluginManager(final HostComponentProvider hostComponentProvider, final ModuleDescriptorFactory moduleDescriptorFactory) throws Exception
95      {
96          initPluginManager(hostComponentProvider, moduleDescriptorFactory, null);
97      }
98  
99      protected void initPluginManager(final HostComponentProvider hostComponentProvider, final ModuleDescriptorFactory moduleDescriptorFactory, final String version) throws Exception
100     {
101         this.moduleDescriptorFactory = moduleDescriptorFactory;
102         final PackageScannerConfiguration scannerConfig = buildScannerConfiguration(version);
103         HostComponentProvider requiredWrappingProvider = getWrappingHostComponentProvider(hostComponentProvider);
104         OsgiPersistentCache cache = new DefaultOsgiPersistentCache(cacheDir);
105         osgiContainerManager = new FelixOsgiContainerManager(cache, scannerConfig, requiredWrappingProvider, pluginEventManager);
106 
107         final LegacyDynamicPluginFactory legacyFactory = new LegacyDynamicPluginFactory(PluginAccessor.Descriptor.FILENAME, tmpDir);
108         final OsgiPluginFactory osgiPluginDeployer = new OsgiPluginFactory(PluginAccessor.Descriptor.FILENAME, (String) null, cache, osgiContainerManager, pluginEventManager);
109         final OsgiBundleFactory osgiBundleFactory = new OsgiBundleFactory(osgiContainerManager, pluginEventManager);
110 
111         final DirectoryPluginLoader loader = new DirectoryPluginLoader(pluginsDir, Arrays.asList(legacyFactory, osgiPluginDeployer, osgiBundleFactory),
112             new DefaultPluginEventManager());
113 
114         pluginManager = new DefaultPluginManager(new MemoryPluginPersistentStateStore(), Arrays.<PluginLoader> asList(loader), moduleDescriptorFactory,
115             pluginEventManager);
116         pluginManager.setPluginInstaller(new FilePluginInstaller(pluginsDir));
117         pluginManager.init();
118     }
119 
120     protected void initBundlingPluginManager(final ModuleDescriptorFactory moduleDescriptorFactory, File... bundledPluginJars) throws Exception
121     {
122         this.moduleDescriptorFactory = moduleDescriptorFactory;
123         final PackageScannerConfiguration scannerConfig = buildScannerConfiguration("1.0");
124         HostComponentProvider requiredWrappingProvider = getWrappingHostComponentProvider(null);
125         OsgiPersistentCache cache = new DefaultOsgiPersistentCache(cacheDir);
126         osgiContainerManager = new FelixOsgiContainerManager(cache, scannerConfig, requiredWrappingProvider, pluginEventManager);
127 
128         final OsgiPluginFactory osgiPluginDeployer = new OsgiPluginFactory(PluginAccessor.Descriptor.FILENAME, (String) null, cache, osgiContainerManager, pluginEventManager);
129 
130         final DirectoryPluginLoader loader = new DirectoryPluginLoader(pluginsDir, Arrays.<PluginFactory>asList(osgiPluginDeployer),
131             new DefaultPluginEventManager());
132 
133         File zip = new File(bundledPluginJars[0].getParentFile(), "bundled-plugins.zip");
134         for (File bundledPluginJar : bundledPluginJars)
135         {
136             ZipOutputStream stream = null;
137             InputStream in = null;
138             try
139             {
140                 stream = new ZipOutputStream(new FileOutputStream(zip));
141                 in = new FileInputStream(bundledPluginJar);
142                 stream.putNextEntry(new ZipEntry(bundledPluginJar.getName()));
143                 IOUtils.copy(in, stream);
144                 stream.closeEntry();
145             }
146             catch (IOException ex)
147             {
148                 IOUtils.closeQuietly(in);
149                 IOUtils.closeQuietly(stream);
150             }
151         }
152         File bundledDir = new File(bundledPluginJars[0].getParentFile(), "bundled-plugins");
153         final BundledPluginLoader bundledLoader = new BundledPluginLoader(zip.toURL(), bundledDir, Arrays.<PluginFactory>asList(osgiPluginDeployer),
154             new DefaultPluginEventManager());
155 
156         pluginManager = new DefaultPluginManager(new MemoryPluginPersistentStateStore(), Arrays.<PluginLoader> asList(bundledLoader, loader), moduleDescriptorFactory,
157             pluginEventManager);
158         pluginManager.setPluginInstaller(new FilePluginInstaller(pluginsDir));
159         pluginManager.init();
160     }
161 
162     private HostComponentProvider getWrappingHostComponentProvider(final HostComponentProvider hostComponentProvider)
163     {
164         HostComponentProvider requiredWrappingProvider = new HostComponentProvider()
165         {
166             public void provide(final ComponentRegistrar registrar)
167             {
168 
169                 if (hostComponentProvider != null)
170                 {
171                     hostComponentProvider.provide(new ComponentRegistrar()
172                     {
173                         public InstanceBuilder register(Class<?>... mainInterfaces)
174                         {
175                             if (!Arrays.asList(mainInterfaces).contains(PluginEventManager.class))
176                             {
177                                 return registrar.register(mainInterfaces);
178                             }
179                             return null;
180                         }
181                     });
182                 }
183                 registrar.register(PluginEventManager.class).forInstance(pluginEventManager);
184             }
185         };
186         return requiredWrappingProvider;
187     }
188 
189     private PackageScannerConfiguration buildScannerConfiguration(String version)
190     {
191         final PackageScannerConfiguration scannerConfig = new DefaultPackageScannerConfiguration(version);
192         scannerConfig.getPackageIncludes().add("com.atlassian.plugin*");
193         scannerConfig.getPackageIncludes().add("javax.servlet*");
194         scannerConfig.getPackageIncludes().add("com_cenqua_clover");
195         scannerConfig.getPackageExcludes().add("com.atlassian.plugin.osgi.bridge*");
196         return scannerConfig;
197     }
198 }