Collection<ModelledResource> byValueBundles = new ArrayList<ModelledResource>(provideByValueBundles);
ModelledResource fakeBundleResource;
try {
fakeBundleResource = createFakeBundle(appMetadata.getApplicationImportServices());
} catch (InvalidAttributeException iax) {
ResolverException rx = new ResolverException (iax);
_logger.debug(LOG_EXIT, "generateDeploymentManifest", new Object[] {rx});
throw rx;
}
byValueBundles.add(fakeBundleResource);
String appSymbolicName = appMetadata.getApplicationSymbolicName();
String appVersion = appMetadata.getApplicationVersion().toString();
String uniqueName = appSymbolicName + "_" + appVersion;
DeployedBundles deployedBundles = modellingHelper.createDeployedBundles(appSymbolicName, appContentIB, useBundleIB, Arrays.asList(fakeBundleResource));
Collection<ModelledResource> bundlesToBeProvisioned = resolver.resolve(
appSymbolicName, appVersion, byValueBundles, bundlesToResolve);
pruneFakeBundleFromResults (bundlesToBeProvisioned);
if (bundlesToBeProvisioned.isEmpty()) {
throw new ResolverException(MessageUtil.getMessage("EMPTY_DEPLOYMENT_CONTENT",uniqueName));
}
for (ModelledResource rbm : bundlesToBeProvisioned)
{
deployedBundles.addBundle(rbm);
}
Collection<ModelledResource> requiredUseBundle = deployedBundles.getRequiredUseBundle();
if (requiredUseBundle.size() < useBundleSet.size())
{
// Some of the use-bundle entries were redundant so resolve again with just the good ones.
deployedBundles = modellingHelper.createDeployedBundles(appSymbolicName, appContentIB, useBundleIB, Arrays.asList(fakeBundleResource));
bundlesToResolve.clear();
bundlesToResolve.addAll(appContent);
Collection<ImportedBundle> slimmedDownUseBundle = narrowUseBundles(useBundleIB, requiredUseBundle);
bundlesToResolve.addAll(toContent(slimmedDownUseBundle));
bundlesToBeProvisioned = resolver.resolve(appSymbolicName, appVersion, byValueBundles, bundlesToResolve);
pruneFakeBundleFromResults (bundlesToBeProvisioned);
for (ModelledResource rbm : bundlesToBeProvisioned)
{
deployedBundles.addBundle(rbm);
}
}
// Check for circular dependencies. No shared bundle can depend on any
// isolated bundle.
Collection<ModelledResource> sharedBundles = new HashSet<ModelledResource>();
sharedBundles.addAll (deployedBundles.getDeployedProvisionBundle());
sharedBundles.addAll (deployedBundles.getRequiredUseBundle());
Collection<ModelledResource> appContentBundles = deployedBundles.getDeployedContent();
Collection<Content> requiredSharedBundles = new ArrayList<Content>();
for (ModelledResource mr : sharedBundles) {
String version = mr.getExportedBundle().getVersion();
String exactVersion = "[" + version + "," + version + "]";
Content ib = ManifestHeaderProcessor.parseContent(mr.getExportedBundle().getSymbolicName(),
exactVersion);
requiredSharedBundles.add(ib);
}
// This will throw a ResolverException if the shared content does not resolve
Collection<ModelledResource> resolvedSharedBundles = resolver.resolve(appSymbolicName, appVersion
, byValueBundles, requiredSharedBundles);
// we need to find out whether any shared bundles depend on the isolated bundles
List<String> suspects = findSuspects (resolvedSharedBundles, sharedBundles, appContentBundles);
// If we have differences, it means that we have shared bundles trying to import packages
// from isolated bundles. We need to build up the error message and throw a ResolverException
if (!suspects.isEmpty()) {
StringBuilder msgs = new StringBuilder();
List<String> unsatisfiedRequirements = new ArrayList<String>();
Map<String, List<String>> isolatedBundles = new HashMap<String, List<String>>();
// Find the isolated bundles and store all the packages that they export in a map.
for (ModelledResource mr : resolvedSharedBundles) {
String mrName = mr.getSymbolicName() + "_" + mr.getExportedBundle().getVersion();
if (suspects.contains(mrName)) {
List<String> exportedPackages = new ArrayList<String>();
isolatedBundles.put(mrName, exportedPackages);
for (ExportedPackage ep : mr.getExportedPackages()) {
exportedPackages.add(ep.getPackageName());
}
}
}
// Now loop through the shared bundles, reading the imported packages, and find which ones
// are exported from the isolated bundles.
for (ModelledResource mr : resolvedSharedBundles) {
String mrName = mr.getSymbolicName() + "_" + mr.getExportedBundle().getVersion();
// if current resource isn't an isolated bundle check it's requirements
if (!!! suspects.contains(mrName)) {
// Iterate through the imported packages of the current shared bundle.
for (ImportedPackage ip : mr.getImportedPackages()) {
String packageName = ip.getPackageName();
List<String> bundlesExportingPackage = new ArrayList<String>();
// Loop through each exported package of each isolated bundle, and if we
// get a match store the info away.
for (Map.Entry<String, List<String>> currBundle : isolatedBundles.entrySet()) {
List<String> exportedPackages = currBundle.getValue();
if (exportedPackages != null && exportedPackages.contains(packageName)) {
bundlesExportingPackage.add(currBundle.getKey());
}
}
// If we have found at least one matching entry, we construct the sub message for the
// exception.
if (!!! bundlesExportingPackage.isEmpty()) {
String newMsg;
if (bundlesExportingPackage.size() > 1) {
newMsg = MessageUtil.getMessage("SHARED_BUNDLE_IMPORTING_FROM_ISOLATED_BUNDLES",
new Object[] {mrName, packageName, bundlesExportingPackage});
} else {
newMsg = MessageUtil.getMessage("SHARED_BUNDLE_IMPORTING_FROM_ISOLATED_BUNDLE",
new Object[] {mrName, packageName, bundlesExportingPackage});
}
msgs.append("\n");
msgs.append(newMsg);
unsatisfiedRequirements.add(newMsg);
}
}
}
}
// Once we have iterated over all bundles and have got our translated submessages,
// throw the exception.
// Well! if the msgs is empty, no need to throw an exception
if (msgs.length() !=0) {
String message = MessageUtil.getMessage(
"SUSPECTED_CIRCULAR_DEPENDENCIES", new Object[] {appSymbolicName, msgs});
ResolverException rx = new ResolverException (message);
rx.setUnsatisfiedRequirements(unsatisfiedRequirements);
_logger.debug(LOG_EXIT, "generateDeploymentManifest", new Object[] {rx});
throw (rx);
}
}