using java completionstage in asynchronous programming · •what: java standard database access...

58
Copyright © 2018, Oracle and/or its affiliates. All rights reserved. | Using Java CompletionStage in Asynchronous Programming DEV4798 Douglas Surber Oracle Database JDBC Architect Database Server Technologies October 25, 2018

Upload: others

Post on 30-Mar-2020

18 views

Category:

Documents


0 download

TRANSCRIPT

Page 1: Using Java CompletionStage in Asynchronous Programming · •What: Java standard database access API that never blocks user threads •Who: Developed by the JDBC Community, JDBC Expert

Copyright © 2018, Oracle and/or its affiliates. All rights reserved. |

Using Java CompletionStage in Asynchronous ProgrammingDEV4798

Douglas SurberOracle Database JDBC ArchitectDatabase Server TechnologiesOctober 25, 2018

Page 2: Using Java CompletionStage in Asynchronous Programming · •What: Java standard database access API that never blocks user threads •Who: Developed by the JDBC Community, JDBC Expert

Copyright © 2018, Oracle and/or its affiliates. All rights reserved. |

Safe Harbor Statement

The following is intended to outline our general product direction. It is intended for information purposes only, and may not be incorporated into any contract. It is not a commitment to deliver any material, code, or functionality, and should not be relied upon in making purchasing decisions. The development, release, timing, and pricing of any features or functionality described for Oracle’s products may change and remains at the sole discretion of Oracle Corporation.

2

Page 3: Using Java CompletionStage in Asynchronous Programming · •What: Java standard database access API that never blocks user threads •Who: Developed by the JDBC Community, JDBC Expert

Copyright © 2018, Oracle and/or its affiliates. All rights reserved. |

Introduction to CompletionStageWhat are java.util.concurrent.CompletionStageand java.util.concurrent.CompletableFuture?

3

Page 4: Using Java CompletionStage in Asynchronous Programming · •What: Java standard database access API that never blocks user threads •Who: Developed by the JDBC Community, JDBC Expert

Copyright © 2018, Oracle and/or its affiliates. All rights reserved. |

CompletableFuture:The Promises of Java[DEV5375]Venkat SubramaniamWednesday, October 24

4

Page 5: Using Java CompletionStage in Asynchronous Programming · •What: Java standard database access API that never blocks user threads •Who: Developed by the JDBC Community, JDBC Expert

Copyright © 2018, Oracle and/or its affiliates. All rights reserved. |

Hands-on Lab: The Asynchronous Java Database Access Driver[HOL4799]Douglas SurberWednesday, October 24

5

Page 6: Using Java CompletionStage in Asynchronous Programming · •What: Java standard database access API that never blocks user threads •Who: Developed by the JDBC Community, JDBC Expert

Copyright © 2018, Oracle and/or its affiliates. All rights reserved. |

• A stage of a possibly asynchronous computation, that performs an action or computes a value when another CompletionStage completes. A stage completes upon termination of its computation, but this may in turn trigger other dependent stages.• stage.thenApply(x -> square(x))

.thenAccept(x -> System.out.print(x))

.thenRun(() -> System.out.println());

6

java.util.concurrent.CompletionStagepublic interface CompletionStage<T>

Page 7: Using Java CompletionStage in Asynchronous Programming · •What: Java standard database access API that never blocks user threads •Who: Developed by the JDBC Community, JDBC Expert

Copyright © 2018, Oracle and/or its affiliates. All rights reserved. |

• Both a CompletionStage and a Future• A Future that may be explicitly completed (setting its value and status),

and may be used as a CompletionStage, supporting dependent functions and actions that trigger upon its completion.• CompletableFuture future = ...;future.complete(value);future.get();

public class CompletableFuture<T> implements Future<T>, CompletionStage<T>

7

java.util.concurrent.CompletableFuture

Page 8: Using Java CompletionStage in Asynchronous Programming · •What: Java standard database access API that never blocks user threads •Who: Developed by the JDBC Community, JDBC Expert

Copyright © 2018, Oracle and/or its affiliates. All rights reserved. |

