diff options
author | Thomas Watson | 2018-02-19 14:00:59 +0000 |
---|---|---|
committer | Thomas Watson | 2018-02-19 15:11:13 +0000 |
commit | 40b6fcec3631651554c6f8a02df558995460d3df (patch) | |
tree | 09d83862b0d484c2a56a4e47a5b895dad60a1541 | |
parent | 1c1fa3211389fd40c931c5741e42c94807cf9ddd (diff) | |
download | rt.equinox.framework-40b6fcec3631651554c6f8a02df558995460d3df.tar.gz rt.equinox.framework-40b6fcec3631651554c6f8a02df558995460d3df.tar.xz rt.equinox.framework-40b6fcec3631651554c6f8a02df558995460d3df.zip |
Bug 531342 - [osgi R7] update the latest R7 OSGi Core API
Change-Id: I77ac4b864675648e0bca6a194b82907d2391f0be
Signed-off-by: Thomas Watson <tjwatson@us.ibm.com>
19 files changed, 418 insertions, 180 deletions
diff --git a/bundles/org.eclipse.osgi.services/.settings/.api_filters b/bundles/org.eclipse.osgi.services/.settings/.api_filters index ae6aa31ae..4398895df 100644 --- a/bundles/org.eclipse.osgi.services/.settings/.api_filters +++ b/bundles/org.eclipse.osgi.services/.settings/.api_filters @@ -1,5 +1,33 @@ <?xml version="1.0" encoding="UTF-8" standalone="no"?> <component id="org.eclipse.osgi.services" version="2"> + <resource path="src/org/osgi/service/event/EventConstants.java" type="org.osgi.service.event.EventConstants"> + <filter id="403767336"> + <message_arguments> + <message_argument value="org.osgi.service.event.EventConstants"/> + <message_argument value="EVENT_ADMIN_IMPLEMENTATION"/> + </message_arguments> + </filter> + <filter id="403767336"> + <message_arguments> + <message_argument value="org.osgi.service.event.EventConstants"/> + <message_argument value="EVENT_ADMIN_SPECIFICATION_VERSION"/> + </message_arguments> + </filter> + <filter id="1209008130"> + <message_arguments> + <message_argument value="1.4"/> + <message_argument value="3.7"/> + <message_argument value="EVENT_ADMIN_IMPLEMENTATION"/> + </message_arguments> + </filter> + <filter id="1209008130"> + <message_arguments> + <message_argument value="1.4"/> + <message_argument value="3.7"/> + <message_argument value="EVENT_ADMIN_SPECIFICATION_VERSION"/> + </message_arguments> + </filter> + </resource> <resource path="src/org/osgi/service/log/FormatterLogger.java" type="org.osgi.service.log.FormatterLogger"> <filter id="1108344834"> <message_arguments> diff --git a/bundles/org.eclipse.osgi.services/META-INF/MANIFEST.MF b/bundles/org.eclipse.osgi.services/META-INF/MANIFEST.MF index 81843c325..4b7d8c50d 100644 --- a/bundles/org.eclipse.osgi.services/META-INF/MANIFEST.MF +++ b/bundles/org.eclipse.osgi.services/META-INF/MANIFEST.MF @@ -14,7 +14,7 @@ Export-Package: org.osgi.service.cm;version="1.5";uses:="org.osgi.framework", org.osgi.service.component.runtime;version="1.3";uses:="org.osgi.framework,org.osgi.util.promise,org.osgi.service.component.runtime.dto", org.osgi.service.component.runtime.dto;version="1.3";uses:="org.osgi.dto,org.osgi.framework.dto", org.osgi.service.device;version="1.1";uses:="org.osgi.framework", - org.osgi.service.event;version="1.3.1";uses:="org.osgi.framework", + org.osgi.service.event;version="1.4";uses:="org.osgi.framework", org.osgi.service.http;version="1.2.1";uses:="javax.servlet,javax.servlet.http", org.osgi.service.http.context;version="1.0";uses:="org.osgi.framework,javax.servlet.http", org.osgi.service.http.runtime;version="1.0";uses:="org.osgi.service.http.runtime.dto", @@ -37,7 +37,7 @@ Import-Package: javax.servlet;resolution:=optional, org.osgi.service.component.runtime; version="[1.3,1.4)", org.osgi.service.component.runtime.dto; version="[1.3,1.4)", org.osgi.service.device;version="[1.1,1.2)", - org.osgi.service.event;version="[1.3,1.4)", + org.osgi.service.event;version="[1.4,1.5)", org.osgi.service.http;version="[1.2,1.3)", org.osgi.service.log;version="[1.4,1.5)", org.osgi.service.metatype;version="[1.4,1.5)", diff --git a/bundles/org.eclipse.osgi.services/src/org/osgi/service/event/EventConstants.java b/bundles/org.eclipse.osgi.services/src/org/osgi/service/event/EventConstants.java index b9345200f..b478c6745 100644 --- a/bundles/org.eclipse.osgi.services/src/org/osgi/service/event/EventConstants.java +++ b/bundles/org.eclipse.osgi.services/src/org/osgi/service/event/EventConstants.java @@ -1,5 +1,5 @@ /* - * Copyright (c) OSGi Alliance (2005, 2014). All Rights Reserved. + * Copyright (c) OSGi Alliance (2005, 2018). All Rights Reserved. * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. @@ -234,6 +234,21 @@ public interface EventConstants { public static final String TIMESTAMP = "timestamp"; /** + * The name of the implementation capability for the Event Admin + * specification + * + * @since 1.4 + */ + public static final String EVENT_ADMIN_IMPLEMENTATION = "osgi.event"; + /** + * The version of the implementation capability for the Event Admin + * specification + * + * @since 1.4 + */ + public static final String EVENT_ADMIN_SPECIFICATION_VERSION = "1.4.0"; + + /** * This constant was released with an incorrectly spelled name. It has been * replaced by {@link #EXCEPTION_CLASS} * diff --git a/bundles/org.eclipse.osgi.services/src/org/osgi/service/event/package-info.java b/bundles/org.eclipse.osgi.services/src/org/osgi/service/event/package-info.java index 90332d68d..a3f50f169 100644 --- a/bundles/org.eclipse.osgi.services/src/org/osgi/service/event/package-info.java +++ b/bundles/org.eclipse.osgi.services/src/org/osgi/service/event/package-info.java @@ -1,5 +1,5 @@ /* - * Copyright (c) OSGi Alliance (2010, 2014). All Rights Reserved. + * Copyright (c) OSGi Alliance (2010, 2018). All Rights Reserved. * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. @@ -15,28 +15,28 @@ */ /** - * Event Admin Package Version 1.3. - * + * Event Admin Package Version 1.4. * <p> * Bundles wishing to use this package must list the package in the * Import-Package header of the bundle's manifest. This package has two types of * users: the consumers that use the API in this package and the providers that * implement the API in this package. - * * <p> * Example import for consumers using the API in this package: * <p> - * {@code Import-Package: org.osgi.service.event; version="[1.3,2.0)"} + * {@code Import-Package: org.osgi.service.event; version="[1.4,2.0)"} * <p> * Example import for providers implementing the API in this package: * <p> - * {@code Import-Package: org.osgi.service.event; version="[1.3,1.4)"} + * {@code Import-Package: org.osgi.service.event; version="[1.4,1.5)"} * * @author $Id$ */ -@Version("1.3.1") +@Version(EVENT_ADMIN_SPECIFICATION_VERSION) package org.osgi.service.event; +import static org.osgi.service.event.EventConstants.EVENT_ADMIN_SPECIFICATION_VERSION; + import org.osgi.annotation.versioning.Version; diff --git a/bundles/org.eclipse.osgi.services/src/org/osgi/service/metatype/AttributeDefinition.java b/bundles/org.eclipse.osgi.services/src/org/osgi/service/metatype/AttributeDefinition.java index 057587a3c..615bc535a 100644 --- a/bundles/org.eclipse.osgi.services/src/org/osgi/service/metatype/AttributeDefinition.java +++ b/bundles/org.eclipse.osgi.services/src/org/osgi/service/metatype/AttributeDefinition.java @@ -1,5 +1,5 @@ /* - * Copyright (c) OSGi Alliance (2001, 2015). All Rights Reserved. + * Copyright (c) OSGi Alliance (2001, 2017). All Rights Reserved. * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. @@ -260,11 +260,10 @@ public interface AttributeDefinition { String[] getOptionLabels(); /** - * Validate an attribute in {@code String} form. - * - * An attribute might be further constrained in value. This method will - * attempt to validate the attribute according to these constraints. It can - * return three different values: + * Validate an attribute in {@code String} form. An attribute might be + * further constrained in value. This method will attempt to validate the + * attribute according to these constraints. It can return three different + * values: * * <pre> * null No validation present @@ -280,12 +279,12 @@ public interface AttributeDefinition { * backslash. Escaped spaces must not be trimmed. For example: * * <pre> - * value=" a\,b,b\,c,\ c\\,d " => [ "a,b", "b,c", " c\", "d" ] + * value=" a\,b,b\,c,\ c\\,d " => [ "a,b", "b,c", " c\", "d" ] * </pre> * * @param value The value before turning it into the basic data type. If the - * cardinality indicates a multi-valued attribute then the given - * string must be escaped. + * cardinality indicates a multi-valued attribute then the given + * string must be escaped. * @return {@code null}, "", or another string */ String validate(String value); diff --git a/bundles/org.eclipse.osgi.services/src/org/osgi/service/metatype/ObjectClassDefinition.java b/bundles/org.eclipse.osgi.services/src/org/osgi/service/metatype/ObjectClassDefinition.java index 0db886aca..baadcea21 100644 --- a/bundles/org.eclipse.osgi.services/src/org/osgi/service/metatype/ObjectClassDefinition.java +++ b/bundles/org.eclipse.osgi.services/src/org/osgi/service/metatype/ObjectClassDefinition.java @@ -1,5 +1,5 @@ /* - * Copyright (c) OSGi Alliance (2001, 2015). All Rights Reserved. + * Copyright (c) OSGi Alliance (2001, 2018). All Rights Reserved. * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. @@ -18,6 +18,7 @@ package org.osgi.service.metatype; import java.io.IOException; import java.io.InputStream; + import org.osgi.annotation.versioning.ConsumerType; /** @@ -61,7 +62,6 @@ public interface ObjectClassDefinition { /** * Return the id of this object class. - * * <p> * {@code ObjectDefintion} objects share a global namespace in the registry. * They share this aspect with LDAP/X.500 attributes. In these standards the @@ -69,7 +69,7 @@ public interface ObjectClassDefinition { * If such an OID exists, (which can be requested at several standard * organizations and many companies already have a node in the tree) it can * be returned here. Otherwise, a unique id should be returned which can be - * a java class name (reverse domain name) or generated with a GUID + * a Java class name (reverse domain name) or generated with a GUID * algorithm. Note that all LDAP defined object classes already have an OID * associated. It is strongly advised to define the object classes from * existing LDAP schemes which will give the OID for free. Many such schemes diff --git a/bundles/org.eclipse.osgi.util/src/org/osgi/util/promise/DeferredPromiseImpl.java b/bundles/org.eclipse.osgi.util/src/org/osgi/util/promise/DeferredPromiseImpl.java index 5f103429f..a65f67090 100644 --- a/bundles/org.eclipse.osgi.util/src/org/osgi/util/promise/DeferredPromiseImpl.java +++ b/bundles/org.eclipse.osgi.util/src/org/osgi/util/promise/DeferredPromiseImpl.java @@ -22,6 +22,8 @@ import java.lang.reflect.InvocationTargetException; import java.util.NoSuchElementException; import java.util.concurrent.Callable; import java.util.concurrent.CountDownLatch; +import java.util.concurrent.ScheduledFuture; +import java.util.concurrent.TimeUnit; import org.osgi.util.function.Consumer; import org.osgi.util.function.Function; @@ -91,10 +93,30 @@ final class DeferredPromiseImpl<T> extends PromiseImpl<T> { } /** + * Return a resolved PromiseImpl if this DeferredPromiseImpl is resolved. + * + * @return A ResolvedPromiseImpl holding the value of this + * DeferredPromiseImpl or a FailedPromiseImpl holding the failure of + * this DeferredPromiseImpl or this DeferredPromiseImpl if this + * DeferredPromiseImpl is not resolved. + */ + PromiseImpl<T> orDone() { + // ensure latch open before reading state + if (!isDone()) { + return this; + } + if (fail == null) { + return resolved(value); + } + return failed(fail); + } + + /** * {@inheritDoc} */ @Override public T getValue() throws InvocationTargetException, InterruptedException { + // ensure latch open before reading state resolved.await(); if (fail == null) { return value; @@ -107,12 +129,13 @@ final class DeferredPromiseImpl<T> extends PromiseImpl<T> { */ @Override public Throwable getFailure() throws InterruptedException { + // ensure latch open before reading state resolved.await(); return fail; } /** - * Return a holder of the result of this PromiseImpl. + * {@inheritDoc} */ @Override Result<T> collect() { @@ -207,8 +230,8 @@ final class DeferredPromiseImpl<T> extends PromiseImpl<T> { */ Promise<Void> resolveWith(Promise< ? extends T> with) { DeferredPromiseImpl<Void> chained = deferred(); - with.onResolve(chained.new ResolveWith<>(this, with)); - return chained; + chain(with, chained.new ResolveWith<>(with, this)); + return chained.orDone(); } /** @@ -218,21 +241,21 @@ final class DeferredPromiseImpl<T> extends PromiseImpl<T> { * @Immutable */ private final class ResolveWith<P> implements Runnable { - private final DeferredPromiseImpl<P> promise; - private final Promise< ? extends P> with; + private final Promise< ? extends P> promise; + private final DeferredPromiseImpl<P> target; - ResolveWith(DeferredPromiseImpl<P> promise, - Promise< ? extends P> with) { - this.promise = promise; - this.with = requireNonNull(with); + ResolveWith(Promise< ? extends P> promise, + DeferredPromiseImpl<P> target) { + this.promise = requireNonNull(promise); + this.target = requireNonNull(target); } @Override public void run() { Throwable f = null; - Result<P> result = collect(with); + Result<P> result = collect(promise); try { - promise.resolve(result.value, result.fail); + target.resolve(result.value, result.fail); } catch (Throwable e) { f = e; // propagate new exception } @@ -254,7 +277,7 @@ final class DeferredPromiseImpl<T> extends PromiseImpl<T> { @SuppressWarnings("unchecked") Then(PromiseImpl<P> promise, Success< ? super P, ? extends T> success, Failure failure) { - this.promise = promise; + this.promise = requireNonNull(promise); this.success = (Success<P, ? extends T>) success; this.failure = failure; } @@ -278,8 +301,7 @@ final class DeferredPromiseImpl<T> extends PromiseImpl<T> { result.fail = e; // propagate new exception } if (returned != null) { - // resolve chained when returned promise is resolved - returned.onResolve(new Chain(returned)); + chain(returned, new Chain(returned)); return; } } @@ -297,7 +319,7 @@ final class DeferredPromiseImpl<T> extends PromiseImpl<T> { private final Promise< ? extends T> promise; Chain(Promise< ? extends T> promise) { - this.promise = promise; + this.promise = requireNonNull(promise); } @Override @@ -313,11 +335,11 @@ final class DeferredPromiseImpl<T> extends PromiseImpl<T> { * * @Immutable */ - final class ChainImpl implements Runnable { + private final class ChainImpl implements Runnable { private final PromiseImpl<T> promise; ChainImpl(PromiseImpl<T> promise) { - this.promise = promise; + this.promise = requireNonNull(promise); } @Override @@ -337,7 +359,7 @@ final class DeferredPromiseImpl<T> extends PromiseImpl<T> { private final Consumer< ? super T> consumer; ThenAccept(PromiseImpl<T> promise, Consumer< ? super T> consumer) { - this.promise = promise; + this.promise = requireNonNull(promise); this.consumer = requireNonNull(consumer); } @@ -365,7 +387,7 @@ final class DeferredPromiseImpl<T> extends PromiseImpl<T> { private final Predicate< ? super T> predicate; Filter(PromiseImpl<T> promise, Predicate< ? super T> predicate) { - this.promise = promise; + this.promise = requireNonNull(promise); this.predicate = requireNonNull(predicate); } @@ -395,7 +417,7 @@ final class DeferredPromiseImpl<T> extends PromiseImpl<T> { private final Function< ? super P, ? extends T> mapper; Map(PromiseImpl<P> promise, Function< ? super P, ? extends T> mapper) { - this.promise = promise; + this.promise = requireNonNull(promise); this.mapper = requireNonNull(mapper); } @@ -425,7 +447,7 @@ final class DeferredPromiseImpl<T> extends PromiseImpl<T> { FlatMap(PromiseImpl<P> promise, Function< ? super P,Promise< ? extends T>> mapper) { - this.promise = promise; + this.promise = requireNonNull(promise); this.mapper = requireNonNull(mapper); } @@ -440,7 +462,7 @@ final class DeferredPromiseImpl<T> extends PromiseImpl<T> { result.fail = e; } if (flatmap != null) { - flatmap.onResolve(new Chain(flatmap)); + chain(flatmap, new Chain(flatmap)); return; } } @@ -459,7 +481,7 @@ final class DeferredPromiseImpl<T> extends PromiseImpl<T> { Recover(PromiseImpl<T> promise, Function<Promise< ? >, ? extends T> recovery) { - this.promise = promise; + this.promise = requireNonNull(promise); this.recovery = requireNonNull(recovery); } @@ -492,7 +514,7 @@ final class DeferredPromiseImpl<T> extends PromiseImpl<T> { RecoverWith(PromiseImpl<T> promise, Function<Promise< ? >,Promise< ? extends T>> recovery) { - this.promise = promise; + this.promise = requireNonNull(promise); this.recovery = requireNonNull(recovery); } @@ -507,7 +529,7 @@ final class DeferredPromiseImpl<T> extends PromiseImpl<T> { result.fail = e; } if (recovered != null) { - recovered.onResolve(new Chain(recovered)); + chain(recovered, new Chain(recovered)); return; } } @@ -525,7 +547,7 @@ final class DeferredPromiseImpl<T> extends PromiseImpl<T> { private final Promise< ? extends T> fallback; FallbackTo(PromiseImpl<T> promise, Promise< ? extends T> fallback) { - this.promise = promise; + this.promise = requireNonNull(promise); this.fallback = requireNonNull(fallback); } @@ -533,7 +555,7 @@ final class DeferredPromiseImpl<T> extends PromiseImpl<T> { public void run() { Result<T> result = promise.collect(); if (result.fail != null) { - fallback.onResolve(new FallbackChain(fallback, result.fail)); + chain(fallback, new FallbackChain(fallback, result.fail)); return; } tryResolve(result.value, null); @@ -551,8 +573,8 @@ final class DeferredPromiseImpl<T> extends PromiseImpl<T> { private final Throwable failure; FallbackChain(Promise< ? extends T> fallback, Throwable failure) { - this.fallback = fallback; - this.failure = failure; + this.fallback = requireNonNull(fallback); + this.failure = requireNonNull(failure); } @Override @@ -566,6 +588,59 @@ final class DeferredPromiseImpl<T> extends PromiseImpl<T> { } /** + * A callback used by the {@link PromiseImpl#timeout(long)} method to + * schedule the timeout and to resolve the chained Promise and cancel the + * timeout. + * + * @Immutable + */ + final class Timeout implements Runnable { + private final PromiseImpl<T> promise; + private final ScheduledFuture< ? > future; + + Timeout(PromiseImpl<T> promise, long millis) { + this.promise = requireNonNull(promise); + if (promise.isDone()) { + this.future = null; + } else { + FailedPromiseImpl<T> timedout = failed(new TimeoutException()); + Runnable operation = new ChainImpl(timedout); + this.future = schedule(operation, millis, TimeUnit.MILLISECONDS); + } + } + + @Override + public void run() { + Result<T> result = promise.collect(); + tryResolve(result.value, result.fail); + if (future != null) { + future.cancel(false); + } + } + } + + /** + * A callback used by the {@link PromiseImpl#delay(long)} method to delay + * chaining a promise. + * + * @Immutable + */ + final class Delay implements Runnable { + private final Runnable operation; + private final long millis; + + Delay(PromiseImpl<T> promise, long millis) { + this.operation = new ChainImpl(promise); + this.millis = millis; + } + + @Override + public void run() { + schedule(operation, millis, TimeUnit.MILLISECONDS); + } + } + + /** * A callback used by the {@link PromiseFactory#submit(Callable)} method. * * @Immutable diff --git a/bundles/org.eclipse.osgi.util/src/org/osgi/util/promise/FailedPromiseImpl.java b/bundles/org.eclipse.osgi.util/src/org/osgi/util/promise/FailedPromiseImpl.java index b2e757f45..dd5b6094d 100644 --- a/bundles/org.eclipse.osgi.util/src/org/osgi/util/promise/FailedPromiseImpl.java +++ b/bundles/org.eclipse.osgi.util/src/org/osgi/util/promise/FailedPromiseImpl.java @@ -20,6 +20,10 @@ import static java.util.Objects.requireNonNull; import java.lang.reflect.InvocationTargetException; +import org.osgi.util.function.Consumer; +import org.osgi.util.function.Function; +import org.osgi.util.function.Predicate; + /** * Failed Promise implementation. * <p> @@ -73,7 +77,7 @@ final class FailedPromiseImpl<T> extends PromiseImpl<T> { } /** - * Return a holder of the result of this PromiseImpl. + * {@inheritDoc} */ @Override Result<T> collect() { @@ -84,4 +88,80 @@ final class FailedPromiseImpl<T> extends PromiseImpl<T> { public String toString() { return super.toString() + "[failed: " + fail + "]"; } + + /** + * Coerce the value type of this FailedPromiseImpl. + * + * @return This FailedPromiseImpl. + */ + @SuppressWarnings("unchecked") + private <V> FailedPromiseImpl<V> coerce() { + return (FailedPromiseImpl<V>) this; + } + + /** + * {@inheritDoc} + */ + @Override + public Promise<T> onSuccess(Consumer< ? super T> success) { + requireNonNull(success); + return this; + } + + /** + * {@inheritDoc} + */ + @Override + public <R> Promise<R> then(Success< ? super T, ? extends R> success, + Failure failure) { + if (failure == null) { + return coerce(); + } + return super.then(success, failure); + } + + /** + * {@inheritDoc} + */ + @Override + public Promise<T> thenAccept(Consumer< ? super T> consumer) { + requireNonNull(consumer); + return this; + } + + /** + * {@inheritDoc} + */ + @Override + public Promise<T> filter(Predicate< ? super T> predicate) { + requireNonNull(predicate); + return this; + } + + /** + * {@inheritDoc} + */ + @Override + public <R> Promise<R> map(Function< ? super T, ? extends R> mapper) { + requireNonNull(mapper); + return coerce(); + } + + /** + * {@inheritDoc} + */ + @Override + public <R> Promise<R> flatMap( + Function< ? super T,Promise< ? extends R>> mapper) { + requireNonNull(mapper); + return coerce(); + } + + /** + * {@inheritDoc} + */ + @Override + public Promise<T> timeout(long millis) { + return this; + } } diff --git a/bundles/org.eclipse.osgi.util/src/org/osgi/util/promise/Promise.java b/bundles/org.eclipse.osgi.util/src/org/osgi/util/promise/Promise.java index a2082aef3..340a61ee6 100644 --- a/bundles/org.eclipse.osgi.util/src/org/osgi/util/promise/Promise.java +++ b/bundles/org.eclipse.osgi.util/src/org/osgi/util/promise/Promise.java @@ -1,5 +1,5 @@ /* - * Copyright (c) OSGi Alliance (2014, 2016). All Rights Reserved. + * Copyright (c) OSGi Alliance (2014, 2018). All Rights Reserved. * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. @@ -156,7 +156,7 @@ public interface Promise<T> { * upon that the registration of the callback <i>happens-before</i> the * registered callback is called. * - * @param success The Consumer callback that receives the the value of this + * @param success The Consumer callback that receives the value of this * Promise. Must not be {@code null}. * @return This Promise. * @since 1.1 @@ -181,8 +181,8 @@ public interface Promise<T> { * upon that the registration of the callback <i>happens-before</i> the * registered callback is called. * - * @param failure The Consumer callback that receives the the failure of - * this Promise. Must not be {@code null}. + * @param failure The Consumer callback that receives the failure of this + * Promise. Must not be {@code null}. * @return This Promise. * @since 1.1 */ @@ -282,7 +282,7 @@ public interface Promise<T> { * upon that the registration of the callback <i>happens-before</i> the * registered callback is called. * - * @param consumer The Consumer callback that receives the the value of this + * @param consumer The Consumer callback that receives the value of this * Promise. Must not be {@code null}. * @return A new Promise which is chained to this Promise. The returned * Promise must be resolved when this Promise is resolved after the diff --git a/bundles/org.eclipse.osgi.util/src/org/osgi/util/promise/PromiseFactory.java b/bundles/org.eclipse.osgi.util/src/org/osgi/util/promise/PromiseFactory.java index 09c0c038f..16820b27f 100644 --- a/bundles/org.eclipse.osgi.util/src/org/osgi/util/promise/PromiseFactory.java +++ b/bundles/org.eclipse.osgi.util/src/org/osgi/util/promise/PromiseFactory.java @@ -16,7 +16,8 @@ package org.osgi.util.promise; -import static org.osgi.util.promise.PromiseImpl.uncaughtException; +import static java.util.Objects.requireNonNull; +import static org.osgi.util.promise.PromiseImpl.*; import java.util.ArrayList; import java.util.Collection; @@ -203,7 +204,7 @@ public class PromiseFactory { } catch (Exception t) { promise.tryResolve(null, t); } - return promise; + return promise.orDone(); } /** @@ -236,18 +237,19 @@ public class PromiseFactory { public <T, S extends T> Promise<List<T>> all( Collection<Promise<S>> promises) { if (promises.isEmpty()) { - List<T> result = new ArrayList<>(); - return resolved(result); + List<T> value = new ArrayList<>(); + return resolved(value); } - DeferredPromiseImpl<List<T>> promise = new DeferredPromiseImpl<>(this); /* make a copy and capture the ordering */ List<Promise<S>> list = new ArrayList<>(promises); - All<T,S> all = new All<>(promise, list); + + DeferredPromiseImpl<List<T>> chained = new DeferredPromiseImpl<>(this); + All<T,S> all = new All<>(chained, list); for (Promise<S> p : list) { - p.onResolve(all); + chain(p, all); } - return promise; + return chained.orDone(); } /** @@ -258,14 +260,14 @@ public class PromiseFactory { * @ThreadSafe */ private static final class All<T, S extends T> implements Runnable { - private final DeferredPromiseImpl<List<T>> promise; - private final List<Promise<S>> promises; - private final AtomicInteger promiseCount; + private final DeferredPromiseImpl<List<T>> chained; + private final List<Promise<S>> promises; + private final AtomicInteger promiseCount; - All(DeferredPromiseImpl<List<T>> promise, + All(DeferredPromiseImpl<List<T>> chained, List<Promise<S>> promises) { - this.promise = promise; - this.promises = promises; + this.chained = requireNonNull(chained); + this.promises = requireNonNull(promises); this.promiseCount = new AtomicInteger(promises.size()); } @@ -289,9 +291,9 @@ public class PromiseFactory { } } if (failed.isEmpty()) { - promise.tryResolve(value, null); + chained.tryResolve(value, null); } else { - promise.tryResolve(null, + chained.tryResolve(null, new FailedPromisesException(failed, cause)); } } diff --git a/bundles/org.eclipse.osgi.util/src/org/osgi/util/promise/PromiseImpl.java b/bundles/org.eclipse.osgi.util/src/org/osgi/util/promise/PromiseImpl.java index 71ecd591b..d78ae3b66 100644 --- a/bundles/org.eclipse.osgi.util/src/org/osgi/util/promise/PromiseImpl.java +++ b/bundles/org.eclipse.osgi.util/src/org/osgi/util/promise/PromiseImpl.java @@ -56,7 +56,7 @@ abstract class PromiseImpl<T> implements Promise<T> { * operations. */ PromiseImpl(PromiseFactory factory) { - this.factory = factory; + this.factory = requireNonNull(factory); callbacks = new ConcurrentLinkedQueue<>(); } @@ -72,6 +72,30 @@ abstract class PromiseImpl<T> implements Promise<T> { } /** + * Return a new {@link ResolvedPromiseImpl} using the {@link PromiseFactory} + * of this PromiseImpl. + * + * @param v Value for the ResolvedPromiseImpl. + * @return A new ResolvedPromiseImpl. + * @since 1.1 + */ + <V> ResolvedPromiseImpl<V> resolved(V v) { + return new ResolvedPromiseImpl<>(v, factory); + } + + /** + * Return a new {@link FailedPromiseImpl} using the {@link PromiseFactory} + * of this PromiseImpl. + * + * @param f Failure for the FailedPromiseImpl. + * @return A new FailedPromiseImpl. + * @since 1.1 + */ + <V> FailedPromiseImpl<V> failed(Throwable f) { + return new FailedPromiseImpl<>(f, factory); + } + + /** * {@inheritDoc} */ @Override @@ -142,9 +166,25 @@ abstract class PromiseImpl<T> implements Promise<T> { } /** - * {@inheritDoc} + * Run the specified chain when the specified promise is resolved. * - * @since 1.1 + * @param promise The promise associated with the chain. + * @param chain The chain to run when the promise is resolved. + */ + static <V> void chain(Promise<V> promise, Runnable chain) { + if (promise.isDone()) { + try { + chain.run(); + } catch (Throwable t) { + uncaughtException(t); + } + } else { + promise.onResolve(chain); + } + } + + /** + * {@inheritDoc} */ @Override public Promise<T> onSuccess(Consumer< ? super T> success) { @@ -179,8 +219,6 @@ abstract class PromiseImpl<T> implements Promise<T> { /** * {@inheritDoc} - * - * @since 1.1 */ @Override public Promise<T> onFailure(Consumer< ? super Throwable> failure) { @@ -219,8 +257,8 @@ abstract class PromiseImpl<T> implements Promise<T> { @Override public <R> Promise<R> then(Success<? super T, ? extends R> success, Failure failure) { DeferredPromiseImpl<R> chained = deferred(); - onResolve(chained.new Then<>(this, success, failure)); - return chained; + chain(this, chained.new Then<>(this, success, failure)); + return chained.orDone(); } /** @@ -233,14 +271,12 @@ abstract class PromiseImpl<T> implements Promise<T> { /** * {@inheritDoc} - * - * @since 1.1 */ @Override public Promise<T> thenAccept(Consumer< ? super T> consumer) { DeferredPromiseImpl<T> chained = deferred(); - onResolve(chained.new ThenAccept(this, consumer)); - return chained; + chain(this, chained.new ThenAccept(this, consumer)); + return chained.orDone(); } @@ -250,8 +286,8 @@ abstract class PromiseImpl<T> implements Promise<T> { @Override public Promise<T> filter(Predicate<? super T> predicate) { DeferredPromiseImpl<T> chained = deferred(); - onResolve(chained.new Filter(this, predicate)); - return chained; + chain(this, chained.new Filter(this, predicate)); + return chained.orDone(); } /** @@ -260,8 +296,8 @@ abstract class PromiseImpl<T> implements Promise<T> { @Override public <R> Promise<R> map(Function<? super T, ? extends R> mapper) { DeferredPromiseImpl<R> chained = deferred(); - onResolve(chained.new Map<>(this, mapper)); - return chained; + chain(this, chained.new Map<>(this, mapper)); + return chained.orDone(); } @@ -271,8 +307,8 @@ abstract class PromiseImpl<T> implements Promise<T> { @Override public <R> Promise<R> flatMap(Function<? super T, Promise<? extends R>> mapper) { DeferredPromiseImpl<R> chained = deferred(); - onResolve(chained.new FlatMap<>(this, mapper)); - return chained; + chain(this, chained.new FlatMap<>(this, mapper)); + return chained.orDone(); } /** @@ -281,8 +317,8 @@ abstract class PromiseImpl<T> implements Promise<T> { @Override public Promise<T> recover(Function<Promise<?>, ? extends T> recovery) { DeferredPromiseImpl<T> chained = deferred(); - onResolve(chained.new Recover(this, recovery)); - return chained; + chain(this, chained.new Recover(this, recovery)); + return chained.orDone(); } /** @@ -291,8 +327,8 @@ abstract class PromiseImpl<T> implements Promise<T> { @Override public Promise<T> recoverWith(Function<Promise<?>, Promise<? extends T>> recovery) { DeferredPromiseImpl<T> chained = deferred(); - onResolve(chained.new RecoverWith(this, recovery)); - return chained; + chain(this, chained.new RecoverWith(this, recovery)); + return chained.orDone(); } /** @@ -301,85 +337,28 @@ abstract class PromiseImpl<T> implements Promise<T> { @Override public Promise<T> fallbackTo(Promise<? extends T> fallback) { DeferredPromiseImpl<T> chained = deferred(); - onResolve(chained.new FallbackTo(this, fallback)); - return chained; + chain(this, chained.new FallbackTo(this, fallback)); + return chained.orDone(); } /** * {@inheritDoc} - * - * @since 1.1 */ @Override public Promise<T> timeout(long millis) { DeferredPromiseImpl<T> chained = deferred(); - onResolve(chained.new ChainImpl(this)); - if (!isDone()) { - PromiseImpl<T> timedout = new FailedPromiseImpl<>( - new TimeoutException(), factory); - onResolve(new Timeout(chained.new ChainImpl(timedout), millis, - TimeUnit.MILLISECONDS)); - } - return chained; - } - - /** - * Timeout class used by the {@link PromiseImpl#timeout(long)} method to - * cancel timeout when the Promise is resolved. - * - * @Immutable - * @since 1.1 - */ - private final class Timeout implements Runnable { - private final ScheduledFuture< ? > future; - - Timeout(Runnable operation, long delay, TimeUnit unit) { - future = schedule(operation, delay, unit); - } - - @Override - public void run() { - if (future != null) { - future.cancel(false); - } - } + chain(this, chained.new Timeout(this, millis)); + return chained.orDone(); } /** * {@inheritDoc} - * - * @since 1.1 */ @Override public Promise<T> delay(long millis) { DeferredPromiseImpl<T> chained = deferred(); - onResolve(new Delay(chained.new ChainImpl(this), millis, - TimeUnit.MILLISECONDS)); - return chained; - } - - /** - * Delay class used by the {@link PromiseImpl#delay(long)} method to delay - * chaining a promise. - * - * @Immutable - * @since 1.1 - */ - private final class Delay implements Runnable { - private final Runnable operation; - private final long delay; - private final TimeUnit unit; - - Delay(Runnable operation, long delay, TimeUnit unit) { - this.operation = operation; - this.delay = delay; - this.unit = unit; - } - - @Override - public void run() { - schedule(operation, delay, unit); - } + chain(this, chained.new Delay(this, millis)); + return chained.orDone(); } /** diff --git a/bundles/org.eclipse.osgi.util/src/org/osgi/util/promise/ResolvedPromiseImpl.java b/bundles/org.eclipse.osgi.util/src/org/osgi/util/promise/ResolvedPromiseImpl.java index d65146576..e5fa47a9a 100644 --- a/bundles/org.eclipse.osgi.util/src/org/osgi/util/promise/ResolvedPromiseImpl.java +++ b/bundles/org.eclipse.osgi.util/src/org/osgi/util/promise/ResolvedPromiseImpl.java @@ -16,6 +16,11 @@ package org.osgi.util.promise; +import static java.util.Objects.requireNonNull; + +import org.osgi.util.function.Consumer; +import org.osgi.util.function.Function; + /** * Resolved Promise implementation. * <p> @@ -69,7 +74,7 @@ final class ResolvedPromiseImpl<T> extends PromiseImpl<T> { } /** - * Return a holder of the result of this PromiseImpl. + * {@inheritDoc} */ @Override Result<T> collect() { @@ -80,4 +85,61 @@ final class ResolvedPromiseImpl<T> extends PromiseImpl<T> { public String toString() { return super.toString() + "[resolved: " + value + "]"; } + + /** + * {@inheritDoc} + */ + @Override + public Promise<T> onFailure(Consumer< ? super Throwable> failure) { + requireNonNull(failure); + return this; + } + + /** + * {@inheritDoc} + */ + @Override + public <R> Promise<R> then(Success< ? super T, ? extends R> success, + Failure failure) { + if (success == null) { + return resolved(null); + } + return super.then(success, failure); + } + + /** + * {@inheritDoc} + */ + @Override + public Promise<T> recover(Function<Promise< ? >, ? extends T> recovery) { + requireNonNull(recovery); + return this; + } + + /** + * {@inheritDoc} + */ + @Override + public Promise<T> recoverWith( + Function<Promise< ? >,Promise< ? extends T>> recovery) { + requireNonNull(recovery); + return this; + } + + /** + * {@inheritDoc} + */ + @Override + public Promise<T> fallbackTo(Promise< ? extends T> fallback) { + requireNonNull(fallback); + return this; + } + + /** + * {@inheritDoc} + */ + @Override + public Promise<T> timeout(long millis) { + return this; + } } diff --git a/bundles/org.eclipse.osgi/osgi/src/org/osgi/framework/Bundle.java b/bundles/org.eclipse.osgi/osgi/src/org/osgi/framework/Bundle.java index 81a8f18b2..545299bc4 100644 --- a/bundles/org.eclipse.osgi/osgi/src/org/osgi/framework/Bundle.java +++ b/bundles/org.eclipse.osgi/osgi/src/org/osgi/framework/Bundle.java @@ -1,5 +1,5 @@ /* - * Copyright (c) OSGi Alliance (2000, 2013). All Rights Reserved. + * Copyright (c) OSGi Alliance (2000, 2018). All Rights Reserved. * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. @@ -399,8 +399,8 @@ public interface Bundle extends Comparable<Bundle> { * before continuing. If this does not occur in a reasonable time, a * {@code BundleException} is thrown to indicate this bundle was unable to * be stopped.</li> - * <li>If the {@link #STOP_TRANSIENT} option is not set then then set this - * bundle's persistent autostart setting to to <em>Stopped</em>. When the + * <li>If the {@link #STOP_TRANSIENT} option is not set then set this + * bundle's persistent autostart setting to <em>Stopped</em>. When the * Framework is restarted and this bundle's autostart setting is * <em>Stopped</em>, this bundle must not be automatically started.</li> * <li>If this bundle's state is not {@code STARTING} or {@code ACTIVE} then diff --git a/bundles/org.eclipse.osgi/osgi/src/org/osgi/framework/BundleContext.java b/bundles/org.eclipse.osgi/osgi/src/org/osgi/framework/BundleContext.java index 6e24d39be..6c43d322b 100644 --- a/bundles/org.eclipse.osgi/osgi/src/org/osgi/framework/BundleContext.java +++ b/bundles/org.eclipse.osgi/osgi/src/org/osgi/framework/BundleContext.java @@ -1,5 +1,5 @@ /* - * Copyright (c) OSGi Alliance (2000, 2015). All Rights Reserved. + * Copyright (c) OSGi Alliance (2000, 2018). All Rights Reserved. * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. @@ -405,7 +405,7 @@ public interface BundleContext extends BundleReference { * <li>A property named {@link Constants#SERVICE_SCOPE} identifying the * scope of the service.</li> * <li>A property named {@link Constants#SERVICE_BUNDLEID} identifying the - * the context bundle.</li> + * context bundle.</li> * </ul> * Properties with these names in the specified {@code Dictionary} will be * ignored.</li> diff --git a/bundles/org.eclipse.osgi/osgi/src/org/osgi/framework/Constants.java b/bundles/org.eclipse.osgi/osgi/src/org/osgi/framework/Constants.java index b53b1a9b4..41e648afb 100644 --- a/bundles/org.eclipse.osgi/osgi/src/org/osgi/framework/Constants.java +++ b/bundles/org.eclipse.osgi/osgi/src/org/osgi/framework/Constants.java @@ -1,5 +1,5 @@ /* - * Copyright (c) OSGi Alliance (2000, 2017). All Rights Reserved. + * Copyright (c) OSGi Alliance (2000, 2018). All Rights Reserved. * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. @@ -783,9 +783,8 @@ public interface Constants { * Manifest header directive value identifying a reexport visibility type. A * reexport visibility type indicates any packages that are exported by the * required bundle are re-exported by the requiring bundle. Any arbitrary - * arbitrary matching attributes with which they were exported by the - * required bundle are deleted. - * + * matching attributes with which they were exported by the required bundle + * are deleted. * <p> * The directive value is encoded in the Require-Bundle manifest header * like: diff --git a/bundles/org.eclipse.osgi/osgi/src/org/osgi/framework/hooks/resolver/ResolverHook.java b/bundles/org.eclipse.osgi/osgi/src/org/osgi/framework/hooks/resolver/ResolverHook.java index 7b2a0a5db..6c1f3732d 100644 --- a/bundles/org.eclipse.osgi/osgi/src/org/osgi/framework/hooks/resolver/ResolverHook.java +++ b/bundles/org.eclipse.osgi/osgi/src/org/osgi/framework/hooks/resolver/ResolverHook.java @@ -1,5 +1,5 @@ /* - * Copyright (c) OSGi Alliance (2010, 2013). All Rights Reserved. + * Copyright (c) OSGi Alliance (2010, 2018). All Rights Reserved. * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. @@ -51,9 +51,8 @@ import org.osgi.framework.wiring.FrameworkWiring; * stop calling the resolver hook instance provided by the unregistered hook * factory and the current resolve process must fail. If possible, an exception * must be thrown to the caller of the API which triggered the resolve process. - * In cases where the the caller is not available a framework event of type - * error should be fired.</li> - * + * In cases where the caller is not available a framework event of type error + * should be fired.</li> * <li>For each registered hook factory call the * {@link ResolverHookFactory#begin(Collection)} method to inform the hooks * about a resolve process beginning and to obtain a Resolver Hook instance that diff --git a/bundles/org.eclipse.osgi/osgi/src/org/osgi/framework/hooks/service/ListenerHook.java b/bundles/org.eclipse.osgi/osgi/src/org/osgi/framework/hooks/service/ListenerHook.java index d7cea4e51..b17e35a5c 100644 --- a/bundles/org.eclipse.osgi/osgi/src/org/osgi/framework/hooks/service/ListenerHook.java +++ b/bundles/org.eclipse.osgi/osgi/src/org/osgi/framework/hooks/service/ListenerHook.java @@ -1,5 +1,5 @@ /* - * Copyright (c) OSGi Alliance (2008, 2015). All Rights Reserved. + * Copyright (c) OSGi Alliance (2008, 2018). All Rights Reserved. * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. @@ -102,7 +102,7 @@ public interface ListenerHook { * service listener. This method can be used to detect this rare * occurrence. * - * @return {@code false} if the listener has not been been removed, + * @return {@code false} if the listener has not been removed, * {@code true} otherwise. */ boolean isRemoved(); diff --git a/bundles/org.eclipse.osgi/osgi/src/org/osgi/framework/launch/Framework.java b/bundles/org.eclipse.osgi/osgi/src/org/osgi/framework/launch/Framework.java index fcdc6be30..7fa67978e 100644 --- a/bundles/org.eclipse.osgi/osgi/src/org/osgi/framework/launch/Framework.java +++ b/bundles/org.eclipse.osgi/osgi/src/org/osgi/framework/launch/Framework.java @@ -1,5 +1,5 @@ /* - * Copyright (c) OSGi Alliance (2008, 2015). All Rights Reserved. + * Copyright (c) OSGi Alliance (2008, 2018). All Rights Reserved. * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. @@ -85,8 +85,8 @@ public interface Framework extends Bundle { * {@link #STARTING}, {@link #ACTIVE} or {@link #STOPPING} states. * * <p> - * All framework events fired by this method method are also delivered to - * the specified FrameworkListeners in the order they are specified before + * All framework events fired by this method are also delivered to the + * specified FrameworkListeners in the order they are specified before * returning from this method. After returning from this method the * specified listeners are no longer notified of framework events. * diff --git a/bundles/org.eclipse.osgi/osgi/src/org/osgi/framework/wiring/BundleRevision.java b/bundles/org.eclipse.osgi/osgi/src/org/osgi/framework/wiring/BundleRevision.java index 814d8d4db..0d0ae508d 100644 --- a/bundles/org.eclipse.osgi/osgi/src/org/osgi/framework/wiring/BundleRevision.java +++ b/bundles/org.eclipse.osgi/osgi/src/org/osgi/framework/wiring/BundleRevision.java @@ -1,5 +1,5 @@ /* - * Copyright (c) OSGi Alliance (2010, 2015). All Rights Reserved. + * Copyright (c) OSGi Alliance (2010, 2018). All Rights Reserved. * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. @@ -111,7 +111,7 @@ public interface BundleRevision extends BundleReference, Resource { * The name of the package is stored in the capability attribute of the same * name as this namespace (osgi.wiring.package). The other directives and * attributes of the package, from the {@link Constants#EXPORT_PACKAGE - * Export-Package} manifest header, can be found in the cabability's + * Export-Package} manifest header, can be found in the capability's * {@link BundleCapability#getDirectives() directives} and * {@link BundleCapability#getAttributes() attributes}. The * {@link Constants#VERSION_ATTRIBUTE version} capability attribute must @@ -157,7 +157,7 @@ public interface BundleRevision extends BundleReference, Resource { * attribute of the same name as this namespace (osgi.wiring.bundle). The * other directives and attributes of the bundle, from the * {@link Constants#BUNDLE_SYMBOLICNAME Bundle-SymbolicName} manifest - * header, can be found in the cabability's + * header, can be found in the capability's * {@link BundleCapability#getDirectives() directives} and * {@link BundleCapability#getAttributes() attributes}. The * {@link Constants#BUNDLE_VERSION_ATTRIBUTE bundle-version} capability @@ -197,7 +197,7 @@ public interface BundleRevision extends BundleReference, Resource { * attribute of the same name as this namespace (osgi.wiring.host). The * other directives and attributes of the bundle, from the * {@link Constants#BUNDLE_SYMBOLICNAME Bundle-SymbolicName} manifest - * header, can be found in the cabability's + * header, can be found in the capability's * {@link BundleCapability#getDirectives() directives} and * {@link BundleCapability#getAttributes() attributes}. The * {@link Constants#BUNDLE_VERSION_ATTRIBUTE bundle-version} capability |