Skip to content

Commit

Permalink
Add back generic types to Promise onComplete(), onError() and then()
Browse files Browse the repository at this point in the history
  • Loading branch information
matrei committed Nov 21, 2023
1 parent 956b0c6 commit 78fa7e6
Show file tree
Hide file tree
Showing 17 changed files with 66 additions and 58 deletions.
6 changes: 3 additions & 3 deletions grails-async-core/src/main/groovy/grails/async/Promise.groovy
Original file line number Diff line number Diff line change
Expand Up @@ -38,18 +38,18 @@ interface Promise<T> extends Future<T> {
* @param callable
* @return The Promise
*/
Promise<?> onComplete(Closure<?> callable)
Promise<T> onComplete(Closure<T> callable)

/**
* Execute the given closure when an error occurs
*
* @param callable
* @return The Promise
*/
Promise<?> onError(Closure<?> callable)
Promise<T> onError(Closure<T> callable)

/**
* Same as #onComplete
*/
Promise<?> then(Closure<?> callable)
Promise<T> then(Closure<T> callable)
}
Original file line number Diff line number Diff line change
Expand Up @@ -42,7 +42,7 @@ interface PromiseFactory {
* @param decorators The decorators
* @return The decorated closure
*/
<T> Closure<T> applyDecorators(Closure<?> c, List<PromiseDecorator> decorators)
<T> Closure<T> applyDecorators(Closure<T> c, List<PromiseDecorator> decorators)

/**
* Creates a promise with a value pre-bound to it
Expand Down Expand Up @@ -152,7 +152,7 @@ interface PromiseFactory {
* @param promises The promises
* @param callable The callback to execute
*/
<T> Promise<List<T>> onComplete(List<Promise<T>> promises, Closure<?> callable)
<T> Promise<List<T>> onComplete(List<Promise<T>> promises, Closure<T> callable)

/**
* Executes the given callback if an error occurs for the list of promises
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -105,17 +105,17 @@ class PromiseList<T> implements Promise<List<T>> {
* @param callable The closure
*/
@Override
Promise<?> onComplete(Closure<?> callable) {
Promise<List<T>> onComplete(Closure callable) {
return Promises.onComplete(promises, callable)
}

@Override
Promise<?> onError(Closure<?> callable) {
Promise<List<T>> onError(Closure callable) {
return Promises.onError(promises, callable)
}

@Override
Promise<?> then(Closure<?> callable) {
Promise<List<T>> then(Closure callable) {
return Promises.onComplete(promises, { List<T> values -> return values }).then(callable)
}

Expand Down
11 changes: 7 additions & 4 deletions grails-async-core/src/main/groovy/grails/async/PromiseMap.groovy
Original file line number Diff line number Diff line change
Expand Up @@ -236,7 +236,8 @@ class PromiseMap<K,V> implements Promise<Map<K,V>> {
return resultMap
}

Promise<Map<K,V>> onComplete(Closure<?> callable) {
@Override
Promise<Map<K,V>> onComplete(Closure<Map<K,V>> callable) {
List<Promise<V>> promises = new ArrayList<Promise<V>>(promises.values())
Promises.onComplete(promises) { List<V> values ->
Map<K,V> resultMap = [:]
Expand All @@ -253,16 +254,18 @@ class PromiseMap<K,V> implements Promise<Map<K,V>> {
return this
}

Promise<Map<K,V>> onError(Closure<?> callable) {
@Override
Promise<Map<K,V>> onError(Closure<Map<K,V>> callable) {
Promises.onError(new ArrayList<Promise<V>>(promises.values()), callable)
return this
}

Promise<Map<K, V>> then(Closure<?> callable) {
@Override
Promise<Map<K, V>> then(Closure<Map<K,V>> callable) {
return onComplete(callable)
}

Promise<Map<K, V>> leftShift(Closure<?> callable) {
Promise<Map<K, V>> leftShift(Closure callable) {
return then(callable)
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -71,7 +71,7 @@ class Promises {
/**
* @see PromiseFactory#onComplete(java.util.List, groovy.lang.Closure)
*/
static<T> Promise<List<T>> onComplete(List<Promise<T>> promises, Closure<?> callable) {
static<T> Promise<List<T>> onComplete(List<Promise<T>> promises, Closure<T> callable) {
return getPromiseFactory().onComplete(promises, callable)
}
/**
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -67,21 +67,21 @@ class BoundPromise<T> implements Promise<T> {
return this
}

Promise<?> onComplete(Closure<?> callable) {
Promise<T> onComplete(Closure<T> callable) {
if (!(value instanceof Throwable)) {
return new BoundPromise(callable.call(value))
}
return this
}

Promise<?> onError(Closure<?> callable) {
Promise<T> onError(Closure<T> callable) {
if (value instanceof Throwable) {
return new BoundPromise(callable.call(value))
}
return this
}

Promise<?> then(Closure<?> callable) {
Promise<T> then(Closure<T> callable) {
if (!(value instanceof Throwable)) {
try {
return new BoundPromise(callable.call(value))
Expand All @@ -94,7 +94,7 @@ class BoundPromise<T> implements Promise<T> {
}
}

Promise<?> leftShift(Closure<?> callable) {
Promise<T> leftShift(Closure<T> callable) {
then(callable)
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -74,24 +74,24 @@ class SynchronousPromise<T> implements Promise<T> {
return this
}

Promise<?> onComplete(Closure<?> callable) {
Promise<T> onComplete(Closure<T> callable) {
try { callable.call(get()) }
catch (Throwable ignored) {}
return this
}

Promise<?> onError(Closure<?> callable) {
Promise<T> onError(Closure<T> callable) {
try { get() }
catch (Throwable e) { callable.call(e) }
return this
}

Promise<?> then(Closure<?> callable) {
Promise<T> then(Closure<T> callable) {
final value = get()
return new SynchronousPromise(callable.curry(value))
}

Promise<?> leftShift(Closure<?> callable) {
Promise<T> leftShift(Closure<T> callable) {
then(callable)
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -73,7 +73,8 @@ class SynchronousPromiseFactory extends AbstractPromiseFactory {
return promises.collect { Promise<T> p -> p.get() }
}

<T> Promise<?> onComplete(List<Promise<T>> promises, Closure<?> callable) {
@Override
<T> Promise<T> onComplete(List<Promise<T>> promises, Closure<T> callable) {
try {
List<T> values = promises.collect { Promise<T> p -> p.get() }
return new BoundPromise(callable.call(values))
Expand All @@ -82,7 +83,8 @@ class SynchronousPromiseFactory extends AbstractPromiseFactory {
}
}

<T> Promise<?> onError(List<Promise<T>> promises, Closure<?> callable) {
@Override
<T> Promise<List<T>> onError(List<Promise<T>> promises, Closure<?> callable) {
try {
List<T> values = promises.collect() { Promise<T> p -> p.get() }
return new BoundPromise<List<T>>(values)
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -73,25 +73,28 @@ class CachedThreadPoolPromiseFactory extends AbstractPromiseFactory implements C
}

@Override
<T> Promise<?> onComplete(List<Promise<T>> promises, Closure<?> callable) {
<T> Promise<List<T>> onComplete(List<Promise<T>> promises, Closure<T> callable) {
return executorService.submit({
while (promises.every { Promise promise -> !promise.isDone() }) {
// wait (is this hogging the cpu?)
}
List<T> values = promises.collect { Promise<T> promise -> promise.get() }
callable.call(values)
}) as Promise<?>
}) as Promise<List<T>>
}

@Override
<T> Promise<?> onError(List<Promise<T>> promises, Closure<?> callable) {
<T> Promise<List<T>> onError(List<Promise<T>> promises, Closure<?> callable) {
return executorService.submit({
while (promises.every { Promise promise -> !promise.isDone() }) {
// wait (is this hogging the cpu?)
}
try { for (Promise<T> promise : promises) { promise.get() } }
catch (Throwable e) { callable.call(e) }
}) as Promise<?>
catch (Throwable e) {
callable.call(e)
return e
}
}) as Promise<List<T>>
}

@Override
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -57,21 +57,21 @@ class FutureTaskChildPromise<T> implements Promise<T> {
}

@Override
Promise<?> onComplete(Closure<?> callable) {
Promise<T> onComplete(Closure<T> callable) {
def newPromise = new FutureTaskChildPromise(promiseFactory, this, callable)
successCallbacks.add(newPromise)
return newPromise
}

@Override
Promise<?> onError(Closure<?> callable) {
Promise<T> onError(Closure<T> callable) {
def newPromise = new FutureTaskChildPromise(promiseFactory, this, callable)
failureCallbacks.add(newPromise)
return newPromise
}

@Override
Promise<?> then(Closure<?> callable) {
Promise<T> then(Closure<T> callable) {
return onComplete(callable)
}

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -82,7 +82,7 @@ class FutureTaskPromise<T> extends FutureTask<T> implements Promise<T> {
}

@Override
Promise<?> onComplete(Closure<?> callable) {
Promise<T> onComplete(Closure<T> callable) {
synchronized (successCallbacks) {
if (isDone()) {
try {
Expand All @@ -101,7 +101,7 @@ class FutureTaskPromise<T> extends FutureTask<T> implements Promise<T> {
}

@Override
Promise<?> onError(Closure<?> callable) {
Promise<T> onError(Closure<T> callable) {
synchronized (failureCallbacks) {
if (isDone()) {
try {
Expand All @@ -120,7 +120,7 @@ class FutureTaskPromise<T> extends FutureTask<T> implements Promise<T> {
}

@Override
Promise<?> then(Closure callable) {
Promise<T> then(Closure<T> callable) {
return onComplete(callable)
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -78,12 +78,12 @@ class GparsPromise<T> implements Promise<T> {
return this
}

Promise<?> leftShift(Closure<?> callable) {
Promise<T> leftShift(Closure<T> callable) {
then(callable)
}

@Override
Promise<?> onComplete(Closure<?> callable) {
Promise<T> onComplete(Closure<T> callable) {
def decoratedCallable= promiseFactory.applyDecorators(callable, null)
internalPromise.whenBound { T value ->
if (!(value instanceof Throwable)) {
Expand All @@ -95,7 +95,7 @@ class GparsPromise<T> implements Promise<T> {
}

@Override
Promise<?> onError(Closure<?> callable) {
Promise<T> onError(Closure<T> callable) {
def decoratedCallable = promiseFactory.applyDecorators(callable, null)
internalPromise.whenBound { T value ->
if (value instanceof Throwable) {
Expand All @@ -107,7 +107,7 @@ class GparsPromise<T> implements Promise<T> {
}

@Override
Promise<?> then(Closure<?> callable) {
Promise<T> then(Closure<T> callable) {
def decoratedCallable = promiseFactory.applyDecorators(callable, null)
return new GparsPromise(promiseFactory, internalPromise.then(decoratedCallable))
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -100,18 +100,18 @@ class GparsPromiseFactory extends AbstractPromiseFactory {
}

@Override
<T> Promise<?> onComplete(List<Promise<T>> promises, Closure<?> callable) {
return new GparsPromise<?>(
<T> Promise<T> onComplete(List<Promise<T>> promises, Closure<T> callable) {
return new GparsPromise<T>(
this,
Dataflow.whenAllBound(toGparsPromises(promises), callable as Closure)
)
}

@Override
<T> Promise<?> onError(List<Promise<T>> promises, Closure<?> callable) {
return new GparsPromise<?>(
<T> Promise<List<T>> onError(List<Promise<T>> promises, Closure<?> callable) {
return new GparsPromise<List<T>>(
this,
Dataflow.whenAllBound(toGparsPromises(promises), {} as Closure<T>, callable as Closure)
Dataflow.whenAllBound(toGparsPromises(promises), {} as Closure<T>, callable as Closure<T>)
)
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -57,8 +57,8 @@ class RxPromiseFactory extends AbstractPromiseFactory {
}

@Override
<T> Promise<?> onComplete(List<Promise<T>> promises, Closure<?> callable) {
new RxPromise<>(this, Observable.concat(
<T> Promise<T> onComplete(List<Promise<T>> promises, Closure<T> callable) {
new RxPromise<T>(this, Observable.concat(
promises.collect() { Promise p ->
if(p instanceof BoundPromise) {
return Observable.just(((BoundPromise)p).value)
Expand All @@ -72,8 +72,8 @@ class RxPromiseFactory extends AbstractPromiseFactory {
}

@Override
<T> Promise<?> onError(List<Promise<T>> promises, Closure<?> callable) {
new RxPromise<>(this, Observable.concat(
<T> Promise<T> onError(List<Promise<T>> promises, Closure<?> callable) {
new RxPromise<T>(this, Observable.concat(
promises.collect() { Promise p -> ((RxPromise)p).subject as Observable<T> }
).toList())
.onError(callable)
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -100,19 +100,19 @@ class RxPromise<T> implements Promise<T> {
}

@Override
Promise<?> onComplete(Closure callable) {
Promise<T> onComplete(Closure<T> callable) {
def decoratedCallable = promiseFactory.applyDecorators(callable, null)
return new RxPromise<T>(promiseFactory, subject.map(decoratedCallable as Function<T, T>))
}

@Override
Promise<?> onError(Closure callable) {
Promise<T> onError(Closure<T> callable) {
def decoratedCallable = promiseFactory.applyDecorators(callable, null)
return new RxPromise<T>(promiseFactory, subject.doOnError(decoratedCallable as Consumer<Throwable>))
}

@Override
Promise<?> then(Closure callable) {
Promise<T> then(Closure<T> callable) {
return onComplete(callable)
}

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -57,8 +57,8 @@ class RxPromiseFactory extends AbstractPromiseFactory {
}

@Override
<T> Promise<?> onComplete(List<Promise<T>> promises, Closure<?> callable) {
new RxPromise<>(this, Observable.concat(
<T> Promise<T> onComplete(List<Promise<T>> promises, Closure<T> callable) {
new RxPromise<T>(this, Observable.concat(
promises.collect { Promise p ->
if(p instanceof BoundPromise) {
return Observable.just(((BoundPromise)p).value) as Observable<T>
Expand All @@ -72,10 +72,10 @@ class RxPromiseFactory extends AbstractPromiseFactory {
}

@Override
<T> Promise<?> onError(List<Promise<T>> promises, Closure<?> callable) {
new RxPromise<>(this, Observable.concat(
promises.collect { Promise p -> ((RxPromise)p).toObservable() as Observable<T> }
<T> Promise<List<T>> onError(List<Promise<T>> promises, Closure<?> callable) {
new RxPromise(this, Observable.concat(
promises.collect { ((RxPromise<T>)it).toObservable() }
).toList())
.onError(callable)
.onError(callable) as Promise<List<T>>
}
}
Loading

0 comments on commit 78fa7e6

Please sign in to comment.