CompletionStage task = CompleteableFuture.supplyAsync(() -> 10);CompletionStage squareTask = task.thenApply( v -> v * v );

8

ExamplesupplyAsync(Supplier supplier), thenApply(Function function)

Page 9: Using Java CompletionStage in Asynchronous Programming · •What: Java standard database access API that never blocks user threads •Who: Developed by the JDBC Community, JDBC Expert

Copyright © 2018, Oracle and/or its affiliates. All rights reserved. |

public static <U> CompletableFuture<U> supplyAsync(Supplier<U> supplier)Returns a new CompletableFuture that is asynchronously completed by a task running in the ForkJoinPool.commonPool() with the value obtained by calling the given Supplier.Type Parameters: U - the function's return typeParameters: supplier - a function returning the value to be used to complete the returned CompletableFutureReturns: the new CompletableFuture

9

supplyAsync(Supplier supplier)java.util.concurrent.CompleteableFuture

Page 10: Using Java CompletionStage in Asynchronous Programming · •What: Java standard database access API that never blocks user threads •Who: Developed by the JDBC Community, JDBC Expert

Copyright © 2018, Oracle and/or its affiliates. All rights reserved. |

<U> CompletionStage<U> thenApply(Function<? super T,? extends U> fn)Returns a new CompletionStage that, when this stage completes normally, is executed with this stage's result as the argument to the supplied function.Type Parameters: U - the function's return typeParameters: fn - the function to use to compute the value of the returned CompletionStageReturns: the new CompletionStage

10

thenApply(Function<? super T,? extends U> fn)java.util.concurrent.CompletionStage

Page 11: Using Java CompletionStage in Asynchronous Programming · •What: Java standard database access API that never blocks user threads •Who: Developed by the JDBC Community, JDBC Expert

Copyright © 2018, Oracle and/or its affiliates. All rights reserved. | 11

ExampleCompletionStage task = CompleteableFuture.supplyAsync( () -> 10 );CompletionStage squareTask = task.thenApply( v -> v * v);

() -> 10task () -> 10

thenApply

v -> v * vsquareTask

task*

* CompletionStage

†dependency

Page 12: Using Java CompletionStage in Asynchronous Programming · •What: Java standard database access API that never blocks user threads •Who: Developed by the JDBC Community, JDBC Expert

Copyright © 2018, Oracle and/or its affiliates. All rights reserved. | 12

Example Execution

() -> 10

thenApply

v -> v * vsquareTask

task() -> 10task

thenApply

v -> v * vsquareTask

Page 13: Using Java CompletionStage in Asynchronous Programming · •What: Java standard database access API that never blocks user threads •Who: Developed by the JDBC Community, JDBC Expert

Copyright © 2018, Oracle and/or its affiliates. All rights reserved. |

Introduction to AoJWhat are AoJ and ADBA?

13

Page 14: Using Java CompletionStage in Asynchronous Programming · •What: Java standard database access API that never blocks user threads •Who: Developed by the JDBC Community, JDBC Expert

Copyright © 2018, Oracle and/or its affiliates. All rights reserved. |

• What: Java standard database access API that never blocks user threads• Who: Developed by the JDBC Community, JDBC Expert Group and Oracle• When: Targeted for a near future release, Java 14 perhaps• Why: Async apps have better scalability– Fewer threads means less thread scheduling, less thread contention– Database access is slow so blocked threads leave resources idle for a long time

• http://hg.openjdk.java.net/jdk/sandbox/file/JDK-8188051-branch/src/jdk.incubator.adba/share/classes

14

Asynchronous Database Access (ADBA)Proposed Java Standard

Page 15: Using Java CompletionStage in Asynchronous Programming · •What: Java standard database access API that never blocks user threads •Who: Developed by the JDBC Community, JDBC Expert

Copyright © 2018, Oracle and/or its affiliates. All rights reserved. |

