diff --git a/container-api/src/main/java/org/jboss/forge/furnace/addons/AddonDependency.java b/container-api/src/main/java/org/jboss/forge/furnace/addons/AddonDependency.java
index e2f4298d..4b2e215a 100644
--- a/container-api/src/main/java/org/jboss/forge/furnace/addons/AddonDependency.java
+++ b/container-api/src/main/java/org/jboss/forge/furnace/addons/AddonDependency.java
@@ -6,7 +6,6 @@
*/
package org.jboss.forge.furnace.addons;
-import org.jboss.forge.furnace.versions.Version;
/**
* An edge in the registered {@link Addon} graph.
@@ -15,21 +14,11 @@
*/
public interface AddonDependency
{
- /**
- * Get the {@link Addon} dependent on the {@link Addon} returned by {@link #getDependency()}.
- */
- public Addon getDependent();
-
/**
* Get the {@link Addon} dependency of the {@link Addon} returned by {@link #getDependent()}.
*/
public Addon getDependency();
- /**
- * Return the {@link Version} of which the {@link Addon} returned by {@link #getDependency()} must be included.
- */
- public Version getDependencyVersion();
-
/**
* Return true
if the {@link Addon} dependency returned by {@link #getDependency()} is exported by the
* dependent {@link Addon}. If the dependency is not exported, return false
.
diff --git a/container-tests/src/test/java/org/jboss/forge/furnace/views/MultipleRepositoryViewTest.java b/container-tests/src/test/java/org/jboss/forge/furnace/views/MultipleRepositoryViewTest.java
index f2626946..8cb57110 100644
--- a/container-tests/src/test/java/org/jboss/forge/furnace/views/MultipleRepositoryViewTest.java
+++ b/container-tests/src/test/java/org/jboss/forge/furnace/views/MultipleRepositoryViewTest.java
@@ -10,13 +10,11 @@
import java.io.IOException;
import java.util.concurrent.TimeUnit;
-import org.jboss.forge.addon.convert.ConverterFactory;
import org.jboss.forge.addon.manager.AddonManager;
import org.jboss.forge.addon.manager.impl.AddonManagerImpl;
import org.jboss.forge.addon.maven.dependencies.FileResourceFactory;
import org.jboss.forge.addon.maven.dependencies.MavenContainer;
import org.jboss.forge.addon.maven.dependencies.MavenDependencyResolver;
-import org.jboss.forge.addon.resource.DirectoryResource;
import org.jboss.forge.arquillian.ConfigurationScanListener;
import org.jboss.forge.furnace.Furnace;
import org.jboss.forge.furnace.addons.Addon;
@@ -25,7 +23,6 @@
import org.jboss.forge.furnace.repositories.AddonRepository;
import org.jboss.forge.furnace.repositories.AddonRepositoryMode;
import org.jboss.forge.furnace.se.ForgeFactory;
-import org.jboss.forge.furnace.services.ExportedInstance;
import org.jboss.forge.furnace.spi.ContainerLifecycleListener;
import org.jboss.forge.furnace.spi.ListenerRegistration;
import org.jboss.forge.furnace.util.Addons;
@@ -60,7 +57,7 @@ public void teardown()
}
@Test
- public void testAddonsCanBeSharedBetweenViews() throws IOException, InterruptedException
+ public void testAddonsSharedIfSubgraphEquivalent() throws IOException, InterruptedException
{
Furnace furnace = ForgeFactory.getInstance(Furnace.class.getClassLoader());
AddonRepository left = furnace.addRepository(AddonRepositoryMode.MUTABLE, repodir1);
@@ -121,7 +118,7 @@ public void testAddonsCanBeSharedBetweenViews() throws IOException, InterruptedE
}
@Test
- public void testAddonsDontFailIfDuplicatedInOtherRepositories() throws IOException, Exception
+ public void testAddonsDuplicatedIfSubgraphDiffers() throws IOException, InterruptedException
{
Furnace furnace = ForgeFactory.getInstance(Furnace.class.getClassLoader());
AddonRepository left = furnace.addRepository(AddonRepositoryMode.MUTABLE, repodir1);
@@ -131,43 +128,59 @@ public void testAddonsDontFailIfDuplicatedInOtherRepositories() throws IOExcepti
new MavenContainer());
AddonManager manager = new AddonManagerImpl(furnace, resolver);
- AddonId facets = AddonId.from("org.jboss.forge.addon:facets", "2.0.0-SNAPSHOT");
- AddonId convert = AddonId.from("org.jboss.forge.addon:convert", "2.0.0-SNAPSHOT");
- AddonId resources = AddonId.from("org.jboss.forge.addon:resources", "2.0.0-SNAPSHOT");
+ AddonId facets = AddonId.from("org.jboss.forge.addon:facets", "2.0.0.Alpha5");
+ AddonId convert = AddonId.from("org.jboss.forge.addon:convert", "2.0.0.Alpha5");
+ AddonId resources = AddonId.from("org.jboss.forge.addon:resources", "2.0.0.Alpha5");
+ AddonId dependencies = AddonId.from("org.jboss.forge.addon:dependencies", "2.0.0.Alpha5");
+
+ AddonId facets6 = AddonId.from("org.jboss.forge.addon:facets", "2.0.0.Alpha6");
+ Assert.assertFalse(left.isDeployed(dependencies));
Assert.assertFalse(left.isDeployed(resources));
Assert.assertFalse(left.isDeployed(facets));
+ Assert.assertFalse(left.isDeployed(facets6));
Assert.assertFalse(left.isDeployed(convert));
+ Assert.assertFalse(right.isDeployed(dependencies));
Assert.assertFalse(right.isDeployed(resources));
Assert.assertFalse(right.isDeployed(facets));
+ Assert.assertFalse(right.isDeployed(facets6));
Assert.assertFalse(right.isDeployed(convert));
manager.install(facets).perform(left);
manager.install(convert).perform(left);
manager.install(resources).perform(left);
- manager.install(resources).perform(right);
+ manager.install(dependencies).perform(left);
- Assert.assertFalse(right.isDeployed(facets));
- Assert.assertFalse(right.isDeployed(convert));
- Assert.assertTrue(left.isDeployed(resources));
+ manager.install(facets6).perform(right);
+
+ Assert.assertTrue(left.isDeployed(facets));
Assert.assertTrue(left.isDeployed(convert));
Assert.assertTrue(left.isDeployed(resources));
- Assert.assertTrue(right.isDeployed(resources));
+ Assert.assertTrue(left.isDeployed(dependencies));
+ Assert.assertFalse(left.isDeployed(facets6));
+
+ Assert.assertFalse(right.isDeployed(facets));
+ Assert.assertFalse(right.isDeployed(convert));
+ Assert.assertFalse(right.isDeployed(resources));
+ Assert.assertFalse(right.isDeployed(dependencies));
+ Assert.assertTrue(right.isDeployed(facets6));
furnace.startAsync();
- Addons.waitUntilStarted(furnace.getAddonRegistry().getAddon(resources), 10, TimeUnit.SECONDS);
- Addons.waitUntilStarted(furnace.getAddonRegistry().getAddon(facets), 10, TimeUnit.SECONDS);
- Addons.waitUntilStarted(furnace.getAddonRegistry().getAddon(convert), 10, TimeUnit.SECONDS);
+ ConfigurationScanListener listener = new ConfigurationScanListener();
+ ListenerRegistration registration = furnace.addContainerLifecycleListener(listener);
+
+ while (!listener.isConfigurationScanned())
+ Thread.sleep(100);
+
+ AddonRegistry registry = furnace.getAddonRegistry();
+ Addons.waitUntilStarted(registry.getAddon(resources), 10, TimeUnit.SECONDS);
+ AddonRegistry leftRegistry = furnace.getAddonRegistry(left);
- System.out.println("Getting instances.");
- ExportedInstance instance = furnace.getAddonRegistry()
- .getExportedInstance(ConverterFactory.class);
- ConverterFactory factory = instance.get();
+ Addon addon = leftRegistry.getAddon(facets);
+ Assert.assertNotNull(addon);
- factory.getConverter(File.class,
- furnace.getAddonRegistry().getAddon(resources).getClassLoader()
- .loadClass(DirectoryResource.class.getName()));
+ registration.removeListener();
furnace.stop();
}
diff --git a/container/src/main/java/org/jboss/forge/furnace/FurnaceImpl.java b/container/src/main/java/org/jboss/forge/furnace/FurnaceImpl.java
index 6d701e76..ab3f8a9e 100644
--- a/container/src/main/java/org/jboss/forge/furnace/FurnaceImpl.java
+++ b/container/src/main/java/org/jboss/forge/furnace/FurnaceImpl.java
@@ -14,7 +14,6 @@
import java.util.List;
import java.util.Map;
import java.util.ServiceLoader;
-import java.util.Set;
import java.util.logging.Level;
import java.util.logging.Logger;
@@ -30,7 +29,6 @@
import org.jboss.forge.furnace.spi.ContainerLifecycleListener;
import org.jboss.forge.furnace.spi.ListenerRegistration;
import org.jboss.forge.furnace.util.Assert;
-import org.jboss.forge.furnace.util.Sets;
import org.jboss.forge.furnace.versions.Version;
import org.jboss.modules.Module;
import org.jboss.modules.log.StreamModuleLogger;
@@ -56,7 +54,6 @@ public class FurnaceImpl implements Furnace
private Map lastRepoVersionSeen = new HashMap();
private final LockManager lock = new LockManagerImpl();
- private final Set views = Sets.getConcurrentSet();
private String[] args;
@@ -141,7 +138,7 @@ public Furnace start(ClassLoader loader)
do
{
boolean dirty = false;
- if (!manager.isStartingAddons(views))
+ if (!manager.isStartingAddons())
{
for (AddonRepository repository : repositories)
{
@@ -159,7 +156,7 @@ public Furnace start(ClassLoader loader)
try
{
fireBeforeConfigurationScanEvent();
- manager.forceUpdate(views);
+ manager.forceUpdate();
fireAfterConfigurationScanEvent();
}
catch (Exception e)
@@ -172,7 +169,7 @@ public Furnace start(ClassLoader loader)
}
while (alive && serverMode);
- while (alive && manager.isStartingAddons(views))
+ while (alive && manager.isStartingAddons())
{
Thread.sleep(100);
}
@@ -269,50 +266,26 @@ public AddonRegistry getAddonRegistry(AddonRepository... repositories)
{
assertIsAlive();
- AddonRegistry result = findView(repositories);
+ AddonRegistry result = manager.findView(repositories);
if (result == null)
{
if (repositories == null || repositories.length == 0)
{
result = new AddonRegistryImpl(lock, manager, getRepositories(), "ROOT");
- views.add(result);
+ manager.addView(result);
}
else
{
result = new AddonRegistryImpl(lock, manager, Arrays.asList(repositories), String.valueOf(registryCount++));
- views.add(result);
- manager.forceUpdate(views);
+ manager.addView(result);
+ manager.forceUpdate();
}
}
return result;
}
- private AddonRegistry findView(AddonRepository... repositories)
- {
- AddonRegistry result = null;
-
- for (AddonView view : views)
- {
- Set viewRepositories = view.getRepositories();
- if (repositories == null || repositories.length == 0)
- {
- if (viewRepositories.containsAll(getRepositories()) && getRepositories().containsAll(viewRepositories))
- result = (AddonRegistry) view;
- }
- else if (viewRepositories.containsAll(Arrays.asList(repositories))
- && Arrays.asList(repositories).containsAll(viewRepositories))
- {
- result = (AddonRegistry) view;
- }
-
- if (result != null)
- break;
- }
- return result;
- }
-
public void disposeAddonView(AddonView view)
{
assertIsAlive();
@@ -321,12 +294,8 @@ public void disposeAddonView(AddonView view)
throw new IllegalArgumentException(
"Cannot dispose the root AddonRegistry. Call .stop() instead.");
- if (!views.contains(view))
- throw new IllegalArgumentException("The given AddonRegistry does not belong to this Furnace instance.");
-
- views.remove(view);
-
- manager.forceUpdate(views);
+ manager.removeView(view);
+ manager.forceUpdate();
}
@Override
@@ -402,7 +371,7 @@ public ContainerStatus getStatus()
if (!alive)
return ContainerStatus.STOPPED;
- boolean startingAddons = manager.isStartingAddons(views);
+ boolean startingAddons = manager.isStartingAddons();
return startingAddons ? ContainerStatus.STARTING : status;
}
@@ -416,11 +385,6 @@ public AddonLifecycleManager getAddonLifecycleManager()
return manager;
}
- public Set getViews()
- {
- return views;
- }
-
@Override
public String toString()
{
diff --git a/container/src/main/java/org/jboss/forge/furnace/addons/AddonDependencyImpl.java b/container/src/main/java/org/jboss/forge/furnace/addons/AddonDependencyImpl.java
index ebc301a3..a9562abf 100644
--- a/container/src/main/java/org/jboss/forge/furnace/addons/AddonDependencyImpl.java
+++ b/container/src/main/java/org/jboss/forge/furnace/addons/AddonDependencyImpl.java
@@ -6,63 +6,40 @@
*/
package org.jboss.forge.furnace.addons;
-import org.jboss.forge.furnace.addons.Addon;
-import org.jboss.forge.furnace.addons.AddonDependency;
import org.jboss.forge.furnace.lock.LockManager;
import org.jboss.forge.furnace.util.Assert;
-import org.jboss.forge.furnace.versions.Version;
/**
* An edge in the registered {@link Addon} graph.
- *
+ *
* @author Lincoln Baxter, III
*/
public class AddonDependencyImpl implements AddonDependency
{
- private final Addon dependent;
-
private boolean exported = false;
private boolean optional = false;
private Addon dependency;
- private Version dependencyVersion;
@SuppressWarnings("unused")
private LockManager lockManager;
- public AddonDependencyImpl(LockManager lockManager,
- Addon dependent, Version dependencyVersion, Addon dependency, boolean exported, boolean optional)
+ public AddonDependencyImpl(LockManager lockManager, Addon dependency, boolean exported, boolean optional)
{
Assert.notNull(lockManager, "LockManager must not be null.");
- Assert.notNull(dependent, "Dependent Addon must not be null.");
- Assert.notNull(dependencyVersion, "VersionRange must not be null.");
Assert.notNull(dependency, "Dependency Addon not be null.");
this.lockManager = lockManager;
- this.dependent = dependent;
- this.dependencyVersion = dependencyVersion;
this.dependency = dependency;
this.exported = exported;
this.optional = optional;
}
- @Override
- public Addon getDependent()
- {
- return dependent;
- }
-
@Override
public Addon getDependency()
{
return dependency;
}
- @Override
- public Version getDependencyVersion()
- {
- return dependencyVersion;
- }
-
@Override
public boolean isExported()
{
diff --git a/container/src/main/java/org/jboss/forge/furnace/addons/AddonImpl.java b/container/src/main/java/org/jboss/forge/furnace/addons/AddonImpl.java
index 732360a1..ad20e9c9 100644
--- a/container/src/main/java/org/jboss/forge/furnace/addons/AddonImpl.java
+++ b/container/src/main/java/org/jboss/forge/furnace/addons/AddonImpl.java
@@ -6,72 +6,29 @@
*/
package org.jboss.forge.furnace.addons;
-import java.util.Collections;
import java.util.Set;
import java.util.concurrent.Future;
-import org.jboss.forge.furnace.lock.LockManager;
-import org.jboss.forge.furnace.modules.AddonModuleLoader;
import org.jboss.forge.furnace.repositories.AddonRepository;
import org.jboss.forge.furnace.services.ServiceRegistry;
import org.jboss.forge.furnace.util.Assert;
-import org.jboss.forge.furnace.util.CompletedFuture;
-import org.jboss.forge.furnace.util.Sets;
-import org.jboss.modules.Module;
+import org.jboss.forge.furnace.util.NullFuture;
/**
* @author Lincoln Baxter, III
*/
public class AddonImpl implements Addon
{
- private static class Memento
- {
- public Set dependencies = Sets.getConcurrentSet();
- public Set missingDependencies = Sets.getConcurrentSet();
-
- public AddonModuleLoader moduleLoader;
- public Module module;
- public AddonRunnable runnable;
- public Future future = new CompletedFuture(null);
- public AddonRepository repository;
- public ServiceRegistry registry;
- }
-
- public Set views = Sets.getConcurrentSet();
- @SuppressWarnings("unused")
- private final LockManager lock;
private final AddonId id;
- private Memento state = new Memento();
+ private AddonStateManager manager;
- public AddonImpl(LockManager lock, AddonId id)
+ public AddonImpl(AddonStateManager manager, AddonId id)
{
- Assert.notNull(lock, "LockManager must not be null.");
+ Assert.notNull(manager, "Manager must not be null.");
Assert.notNull(id, "AddonId must not be null.");
this.id = id;
- this.lock = lock;
- }
-
- public boolean canBeStarted()
- {
- return getRunnable() == null && getStatus().isLoaded();
- }
-
- public boolean cancelFuture()
- {
- boolean result = false;
- Future future = getFuture();
- if (future != null && !future.isDone())
- result = future.cancel(true);
- return result;
- }
-
- public void reset()
- {
- if (getModuleLoader() != null)
- getModuleLoader().releaseAddonModule(views, id);
- this.state = new Memento();
- this.views.clear();
+ this.manager = manager;
}
@Override
@@ -83,79 +40,31 @@ public AddonId getId()
@Override
public Set getDependencies()
{
- return Collections.unmodifiableSet(state.dependencies);
- }
-
- public void setDependencies(Set dependencies)
- {
- Assert.notNull(dependencies, "Dependencies must not be null.");
-
- this.state.dependencies = Sets.getConcurrentSet();
- this.state.dependencies.addAll(dependencies);
+ return manager.getDependenciesOf(this);
}
@Override
public ClassLoader getClassLoader()
{
- if (state.module != null)
- return state.module.getClassLoader();
- return null;
- }
-
- public Module getModule()
- {
- return state.module;
- }
-
- public Addon setModule(Module module)
- {
- this.state.module = module;
- return this;
- }
-
- public AddonModuleLoader getModuleLoader()
- {
- return state.moduleLoader;
+ return manager.getClassLoaderOf(this);
}
- public void setModuleLoader(AddonModuleLoader moduleLoader)
+ @Override
+ public Future getFuture()
{
- this.state.moduleLoader = moduleLoader;
+ return manager.getFutureOf(this);
}
@Override
public AddonRepository getRepository()
{
- return state.repository;
- }
-
- public void setRepository(AddonRepository repository)
- {
- this.state.repository = repository;
+ return manager.getRepositoryOf(this);
}
@Override
public ServiceRegistry getServiceRegistry()
{
- return state.registry;
- }
-
- public Addon setServiceRegistry(ServiceRegistry registry)
- {
- Assert.notNull(registry, "Registry must not be null.");
- this.state.registry = registry;
- return this;
- }
-
- public Set getViews()
- {
- return this.views;
- }
-
- public void setViews(Set views)
- {
- this.views.clear();
- this.views.addAll(views);
+ return manager.getServiceRegistryOf(this);
}
@Override
@@ -163,12 +72,12 @@ public AddonStatus getStatus()
{
AddonStatus result = AddonStatus.MISSING;
- if (getClassLoader() != null && getMissingDependencies().isEmpty())
+ if (getClassLoader() != null)
result = AddonStatus.LOADED;
if (getFuture() != null)
{
- if (!(getFuture() instanceof CompletedFuture))
+ if (!(getFuture() instanceof NullFuture))
{
if (getFuture().isDone())
result = AddonStatus.STARTED;
@@ -181,48 +90,12 @@ public AddonStatus getStatus()
return result;
}
- public void setMissingDependencies(Set missingDependencies)
- {
- Assert.notNull(missingDependencies, "Missing dependencies must not be null.");
-
- this.state.missingDependencies = Sets.getConcurrentSet();
- this.state.missingDependencies.addAll(missingDependencies);
- }
-
- public Set getMissingDependencies()
- {
- return Collections.unmodifiableSet(state.missingDependencies);
- }
-
- @Override
- public Future getFuture()
- {
- return state.future;
- }
-
- public void setFuture(Future future)
- {
- Assert.notNull(future, "Future must not be null.");
- this.state.future = future;
- }
-
- public AddonRunnable getRunnable()
- {
- return state.runnable;
- }
-
- public void setRunnable(AddonRunnable runnable)
- {
- Assert.notNull(runnable, "Runnable must not be null.");
- this.state.runnable = runnable;
- }
-
@Override
public String toString()
{
StringBuilder builder = new StringBuilder();
builder.append(getId().toCoordinates() + " +" + getStatus());
- if (canBeStarted())
+ if (getFuture() == null)
builder.append(" READY");
builder.append(" HC: ").append(hashCode());
return builder.toString();
@@ -234,7 +107,6 @@ public int hashCode()
final int prime = 31;
int result = 1;
result = prime * result + ((id == null) ? 0 : id.hashCode());
- result = prime * result + ((views == null) ? 0 : views.hashCode());
return result;
}
@@ -255,13 +127,6 @@ public boolean equals(Object obj)
}
else if (!id.equals(other.id))
return false;
- if (views == null)
- {
- if (other.views != null)
- return false;
- }
- else if (!views.equals(other.views))
- return false;
return true;
}
}
diff --git a/container/src/main/java/org/jboss/forge/furnace/addons/AddonLifecycleManager.java b/container/src/main/java/org/jboss/forge/furnace/addons/AddonLifecycleManager.java
index 8ee9ec4d..f7e842cc 100644
--- a/container/src/main/java/org/jboss/forge/furnace/addons/AddonLifecycleManager.java
+++ b/container/src/main/java/org/jboss/forge/furnace/addons/AddonLifecycleManager.java
@@ -6,10 +6,9 @@
*/
package org.jboss.forge.furnace.addons;
-import java.util.Collections;
+import java.util.Arrays;
import java.util.HashSet;
import java.util.Iterator;
-import java.util.LinkedHashSet;
import java.util.List;
import java.util.Set;
import java.util.concurrent.Callable;
@@ -20,6 +19,7 @@
import java.util.logging.Logger;
import org.jboss.forge.furnace.FurnaceImpl;
+import org.jboss.forge.furnace.exception.ContainerException;
import org.jboss.forge.furnace.impl.graph.CompleteAddonGraph;
import org.jboss.forge.furnace.impl.graph.MasterGraph;
import org.jboss.forge.furnace.impl.graph.MasterGraphChangeHandler;
@@ -30,6 +30,7 @@
import org.jboss.forge.furnace.util.AddonFilters;
import org.jboss.forge.furnace.util.Assert;
import org.jboss.forge.furnace.util.Callables;
+import org.jboss.forge.furnace.util.ClassLoaders;
import org.jboss.forge.furnace.util.Sets;
/**
@@ -39,16 +40,15 @@ public class AddonLifecycleManager
{
private static final Logger logger = Logger.getLogger(AddonLifecycleManager.class.getName());
- private final AtomicInteger starting = new AtomicInteger(-1);
- private final ExecutorService executor = Executors.newCachedThreadPool();
-
- private FurnaceImpl furnace;
private final LockManager lock;
-
- private Set addons = Sets.getConcurrentSet();
+ private FurnaceImpl furnace;
private AddonLoader loader;
+ private AddonStateManager stateManager;
- private MasterGraph currentGraph;
+ private Set addons = Sets.getConcurrentSet();
+ private final Set views = Sets.getConcurrentSet();
+ private final AtomicInteger starting = new AtomicInteger(-1);
+ private final ExecutorService executor = Executors.newCachedThreadPool();
public AddonLifecycleManager(FurnaceImpl furnace)
{
@@ -56,20 +56,19 @@ public AddonLifecycleManager(FurnaceImpl furnace)
this.furnace = furnace;
this.lock = furnace.getLockManager();
+ this.stateManager = new AddonStateManager(lock);
+ this.loader = new AddonLoader(furnace, this, stateManager);
logger.log(Level.FINE, "Instantiated AddonRTegistryImpl: " + this);
}
- private AddonLoader getAddonLoader()
+ public Addon getAddon(Set views, AddonId id)
{
- if (loader == null)
- loader = new AddonLoader(furnace, this);
- return loader;
- }
+ Assert.notNull(views, "Addon view set must not be null.");
+ Assert.isTrue(!views.isEmpty(), "Addon view set must not be empty.");
+ Assert.notNull(id, "Addon ID must not be null.");
- public void add(Addon addon)
- {
- addons.add(addon);
+ return getAddon(views.iterator().next(), id);
}
public Addon getAddon(final AddonView view, final AddonId id)
@@ -91,6 +90,12 @@ public Addon call() throws Exception
}
}
+ if (result == null)
+ {
+ result = new AddonImpl(stateManager, id);
+ addons.add(result);
+ }
+
return result;
}
});
@@ -110,10 +115,10 @@ public Set call() throws Exception
{
HashSet result = new HashSet();
+ AddonViewFilter viewFilter = new AddonViewFilter(stateManager, view);
for (Addon addon : addons)
{
- Set views = ((AddonImpl) addon).getViews();
- if (views.contains(view) && filter.accept(addon))
+ if (viewFilter.accept(addon) && filter.accept(addon))
result.add(addon);
}
@@ -122,24 +127,7 @@ public Set call() throws Exception
});
}
- @Override
- public String toString()
- {
- StringBuilder builder = new StringBuilder();
-
- Iterator addonsIterator = addons.iterator();
- while (addonsIterator.hasNext())
- {
- Addon addon = addonsIterator.next();
- builder.append("- ").append(addon.toString());
- if (addonsIterator.hasNext())
- builder.append("\n");
- }
-
- return builder.toString();
- }
-
- public void forceUpdate(final Set views)
+ public void forceUpdate()
{
lock.performLocked(LockMode.WRITE, new Callable()
{
@@ -164,17 +152,15 @@ public Void call() throws Exception
System.out.println(master);
}
- MasterGraph last = currentGraph;
- currentGraph = master;
+ MasterGraph last = stateManager.getCurrentGraph();
+ stateManager.setCurrentGraph(master);
for (Addon addon : addons)
{
- Callables.call(new StopAddonCallable(addon));
+ Callables.call(new StopAddonCallable(stateManager, addon));
}
- addons.clear();
- new MasterGraphChangeHandler(AddonLifecycleManager.this, last, master)
- .hotSwapChanges(getAddonLoader());
+ new MasterGraphChangeHandler(AddonLifecycleManager.this, stateManager, last, master).hotSwapChanges();
return null;
}
@@ -190,10 +176,7 @@ public Void call() throws Exception
{
for (Addon addon : addons)
{
- if (addon instanceof AddonImpl)
- {
- new StopAddonCallable(addon).call();
- }
+ new StopAddonCallable(stateManager, addon).call();
}
List waiting = executor.shutdownNow();
@@ -205,28 +188,15 @@ public Void call() throws Exception
});
}
- private Set getAllEnabled(Set repositories)
- {
- Set result = new HashSet();
- for (AddonRepository repository : repositories)
- {
- for (AddonId enabled : repository.listEnabled())
- {
- result.add(enabled);
- }
- }
- return result;
- }
-
- public void finishedStarting(AddonImpl addon)
+ public void finishedStarting(Addon addon)
{
starting.decrementAndGet();
}
/**
- * Returns true
if there are currently any Addons being started.
+ * Returns true
if there are currently any Addons being started. (Non-blocking.)
*/
- public boolean isStartingAddons(Set views)
+ public boolean isStartingAddons()
{
if (starting.get() == -1)
return false;
@@ -234,38 +204,94 @@ public boolean isStartingAddons(Set views)
return starting.get() > 0;
}
- public Set getRepositories()
+ public void dispose(AddonView view)
{
- return Collections.unmodifiableSet(new LinkedHashSet(furnace.getRepositories()));
+ furnace.disposeAddonView(view);
}
- public AddonId resolve(AddonView view, final String name)
+ public void startAddon(Addon addon)
{
- Assert.notNull(name, "Addon name must not be null.");
- AddonId result = null;
- for (AddonId id : getAllEnabled(view.getRepositories()))
+ Assert.notNull(addon, "Addon to start must not be null.");
+ Callables.call(new StartEnabledAddonCallable(furnace, this, stateManager, executor, starting, addon));
+ }
+
+ public AddonView getRootView()
+ {
+ return furnace.getAddonRegistry();
+ }
+
+ public void addView(AddonView view)
+ {
+ this.views.add(view);
+ }
+
+ public AddonRegistry findView(AddonRepository... repositories)
+ {
+ AddonRegistry result = null;
+ List furnaceRepositories = furnace.getRepositories();
+
+ for (AddonView view : views)
{
- if (name.equals(id.getName()) && (result == null || id.getVersion().compareTo(result.getVersion()) >= 0))
- result = id;
- }
+ Set viewRepositories = view.getRepositories();
+ if (repositories == null || repositories.length == 0)
+ {
+ if (viewRepositories.containsAll(furnaceRepositories)
+ && furnaceRepositories.containsAll(viewRepositories))
+ result = (AddonRegistry) view;
+ }
+ else if (viewRepositories.containsAll(Arrays.asList(repositories))
+ && Arrays.asList(repositories).containsAll(viewRepositories))
+ {
+ result = (AddonRegistry) view;
+ }
+ if (result != null)
+ break;
+ }
return result;
}
- public void dispose(AddonView view)
+ public void removeView(AddonView view)
{
- furnace.disposeAddonView(view);
+ if (!views.contains(view))
+ throw new IllegalArgumentException("The given view does not belong to this Furnace instance.");
}
- public void startAddon(Addon addon)
+ @Override
+ public String toString()
{
- Assert.notNull(addon, "Addon to start must not be null.");
- Callables.call(new StartEnabledAddonCallable(furnace, executor, starting, (AddonImpl) addon));
+ StringBuilder builder = new StringBuilder();
+
+ Iterator addonsIterator = addons.iterator();
+ while (addonsIterator.hasNext())
+ {
+ Addon addon = addonsIterator.next();
+ builder.append("- ").append(addon.toString());
+ if (addonsIterator.hasNext())
+ builder.append("\n");
+ }
+
+ return builder.toString();
}
- public AddonView getRootView()
+ public void loadAddon(final Addon addon)
{
- return furnace.getAddonRegistry();
+ try
+ {
+ ClassLoaders.executeIn(this.getClass().getClassLoader(), new Callable()
+ {
+ @Override
+ public Void call() throws Exception
+ {
+ loader.loadAddon(addon);
+ return null;
+ }
+ });
+ }
+ catch (Exception e)
+ {
+ throw new ContainerException("Could not load addon: " + addon.getId(), e);
+ }
}
}
diff --git a/container/src/main/java/org/jboss/forge/furnace/addons/AddonLoader.java b/container/src/main/java/org/jboss/forge/furnace/addons/AddonLoader.java
index b7fb59b4..b3f6b17e 100644
--- a/container/src/main/java/org/jboss/forge/furnace/addons/AddonLoader.java
+++ b/container/src/main/java/org/jboss/forge/furnace/addons/AddonLoader.java
@@ -6,6 +6,7 @@
import java.util.logging.Logger;
import org.jboss.forge.furnace.Furnace;
+import org.jboss.forge.furnace.exception.ContainerException;
import org.jboss.forge.furnace.lock.LockManager;
import org.jboss.forge.furnace.modules.AddonModuleLoader;
import org.jboss.forge.furnace.repositories.AddonDependencyEntry;
@@ -18,121 +19,82 @@ public class AddonLoader
private static final Logger logger = Logger.getLogger(AddonLoader.class.getName());
private LockManager lock;
- private AddonLifecycleManager manager;
-
+ private AddonLifecycleManager lifecycleManager;
+ private AddonStateManager stateManager;
private AddonModuleLoader loader;
- public AddonLoader(Furnace furnace, AddonLifecycleManager manager)
+ public AddonLoader(Furnace furnace, AddonLifecycleManager lifecycleManager, AddonStateManager stateManager)
{
this.lock = furnace.getLockManager();
- this.manager = manager;
- this.loader = new AddonModuleLoader(furnace, manager);
+ this.lifecycleManager = lifecycleManager;
+ this.stateManager = stateManager;
+ this.loader = new AddonModuleLoader(furnace, lifecycleManager, stateManager);
}
- public AddonImpl loadAddon(Set views, AddonId addonId)
+ public void loadAddon(Addon addon)
{
- Assert.notNull(addonId, "AddonId to load must not be null.");
-
- AddonImpl addon = null;
-
- AddonView view = views.iterator().next();
- for (Addon existing : view.getAddons())
- {
- if (existing.getId().equals(addonId))
- {
- addon = (AddonImpl) existing;
- break;
- }
- }
-
- if (addon == null || addon.getStatus().isMissing())
- {
- for (AddonRepository repository : view.getRepositories())
- {
- addon = loadAddonFromRepository(views, view, repository, addonId);
- if (addon != null)
- break;
- }
- }
+ Assert.notNull(addon, "Addon to load must not be null.");
- if (addon != null)
- manager.add(addon);
-
- return addon;
- }
-
- private AddonImpl loadAddonFromRepository(Set views, AddonView view, AddonRepository repository,
- final AddonId addonId)
- {
- AddonImpl addon = null;
- if (repository.isEnabled(addonId) && repository.isDeployed(addonId))
+ if (addon.getStatus().isMissing())
{
- addon = (AddonImpl) view.getAddon(addonId);
-
- if (addon == null)
+ AddonRepository repository =
+ stateManager.getViewsOf(addon).iterator().next().getRepositories().iterator().next();
+ if (repository.isEnabled(addon.getId())
+ && repository.isDeployed(addon.getId()))
{
- addon = new AddonImpl(lock, addonId);
- addon.setRepository(repository);
- }
+ Set dependencies = fromAddonDependencyEntries(addon,
+ repository.getAddonDependencies(addon.getId()));
- Set dependencies = fromAddonDependencyEntries(views, view, addon,
- repository.getAddonDependencies(addonId));
-
- if (addon.getModule() == null)
- {
Set missingRequiredDependencies = new HashSet();
for (AddonDependency addonDependency : dependencies)
{
- Addon dependency = addonDependency.getDependency();
- if (dependency == null && !addonDependency.isOptional())
+ if (addonDependency instanceof MissingAddonDependencyImpl && !addonDependency.isOptional())
{
missingRequiredDependencies.add(addonDependency);
}
}
- if (missingRequiredDependencies.isEmpty())
- addon.setMissingDependencies(missingRequiredDependencies);
-
if (!missingRequiredDependencies.isEmpty())
{
- if (addon.getMissingDependencies().size() != missingRequiredDependencies.size())
+ if (stateManager.getMissingDependenciesOf(addon).size() != missingRequiredDependencies.size())
{
logger.warning("Addon [" + addon + "] has [" + missingRequiredDependencies.size()
+ "] missing dependencies: "
+ missingRequiredDependencies + " and will be not be loaded until all required"
+ " dependencies are available.");
}
- addon.setMissingDependencies(missingRequiredDependencies);
+ stateManager.setState(addon, new AddonState(missingRequiredDependencies));
}
else
{
try
{
- Module module = loader.loadModule(views, view, addonId);
- addon.setModuleLoader(loader);
- addon.setModule(module);
- addon.setRepository(repository);
+ Module module = loader.loadAddonModule(addon);
+ stateManager.setState(addon, new AddonState(dependencies, repository, loader, module));
+ }
+ catch (RuntimeException e)
+ {
+ logger.log(Level.FINE, "Failed to load addon [" + addon.getId() + "]", e);
+ throw e;
}
catch (Exception e)
{
- logger.log(Level.FINE, "Failed to load addon [" + addonId + "]", e);
+ logger.log(Level.FINE, "Failed to load addon [" + addon.getId() + "]", e);
+ throw new ContainerException("Failed to load addon [" + addon.getId() + "]", e);
}
}
}
-
- dependencies.removeAll(addon.getMissingDependencies());
- addon.setDependencies(dependencies);
}
- return addon;
}
- private Set fromAddonDependencyEntries(Set views, AddonView view, AddonImpl addon,
+ private Set fromAddonDependencyEntries(Addon addon,
Set entries)
{
Set result = new HashSet();
for (AddonDependencyEntry entry : entries)
{
- AddonId dependencyId = manager.resolve(view, entry.getName());
+ Set views = stateManager.getViewsOf(addon);
+ AddonId dependencyId = stateManager.resolveAddonId(views, entry.getName());
if (dependencyId == null)
{
if (!entry.isOptional())
@@ -142,10 +104,8 @@ private Set fromAddonDependencyEntries(Set views, Ad
}
else
{
- AddonImpl dependency = loadAddon(views, dependencyId);
+ Addon dependency = lifecycleManager.getAddon(views.iterator().next(), dependencyId);
result.add(new AddonDependencyImpl(lock,
- addon,
- dependency.getId().getVersion(),
dependency,
entry.isExported(),
entry.isOptional()));
diff --git a/container/src/main/java/org/jboss/forge/furnace/addons/AddonRunnable.java b/container/src/main/java/org/jboss/forge/furnace/addons/AddonRunnable.java
index f4e6e0ef..87650f39 100644
--- a/container/src/main/java/org/jboss/forge/furnace/addons/AddonRunnable.java
+++ b/container/src/main/java/org/jboss/forge/furnace/addons/AddonRunnable.java
@@ -13,20 +13,16 @@
import javax.enterprise.inject.spi.BeanManager;
import org.jboss.forge.furnace.Furnace;
-import org.jboss.forge.furnace.FurnaceImpl;
-import org.jboss.forge.furnace.addons.Addon;
-import org.jboss.forge.furnace.addons.AddonDependency;
import org.jboss.forge.furnace.event.PostStartup;
import org.jboss.forge.furnace.event.PreShutdown;
+import org.jboss.forge.furnace.exception.ContainerException;
import org.jboss.forge.furnace.impl.AddonProducer;
import org.jboss.forge.furnace.impl.AddonRegistryProducer;
import org.jboss.forge.furnace.impl.AddonRepositoryProducer;
import org.jboss.forge.furnace.impl.ContainerServiceExtension;
import org.jboss.forge.furnace.impl.FurnaceProducer;
-import org.jboss.forge.furnace.impl.NullServiceRegistry;
import org.jboss.forge.furnace.impl.ServiceRegistryImpl;
import org.jboss.forge.furnace.impl.ServiceRegistryProducer;
-import org.jboss.forge.furnace.lock.LockMode;
import org.jboss.forge.furnace.modules.AddonResourceLoader;
import org.jboss.forge.furnace.modules.ModularURLScanner;
import org.jboss.forge.furnace.modules.ModularWeld;
@@ -48,7 +44,7 @@ public final class AddonRunnable implements Runnable
private static final Logger logger = Logger.getLogger(AddonRunnable.class.getName());
private Furnace furnace;
- private AddonImpl addon;
+ private Addon addon;
private AddonContainerStartup container;
private Callable