Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Original file line number Diff line number Diff line change
Expand Up @@ -53,6 +53,7 @@ public interface BrooklynCatalog {

/** As {@link #getCatalogItem(String, String)} but only looking in legacy catalog
* @deprecated since 0.12.0 only provided to allow TypeRegistry to see the legacy items */
@Deprecated
CatalogItem<?,?> getCatalogItemLegacy(String symbolicName, String version);

/** @return Deletes the item with the given {@link CatalogItem#getSymbolicName()
Expand All @@ -70,6 +71,7 @@ public interface BrooklynCatalog {

/** As non-legacy method but only looking in legacy catalog
* @deprecated since 0.12.0 only provided to allow TypeRegistry to see the legacy items */
@Deprecated
<T,SpecT> CatalogItem<T,SpecT> getCatalogItemLegacy(Class<T> type, String symbolicName, String version);

/** @return All items in the catalog
Expand All @@ -89,6 +91,7 @@ public interface BrooklynCatalog {

/** As non-legacy method but only looking in legacy catalog
* @deprecated since 0.12.0 only provided to allow TypeRegistry to see the legacy items */
@Deprecated
<T,SpecT> Iterable<CatalogItem<T,SpecT>> getCatalogItemsLegacy(Predicate<? super CatalogItem<T,SpecT>> filter);

/** persists the catalog item to the object store, if persistence is enabled */
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -44,7 +44,7 @@ public interface RegisteredTypeLoadingContext {
* the instantiator can avoid recursive cycles */
@Nonnull public Set<String> getAlreadyEncounteredTypes();

/** A loader to use, supplying additional search paths */
/** A loader to use, supplying preferred or additional bundles and search paths */
@Nullable public BrooklynClassLoadingContext getLoader();

}
Original file line number Diff line number Diff line change
Expand Up @@ -1407,43 +1407,8 @@ public List<? extends CatalogItem<?,?>> addItems(String yaml, boolean forceUpdat
Maybe<OsgiManager> osgiManager = ((ManagementContextInternal)mgmt).getOsgiManager();
if (osgiManager.isPresent() && AUTO_WRAP_CATALOG_YAML_AS_BUNDLE) {
// wrap in a bundle to be managed; need to get bundle and version from yaml
Map<?, ?> cm = BasicBrooklynCatalog.getCatalogMetadata(yaml);
VersionedName vn = BasicBrooklynCatalog.getVersionedName( cm, false );
if (vn==null) {
// for better legacy compatibiity, if id specified at root use that
String id = (String) cm.get("id");
if (Strings.isNonBlank(id)) {
vn = VersionedName.fromString(id);
}
vn = new VersionedName(vn!=null && Strings.isNonBlank(vn.getSymbolicName()) ? vn.getSymbolicName() : "brooklyn-catalog-bom-"+Identifiers.makeRandomId(8),
vn!=null && vn.getVersionString()!=null ? vn.getVersionString() : getFirstAs(cm, String.class, "version").or(NO_VERSION));
}
log.debug("Wrapping supplied BOM as "+vn);
Manifest mf = new Manifest();
mf.getMainAttributes().putValue(Constants.BUNDLE_SYMBOLICNAME, vn.getSymbolicName());
mf.getMainAttributes().putValue(Constants.BUNDLE_VERSION, vn.getOsgiVersionString());
mf.getMainAttributes().putValue(Constants.BUNDLE_MANIFESTVERSION, "2");
mf.getMainAttributes().putValue(Attributes.Name.MANIFEST_VERSION.toString(), OSGI_MANIFEST_VERSION_VALUE);
mf.getMainAttributes().putValue(BROOKLYN_WRAPPED_BOM_BUNDLE, Boolean.TRUE.toString());

BundleMaker bm = new BundleMaker(mgmt);
File bf = bm.createTempBundle(vn.getSymbolicName(), mf, MutableMap.of(
new ZipEntry(CATALOG_BOM), (InputStream) new ByteArrayInputStream(yaml.getBytes())) );

OsgiBundleInstallationResult result = null;
try {
result = osgiManager.get().install(null, new FileInputStream(bf), true, true, forceUpdate).get();
} catch (FileNotFoundException e) {
throw Exceptions.propagate(e);
} finally {
bf.delete();
}
if (result.getCode().isError()) {
// rollback done by install call above
throw new IllegalStateException(result.getMessage());
}
uninstallEmptyWrapperBundles();
return toLegacyCatalogItems(result.getCatalogItemsInstalled());
OsgiBundleInstallationResult result = addItemsOsgi(yaml, forceUpdate, osgiManager);
return toLegacyCatalogItems(result.getTypesInstalled());

// if all items pertaining to an older anonymous catalog.bom bundle have been overridden
// we delete those later; see list of wrapper bundles kept in OsgiManager
Expand All @@ -1452,10 +1417,73 @@ public List<? extends CatalogItem<?,?>> addItems(String yaml, boolean forceUpdat
return addItems(yaml, null, forceUpdate);
}

/** Like {@link #addItems(String, boolean)} but returning the {@link OsgiBundleInstallationResult} for use from new environments.
* If not using OSGi the bundle/code/etc fields are null but the types will always be set. */
@SuppressWarnings("deprecation")
public OsgiBundleInstallationResult addItemsBundleResult(String yaml, boolean forceUpdate) {
Maybe<OsgiManager> osgiManager = ((ManagementContextInternal)mgmt).getOsgiManager();
if (osgiManager.isPresent() && AUTO_WRAP_CATALOG_YAML_AS_BUNDLE) {
// wrap in a bundle to be managed; need to get bundle and version from yaml
return addItemsOsgi(yaml, forceUpdate, osgiManager);

// if all items pertaining to an older anonymous catalog.bom bundle have been overridden
// we delete those later; see list of wrapper bundles kept in OsgiManager
}
// fallback to non-OSGi for tests and other environments
List<? extends CatalogItem<?, ?>> items = addItems(yaml, null, forceUpdate);
OsgiBundleInstallationResult result = new OsgiBundleInstallationResult();
for (CatalogItem<?, ?> ci: items) {
RegisteredType rt = mgmt.getTypeRegistry().get(ci.getId());
result.getTypesInstalled().add(rt!=null ? rt : RegisteredTypes.of(ci));
}
return result;
}

protected OsgiBundleInstallationResult addItemsOsgi(String yaml, boolean forceUpdate, Maybe<OsgiManager> osgiManager) {
Map<?, ?> cm = BasicBrooklynCatalog.getCatalogMetadata(yaml);
VersionedName vn = BasicBrooklynCatalog.getVersionedName( cm, false );
if (vn==null) {
// for better legacy compatibiity, if id specified at root use that
String id = (String) cm.get("id");
if (Strings.isNonBlank(id)) {
vn = VersionedName.fromString(id);
}
vn = new VersionedName(vn!=null && Strings.isNonBlank(vn.getSymbolicName()) ? vn.getSymbolicName() : "brooklyn-catalog-bom-"+Identifiers.makeRandomId(8),
vn!=null && vn.getVersionString()!=null ? vn.getVersionString() : getFirstAs(cm, String.class, "version").or(NO_VERSION));
}
log.debug("Wrapping supplied BOM as "+vn);
Manifest mf = new Manifest();
mf.getMainAttributes().putValue(Constants.BUNDLE_SYMBOLICNAME, vn.getSymbolicName());
mf.getMainAttributes().putValue(Constants.BUNDLE_VERSION, vn.getOsgiVersionString());
mf.getMainAttributes().putValue(Constants.BUNDLE_MANIFESTVERSION, "2");
mf.getMainAttributes().putValue(Attributes.Name.MANIFEST_VERSION.toString(), OSGI_MANIFEST_VERSION_VALUE);
mf.getMainAttributes().putValue(BROOKLYN_WRAPPED_BOM_BUNDLE, Boolean.TRUE.toString());

BundleMaker bm = new BundleMaker(mgmt);
File bf = bm.createTempBundle(vn.getSymbolicName(), mf, MutableMap.of(
new ZipEntry(CATALOG_BOM), (InputStream) new ByteArrayInputStream(yaml.getBytes())) );

OsgiBundleInstallationResult result = null;
try {
result = osgiManager.get().install(null, new FileInputStream(bf), true, true, forceUpdate).get();
} catch (FileNotFoundException e) {
throw Exceptions.propagate(e);
} finally {
bf.delete();
}
if (result.getCode().isError()) {
// rollback done by install call above
throw new IllegalStateException(result.getMessage());
}
uninstallEmptyWrapperBundles();
return result;
}

@SuppressWarnings("deprecation")
private List<CatalogItem<?,?>> toLegacyCatalogItems(Iterable<String> itemIds) {
private List<CatalogItem<?,?>> toLegacyCatalogItems(Iterable<RegisteredType> list) {
List<CatalogItem<?,?>> result = MutableList.of();
for (String id: itemIds) {
for (RegisteredType t: list) {
String id = t.getId();
CatalogItem<?, ?> item = CatalogUtils.getCatalogItemOptionalVersion(mgmt, id);
if (item==null) {
// using new Type Registry (OSGi addition);
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -60,6 +60,7 @@ public class Entitlements {

// ------------------- individual permissions

// TODO applies to bundles and registered types; should pass object or probably better add more entitlements?
public static EntitlementClass<String> SEE_CATALOG_ITEM = new BasicEntitlementClassDefinition<String>("catalog.see", String.class);
public static EntitlementClass<Object> ADD_CATALOG_ITEM = new BasicEntitlementClassDefinition<Object>("catalog.add", Object.class);
public static EntitlementClass<StringAndArgument> MODIFY_CATALOG_ITEM = new BasicEntitlementClassDefinition<StringAndArgument>("catalog.modify", StringAndArgument.class);
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -60,6 +60,7 @@
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;

import com.google.common.base.Function;
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I only just noticed that a bunch of this code is in core/mgmt/ha. Why is that? I'd have thought it would equally apply to non-ha (e.g. persisting your state locally, and then restarting Brooklyn).

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

indeed, longstanding misplacement. would be good to move OsgiManager and the related classes.

import com.google.common.base.Objects;
import com.google.common.base.Preconditions;
import com.google.common.collect.Iterables;
Expand Down Expand Up @@ -446,7 +447,7 @@ public void run() {
Iterable<RegisteredType> items = mgmt().getTypeRegistry().getMatching(RegisteredTypePredicates.containingBundle(result.getMetadata()));
log.debug("Adding items from bundle "+result.getVersionedName()+": "+items);
for (RegisteredType ci: items) {
result.catalogItemsInstalled.add(ci.getId());
result.addType(ci);
}
} catch (Exception e) {
// unable to install new items; rollback bundles
Expand Down Expand Up @@ -494,15 +495,20 @@ public void run() {
log.debug(result.message+" (Brooklyn load deferred)");
} else {
startRunnable.run();
if (!result.catalogItemsInstalled.isEmpty()) {
if (!result.typesInstalled.isEmpty()) {
// show fewer info messages, only for 'interesting' and non-deferred installations
// (rebind is deferred, as are tests, but REST is not)
final int MAX_TO_LIST_EXPLICITLY = 5;
MutableList<String> firstN = MutableList.copyOf(Iterables.limit(result.catalogItemsInstalled, MAX_TO_LIST_EXPLICITLY));
Iterable<String> firstN = Iterables.transform(MutableList.copyOf(Iterables.limit(result.typesInstalled, MAX_TO_LIST_EXPLICITLY)),
new Function<RegisteredType,String>() {
@Override public String apply(RegisteredType input) {
return input.getVersionedName().toString();
}
});
log.info(result.message+", items: "+firstN+
(result.catalogItemsInstalled.size() > MAX_TO_LIST_EXPLICITLY ? " (and others, "+result.catalogItemsInstalled.size()+" total)" : "") );
if (log.isDebugEnabled() && result.catalogItemsInstalled.size()>MAX_TO_LIST_EXPLICITLY) {
log.debug(result.message+", all items: "+result.catalogItemsInstalled);
(result.typesInstalled.size() > MAX_TO_LIST_EXPLICITLY ? " (and others, "+result.typesInstalled.size()+" total)" : "") );
if (log.isDebugEnabled() && result.typesInstalled.size()>MAX_TO_LIST_EXPLICITLY) {
log.debug(result.message+", all items: "+result.typesInstalled);
}
} else {
log.debug(result.message+" (into Brooklyn), with no catalog items");
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -21,6 +21,7 @@
import java.util.List;

import org.apache.brooklyn.api.typereg.ManagedBundle;
import org.apache.brooklyn.api.typereg.RegisteredType;
import org.apache.brooklyn.util.collections.MutableList;
import org.apache.brooklyn.util.osgi.VersionedName;
import org.osgi.framework.Bundle;
Expand Down Expand Up @@ -48,14 +49,21 @@ public enum ResultCode {
/** bundle successfully installed to OSGi container but there was an error launching it,
* either the OSGi bundle start, catalog items load, or (most commonly) validating the catalog items;
* bundle may be installed (currently it is in most/all places, but behaviour TBC) so caller may have to uninstall it */
ERROR_LAUNCHING_BUNDLE(true);
ERROR_LAUNCHING_BUNDLE(true),
// codes below used for deletion
BUNDLE_REMOVED(false),
ERROR_REMOVING_BUNDLE_IN_USE(true),
ERROR_REMOVING_BUNDLE_OTHER(true);

final boolean isError;
ResultCode(boolean isError) { this.isError = isError; }

public boolean isError() { return isError; }
}
final List<String> catalogItemsInstalled = MutableList.of();
final List<RegisteredType> typesInstalled = MutableList.of();
/** @deprecated since 0.13.0 use {@link #typesInstalled} */
@Deprecated
private final List<String> catalogItemsInstalled = MutableList.of();

public String getMessage() {
return message;
Expand All @@ -69,6 +77,11 @@ public ManagedBundle getMetadata() {
public ResultCode getCode() {
return code;
}
public List<RegisteredType> getTypesInstalled() {
return typesInstalled;
}
/** @deprecated since 0.13.0 use {@link #getTypesInstalled()} */
@Deprecated
public List<String> getCatalogItemsInstalled() {
return ImmutableList.copyOf(catalogItemsInstalled);
}
Expand All @@ -89,4 +102,8 @@ void setIgnoringAlreadyInstalled() {
public String toString() {
return OsgiBundleInstallationResult.class.getSimpleName()+"["+code+", "+metadata+", "+message+"]";
}
public void addType(RegisteredType ci) {
typesInstalled.add(ci);
catalogItemsInstalled.add(ci.getId());
}
}
Loading