public CompletionStage<List<Item>> itemsForAnswer(DataSource ds, int answer) {

String sql = "select id, name, answer from tab where answer = :target";

try (Session session = ds.getSession()) {

return session.<List<Item>>rowOperation(sql)

.set("target", answer, AdbaType.NUMERIC)

.collect(Collectors.mapping(

row -> new Item(row.at("id").get(Integer.class),

row.at("name").get(String.class),

row.at("answer").get(Integer.class)),

Collectors.toList()))

.submit()

.getCompletionStage();

}

}

15

ADBA ExampleSelect some items from a table

Page 16: Using Java CompletionStage in Asynchronous Programming · •What: Java standard database access API that never blocks user threads •Who: Developed by the JDBC Community, JDBC Expert

Copyright © 2018, Oracle and/or its affiliates. All rights reserved. |

DataSource ds = DataSourceFactory.newFactory("com.oracle.adbaoverjdbc.DataSourceFactory").builder().url("jdbc:derby:/myDB").username("scott").password("tiger").build();

• https://github.com/oracle/oracle-db-examples/tree/master/java/AoJ

16

ADBA over JDBC (AoJ)Open Source implementation of ADBA using any JDBC as a backend

Page 17: Using Java CompletionStage in Asynchronous Programming · •What: Java standard database access API that never blocks user threads •Who: Developed by the JDBC Community, JDBC Expert

Copyright © 2018, Oracle and/or its affiliates. All rights reserved. |

Using CompletionStage

17

Page 18: Using Java CompletionStage in Asynchronous Programming · •What: Java standard database access API that never blocks user threads •Who: Developed by the JDBC Community, JDBC Expert

Copyright © 2018, Oracle and/or its affiliates. All rights reserved. |

public CompletionStage<List<Item>> itemsForAnswer(DataSource ds, int answer) {

String sql = "select id, name, answer from tab where answer = :target";

try (Session session = ds.getSession()) {

return session.<List<Item>>rowOperation(sql)

.set("target", answer, AdbaType.NUMERIC)

.collect(Collectors.mapping(

row -> new Item(row.at("id").get(Integer.class),

row.at("name").get(String.class),

row.at("answer").get(Integer.class)),

Collectors.toList()))

.submit()

.getCompletionStage();

}

}

18

ADBA ExampleSelect some items from a table

Page 19: Using Java CompletionStage in Asynchronous Programming · •What: Java standard database access API that never blocks user threads •Who: Developed by the JDBC Community, JDBC Expert

Copyright © 2018, Oracle and/or its affiliates. All rights reserved. |

public Submission<T> submit() {if (isImmutable()) {

throw new IllegalStateException("TODO");}immutable();return group.submit(this);

}

19

submit()com.oracle.adbaoverjdbc.Operation

Page 20: Using Java CompletionStage in Asynchronous Programming · •What: Java standard database access API that never blocks user threads •Who: Developed by the JDBC Community, JDBC Expert

Copyright © 2018, Oracle and/or its affiliates. All rights reserved. |

Submission<S> submit(Operation<S> op) {memberTail =

op.attachCompletionHandler(op.follows(memberTail,getExecutor()));

return Submission.submit(this::cancel, memberTail);}

20

submit(Operation op)com.oracle.adbaoverjdbc.OperationGroup

Page 21: Using Java CompletionStage in Asynchronous Programming · •What: Java standard database access API that never blocks user threads •Who: Developed by the JDBC Community, JDBC Expert

Copyright © 2018, Oracle and/or its affiliates. All rights reserved. |

final CompletionStage<T> attachCompletionHandler(CompletionStage<T> result) {

return result.handle((r, t) -> {Throwable ex = unwrapException(t);checkAbort(ex);if (t == null)

return handleResult(r);else

throw handleError(ex);});

}

21

attachCompletionHandlercom.oracle.adbaoverjdbc.OperationGroup

Page 22: Using Java CompletionStage in Asynchronous Programming · •What: Java standard database access API that never blocks user threads •Who: Developed by the JDBC Community, JDBC Expert

Copyright © 2018, Oracle and/or its affiliates. All rights reserved. |

<U> CompletionStage<U> handle(BiFunction<? super T, Throwable, ? extends U> fn)Returns a new CompletionStage that, when this stage completes either normally or exceptionally, is executed with this stage's result and exception as arguments to the supplied function. When this stage is complete, the given function is invoked with the result (or null if none) and the exception (or null if none) of this stage as arguments, and the function's result is used to complete the returned stage.Type Parameters: U - the function's return typeParameters: fn - the function to use to compute the value of the returned CompletionStageReturns: the new CompletionStage

22

handle(BiFunction<?, Throwable, ?> fn)java.util.concurrent.CompletionStage

Page 23: Using Java CompletionStage in Asynchronous Programming · •What: Java standard database access API that never blocks user threads •Who: Developed by the JDBC Community, JDBC Expert

Copyright © 2018, Oracle and/or its affiliates. All rights reserved. | 23

attachCompletionHandlermemberTail = follows(...).handle( (r, t) -> { ... } )

Result of previous opmemberTail

memberTail

Result of previous op

handle

(r,t) ->{...}

follows(...)

Page 24: Using Java CompletionStage in Asynchronous Programming · •What: Java standard database access API that never blocks user threads •Who: Developed by the JDBC Community, JDBC Expert

Copyright © 2018, Oracle and/or its affiliates. All rights reserved. |

final CompletionStage<T> attachCompletionHandler(CompletionStage<T> result) {

return result.handle((r, t) -> {Throwable ex = unwrapException(t);checkAbort(ex);if (t == null)

return handleResult(r);else

throw handleError(ex);});

}

24

(r, t) -> { ... }com.oracle.adbaoverjdbc.OperationGroup

Page 25: Using Java CompletionStage in Asynchronous Programming · •What: Java standard database access API that never blocks user threads •Who: Developed by the JDBC Community, JDBC Expert

Copyright © 2018, Oracle and/or its affiliates. All rights reserved. |

Submission<S> submit(Operation<S> op) {memberTail =

op.attachCompletionHandler(op.follows(memberTail,getExecutor()));

return Submission.submit(this::cancel, memberTail);}

25

submit(Operation op)com.oracle.adbaoverjdbc.OperationGroup

Page 26: Using Java CompletionStage in Asynchronous Programming · •What: Java standard database access API that never blocks user threads •Who: Developed by the JDBC Community, JDBC Expert

Copyright © 2018, Oracle and/or its affiliates. All rights reserved. |

CompletionStage<T> follows(CompletionStage<?> predecessor,Executor executor) {

predecessor = attachFutureParameters(predecessor);return predecessor

.thenRunAsync(this::executeQuery, executor)

.thenCompose(this::moreRows);}

26

follows(CompletionStage<?> predecessor,Executor executor)

com.oracle.adbaoverjdbc.RowOperation

Page 27: Using Java CompletionStage in Asynchronous Programming · •What: Java standard database access API that never blocks user threads •Who: Developed by the JDBC Community, JDBC Expert

Copyright © 2018, Oracle and/or its affiliates. All rights reserved. |

CompletionStage<Void> thenRunAsync(Runnable action)Returns a new CompletionStage that, when this stage completes normally, executes the given action using this stage's default asynchronous execution facility.Parameters: action - the action to perform before completing the returned CompletionStageReturns: the new CompletionStage

27

thenRunAsync(Runnable action)java.util.concurrent.CompletionStage

Page 28: Using Java CompletionStage in Asynchronous Programming · •What: Java standard database access API that never blocks user threads •Who: Developed by the JDBC Community, JDBC Expert

Copyright © 2018, Oracle and/or its affiliates. All rights reserved. | 28

follows( . . . )predecessor.thenRunAsync(this::executeQuery, executor)

Result of previous oppredecessor Result of

previous op

thenRunAsync

executeQuery

Page 29: Using Java CompletionStage in Asynchronous Programming · •What: Java standard database access API that never blocks user threads •Who: Developed by the JDBC Community, JDBC Expert

Copyright © 2018, Oracle and/or its affiliates. All rights reserved. |

CompletionStage<T> follows(CompletionStage<?> predecessor,Executor executor) {

predecessor = attachFutureParameters(predecessor);return predecessor

.thenRunAsync(this::executeQuery, executor)

.thenCompose(this::moreRows);}

29

follows(CompletionStage<?> predecessor,Executor executor)

com.oracle.adbaoverjdbc.RowOperation

Page 30: Using Java CompletionStage in Asynchronous Programming · •What: Java standard database access API that never blocks user threads •Who: Developed by the JDBC Community, JDBC Expert

Copyright © 2018, Oracle and/or its affiliates. All rights reserved. |

<U> CompletionStage<U> thenCompose(Function<? super T,? extends CompletionStage<U>> fn)Returns a new CompletionStage that is completed with the same value as the CompletionStage returned by the given function.When this stage completes normally, the given function is invoked with this stage's result as the argument, returning another CompletionStage. When that stage completes normally, the CompletionStage returned by this method is completed with the same value.Type Parameters: U - the type of the returned CompletionStage's resultParameters: fn - the function to use to compute another CompletionStageReturns: the new CompletionStage

30

thenCompose(Function<?, CompletionStage>, Executor executor)

java.util.concurrent.CompletionStage

Page 31: Using Java CompletionStage in Asynchronous Programming · •What: Java standard database access API that never blocks user threads •Who: Developed by the JDBC Community, JDBC Expert

Copyright © 2018, Oracle and/or its affiliates. All rights reserved. | 31

follows( . . . )thenCompose(this::moreRows)

executeQuery executeQuery

thenCompose

moreRows

Page 32: Using Java CompletionStage in Asynchronous Programming · •What: Java standard database access API that never blocks user threads •Who: Developed by the JDBC Community, JDBC Expert

Copyright © 2018, Oracle and/or its affiliates. All rights reserved. | 32

submit(Operation op, Executor executor)com.oracle.adbaoverjdbc.OperationGroup

Result of previous op

(r,t) ->{...}

executeQuery

moreRows

thenCompose

thenRunAsync

handle

follows

Page 33: Using Java CompletionStage in Asynchronous Programming · •What: Java standard database access API that never blocks user threads •Who: Developed by the JDBC Community, JDBC Expert

Copyright © 2018, Oracle and/or its affiliates. All rights reserved. | 33

Executing RowOperationPrevious Operation

Result of previous op

(r,t) ->{...}

executeQuery

moreRows

thenCompose

thenRunAsync

handle

Page 34: Using Java CompletionStage in Asynchronous Programming · •What: Java standard database access API that never blocks user threads •Who: Developed by the JDBC Community, JDBC Expert

Copyright © 2018, Oracle and/or its affiliates. All rights reserved. | 34

Executing RowOperationexecuteQuery

Result of previous op

(r,t) ->{...}

executeQuery

moreRows

thenCompose

thenRunAsync

handle

Page 35: Using Java CompletionStage in Asynchronous Programming · •What: Java standard database access API that never blocks user threads •Who: Developed by the JDBC Community, JDBC Expert

Copyright © 2018, Oracle and/or its affiliates. All rights reserved. |

protected CompletionStage<T> moreRows(Object x) {

checkCanceled();

if (rowsRemain) {

return CompletableFuture

.runAsync(this::handleFetchRows, getExecutor())

.thenCompose(this::moreRows);

}

else {

return CompletableFuture

.supplyAsync(this::completeQuery, getExecutor());

}

}

35

moreRows(Object x)com.oracle.adbaoverjdbc.RowOperation

Page 36: Using Java CompletionStage in Asynchronous Programming · •What: Java standard database access API that never blocks user threads •Who: Developed by the JDBC Community, JDBC Expert

Copyright © 2018, Oracle and/or its affiliates. All rights reserved. |

public static CompletableFuture<Void> runAsync(Runnable runnable, Executor executor)Returns a new CompletableFuture that is asynchronously completed by a task running in the given executor after it runs the given action.Parameters: runnable - the action to run before completing the returned CompletableFutureexecutor - the executor to use for asynchronous executionReturns: the new CompletableFuture

36

runAsync(Runnable action, Executor executor)java.util.concurrent.CompletionStage

Page 37: Using Java CompletionStage in Asynchronous Programming · •What: Java standard database access API that never blocks user threads •Who: Developed by the JDBC Community, JDBC Expert

Copyright © 2018, Oracle and/or its affiliates. All rights reserved. | 37

moreRows( . . . )runAsync(this::handleFetchRows).thenCompose(this::moreRows)

handleFetchRows

thenCompose

moreRows

runAsync

Page 38: Using Java CompletionStage in Asynchronous Programming · •What: Java standard database access API that never blocks user threads •Who: Developed by the JDBC Community, JDBC Expert

Copyright © 2018, Oracle and/or its affiliates. All rights reserved. | 38

Executing RowOperationBefore moreRows(Object x)

Result of previous op

(r,t) ->{...}

executeQuery

moreRows

thenCompose

thenRunAsync

handle

Page 39: Using Java CompletionStage in Asynchronous Programming · •What: Java standard database access API that never blocks user threads •Who: Developed by the JDBC Community, JDBC Expert

Copyright © 2018, Oracle and/or its affiliates. All rights reserved. | 39

Executing RowOperationrunAsync(this::handleFetchRows).thenCompose(this::moreRows)

Result of previous op

(r,t) ->{...}

executeQuery

moreRows

thenCompose

thenRunAsync

handleFetchRows

thenCompose

moreRows

handle

runAsync

Page 40: Using Java CompletionStage in Asynchronous Programming · •What: Java standard database access API that never blocks user threads •Who: Developed by the JDBC Community, JDBC Expert

Copyright © 2018, Oracle and/or its affiliates. All rights reserved. | 40

Executing moreRowsrunAsync(this::handleFetchRows).thenCompose(this::moreRows)

Result of previous op

(r,t) ->{...}

executeQuery thenCompose

thenRunAsync

handleFetchRows

thenCompose

moreRows

handle

runAsync

moreRows

First

Second

Page 41: Using Java CompletionStage in Asynchronous Programming · •What: Java standard database access API that never blocks user threads •Who: Developed by the JDBC Community, JDBC Expert

Copyright © 2018, Oracle and/or its affiliates. All rights reserved. | 41

Executing moreRowsrunAsync(this::handleFetchRows).thenCompose(this::moreRows)

Result of previous op

(r,t) ->{...}

executeQuery

moreRows

thenCompose

thenRunAsync

handle

handleFetchRows

thenCompose

handleFetchRows

thenCompose

moreRows

runAsync runAsync

moreRows

Page 42: Using Java CompletionStage in Asynchronous Programming · •What: Java standard database access API that never blocks user threads •Who: Developed by the JDBC Community, JDBC Expert

Copyright © 2018, Oracle and/or its affiliates. All rights reserved. | 42

Executing moreRowsrunAsync(this::handleFetchRows)

Result of previous op

(r,t) ->{...}

executeQuery

moreRows

thenCompose

thenRunAsync

handle

handleFetchRows

thenCompose

moreRows

handleFetchRows

thenCompose

moreRows

runAsync runAsync

Third

Page 43: Using Java CompletionStage in Asynchronous Programming · •What: Java standard database access API that never blocks user threads •Who: Developed by the JDBC Community, JDBC Expert

Copyright © 2018, Oracle and/or its affiliates. All rights reserved. |

Result of previous op

43

Executing moreRows.thenCompose(this::moreRows)

(r,t) ->{...}

executeQuery thenCompose

thenRunAsync

handleFetchRows

thenCompose

runAsync

handleFetchRows

thenCompose

moreRows

handle

runAsync

moreRows

moreRows

Third

Page 44: Using Java CompletionStage in Asynchronous Programming · •What: Java standard database access API that never blocks user threads •Who: Developed by the JDBC Community, JDBC Expert

Copyright © 2018, Oracle and/or its affiliates. All rights reserved. |

protected CompletionStage<T> moreRows(Object x) {

checkCanceled();

if (rowsRemain) {

return CompletableFuture

.runAsync(this::handleFetchRows, getExecutor())

.thenCompose(this::moreRows, getExecutor());

}

else {

return CompletableFuture

.supplyAsync(this::completeQuery, getExecutor());

}

}

44

moreRows(Object x)com.oracle.adbaoverjdbc.RowOperation

Page 45: Using Java CompletionStage in Asynchronous Programming · •What: Java standard database access API that never blocks user threads •Who: Developed by the JDBC Community, JDBC Expert

Copyright © 2018, Oracle and/or its affiliates. All rights reserved. | 45

Executing moreRows when no more rows.supplyAsync(this::completeQuery)

completeQuery

supplyAsync

Result of previous op

(r,t) ->{...}

executeQuery thenCompose

thenRunAsync

handleFetchRows

thenCompose

runAsync

handleFetchRows

thenCompose

handle

runAsync

moreRows

moreRows moreRows

Third

Page 46: Using Java CompletionStage in Asynchronous Programming · •What: Java standard database access API that never blocks user threads •Who: Developed by the JDBC Community, JDBC Expert

Copyright © 2018, Oracle and/or its affiliates. All rights reserved. | 46

Executing completeQuery.supplyAsync(this::completeQuery)

completeQuery

supplyAsync

Result of previous op

(r,t) ->{...}

executeQuery thenCompose

thenRunAsync

handleFetchRows

thenCompose

runAsync

handleFetchRows

thenCompose

handle

runAsync

moreRows

moreRows moreRows

Third

Page 47: Using Java CompletionStage in Asynchronous Programming · •What: Java standard database access API that never blocks user threads •Who: Developed by the JDBC Community, JDBC Expert

Copyright © 2018, Oracle and/or its affiliates. All rights reserved. | 47

Query completeResult of completeQuery propagates back

completeQuery

Result of previous op

(r,t) ->{...}

executeQuery thenCompose

thenRunAsync

handleFetchRows

thenCompose

runAsync

handleFetchRows

thenCompose

handle

runAsync

moreRows

moreRows moreRows

supplyAsync

ThirdSecond

First

Page 48: Using Java CompletionStage in Asynchronous Programming · •What: Java standard database access API that never blocks user threads •Who: Developed by the JDBC Community, JDBC Expert

Copyright © 2018, Oracle and/or its affiliates. All rights reserved. | 48

Executing completionHandler.handle( (r, t) -> { ... } )

completeQuery

Result of previous op

(r,t) ->{...}

executeQuery thenCompose

thenRunAsync

handleFetchRows

thenCompose

runAsync

handleFetchRows

thenCompose

handle

runAsync

moreRows

moreRows moreRows

supplyAsync

Page 49: Using Java CompletionStage in Asynchronous Programming · •What: Java standard database access API that never blocks user threads •Who: Developed by the JDBC Community, JDBC Expert

Copyright © 2018, Oracle and/or its affiliates. All rights reserved. |

Summary

49

Page 50: Using Java CompletionStage in Asynchronous Programming · •What: Java standard database access API that never blocks user threads •Who: Developed by the JDBC Community, JDBC Expert

Copyright © 2018, Oracle and/or its affiliates. All rights reserved. |

CompletionStage<T> follows(CompletionStage<?> predecessor,Executor executor) {

predecessor = attachFutureParameters(predecessor);return predecessor

.thenRunAsync(this::executeQuery, executor)

.thenCompose(this::moreRows);}

50

follows(CompletionStage<?> predecessor,Executor executor)

com.oracle.adbaoverjdbc.RowOperation

Page 51: Using Java CompletionStage in Asynchronous Programming · •What: Java standard database access API that never blocks user threads •Who: Developed by the JDBC Community, JDBC Expert

Copyright © 2018, Oracle and/or its affiliates. All rights reserved. | 51

follows(CompletionStage<?> predecessor,Executor executor)

completeQuery

Result of previous op

(r,t) ->{...}

executeQuery thenCompose

thenRunAsync

handleFetchRows

thenCompose

runAsync

handleFetchRows

thenCompose

handle

runAsync

moreRows

moreRows moreRows

supplyAsync

Page 52: Using Java CompletionStage in Asynchronous Programming · •What: Java standard database access API that never blocks user threads •Who: Developed by the JDBC Community, JDBC Expert

Copyright © 2018, Oracle and/or its affiliates. All rights reserved. |

protected CompletionStage<T> moreRows(Object x) {

checkCanceled();

if (rowsRemain) {

return CompletableFuture

.runAsync(this::handleFetchRows, getExecutor())

.thenCompose(this::moreRows, getExecutor());

}

if {

return CompletableFuture

.supplyAsync(this::completeQuery, getExecutor());

}

}

52

moreRows(Object x)com.oracle.adbaoverjdbc.RowOperation

Page 53: Using Java CompletionStage in Asynchronous Programming · •What: Java standard database access API that never blocks user threads •Who: Developed by the JDBC Community, JDBC Expert

Copyright © 2018, Oracle and/or its affiliates. All rights reserved. | 53

moreRows(Object x)

completeQuery

Result of previous op

(r,t) ->{...}

executeQuery thenCompose

thenRunAsync

handleFetchRows

thenCompose

runAsync

handleFetchRows

thenCompose

handle

runAsync

moreRows

moreRows moreRows

supplyAsync

Page 54: Using Java CompletionStage in Asynchronous Programming · •What: Java standard database access API that never blocks user threads •Who: Developed by the JDBC Community, JDBC Expert

Copyright © 2018, Oracle and/or its affiliates. All rights reserved. |

final CompletionStage<T> attachCompletionHandler(CompletionStage<T> result) {

return result.handle((r, t) -> {Throwable ex = unwrapException(t);checkAbort(ex);if (t == null)

return handleResult(r);else

throw handleError(ex);});

}

54

attachCompletionHandlercom.oracle.adbaoverjdbc.OperationGroup

Page 55: Using Java CompletionStage in Asynchronous Programming · •What: Java standard database access API that never blocks user threads •Who: Developed by the JDBC Community, JDBC Expert

Copyright © 2018, Oracle and/or its affiliates. All rights reserved. | 55

Executing completionHandler.handle( (r, t) -> { ... } )

completeQuery

Result of previous op

(r,t) ->{...}

executeQuery thenCompose

thenRunAsync

handleFetchRows

thenCompose

runAsync

handleFetchRows

thenCompose

handle

runAsync

moreRows

moreRows moreRows

supplyAsync

Page 56: Using Java CompletionStage in Asynchronous Programming · •What: Java standard database access API that never blocks user threads •Who: Developed by the JDBC Community, JDBC Expert

Copyright © 2018, Oracle and/or its affiliates. All rights reserved. |

CompletionStage

<U> CompletionStage<U> handle (BiFunction<? super T, Throwable, ? extends U> fn)

<U> CompletionStage<U> thenApply(Function<? super T,? extends U> fn)

<U> CompletionStage<U> thenCompose (Function<? super T,? extends CompletionStage<U>> fn)

CompletionStage<Void> thenRunAsync (Runnable action, Executor executor)

CompletableFuture

public static CompletableFuture<Void> runAsync (Runnable runnable, Executor executor)

public static <U> CompletableFuture<U> supplyAsync (Supplier<U> supplier)

56

Methods used to implement the example code

Page 57: Using Java CompletionStage in Asynchronous Programming · •What: Java standard database access API that never blocks user threads •Who: Developed by the JDBC Community, JDBC Expert

Copyright © 2018, Oracle and/or its affiliates. All rights reserved. |

Q & A

57

Page 58: Using Java CompletionStage in Asynchronous Programming · •What: Java standard database access API that never blocks user threads •Who: Developed by the JDBC Community, JDBC Expert

Copyright © 2018, Oracle and/or its affiliates. All rights reserved. | 58