1. So how do I do a 2PC in Akka then?
or
Lutz Hühnken (@lutzhuehnken)
A Pragmatic View of Reactive
2. So how do I do a 2PC in Akka then?
Lutz Hühnken (@lutzhuehnken)
A misleading title, really.
Answer: You don’t want to
(we’ll get back to that later)
3. Valuable Experience vs. Bad Habit
From Enterprise to Reactive
Transitions
…
Lutz Hühnken (@lutzhuehnken)
Other failed naming attempts..
14. Pragmatic Reactive
The problem with Threads
14
They discard the most essential and
appealing properties of sequential
computation: understandability,
predictability, and determinism.
Threads, as a model of computation,
are wildly nondeterministic, and the
job of the programmer becomes one
of pruning that nondeterminism.
16. Pragmatic Reactive
Threads
• not efficient
• memory consumption
• cost for context switch
• bad match modern NUMA architectures
• locks lead to contention
• not a good programming model
• shared mutual state is difficult to reason about
16
17. Pragmatic Reactive
What would be better?
Goals
• task level (sub-thread) concurrency
• share nothing approach
• # threads ~ # of cores
17
18. Pragmatic Reactive
Thread alternatives (successors?)
• Green threads / coroutines / fibres
• other granularity, but basically same programming
model
• Event-loop (e.g. vert.x, Reactor)
• very loose coupling, slightly limited, 1 x n dispatch
• Actors !
• truly share-nothing, flexible, resilience-proven,
m x n dispatch
18
19. Pragmatic Reactive
Example: Http Request handling
Java EE: Threads. Servlet API: Thread per Request
19
Note: This is a snapshot at one point in time, not a sequence of events.
20. Pragmatic Reactive
Example: Http Request handling
Reactive: Sub-Thread. Play: n threads per m requests
20
Note: This is a snapshot at one point in time, not a sequence of events.
21. Pragmatic Reactive
Consequences
• We have effectively (even without explicitly
using Actors) switched to a task level
concurrency model
• As a consequence, ThreadLocal becomes
an anti-pattern.
• Libraries that depend on them need extra
work, might better be avoided
• What does it mean for (blocking) I/O?
21
24. Pragmatic Reactive
High concurrency matters
24
But there’s one thing we can all agree on: At high levels of
concurrency (thousands of connections) your server needs to
go to asynchronous non-blocking. [..] any part of your server
code blocks you’re going to need a thread. And at these levels
of concurrency, you can’t go creating threads for every
connection.
From https://strongloop.com/strongblog/node-js-is-faster-than-java/
26. Pragmatic Reactive
Non-blocking
26
For task level (sub-thread level) concurrency
• each thread is responsible for n tasks
• and that n might be pretty big
You don’t want to block such a thread with blocking I/O
27. Pragmatic Reactive
But what if I need this..?
27
try {
stmt = con.createStatement();
ResultSet rs = stmt.executeQuery(query);
while (rs.next()) {
String coffeeName = rs.getString("COF_NAME");
int supplierID = rs.getInt("SUP_ID");
float price = rs.getFloat("PRICE");
int sales = rs.getInt("SALES");
int total = rs.getInt("TOTAL");
System.out.println(coffeeName + "t" + supplierID +
"t" + price + "t" + sales +
29. Pragmatic Reactive
Pragmatic reactive learnings cont’d
• You’ll be using sub-thread level
concurrency. Accept it, embrace it.
• Use asynchronous I/O. If you really can’t,
isolate.
29
31. Pragmatic Reactive
But what if I need this..?
31
@Transactional
public static class GreetingService {
@Inject
private JmsTemplate jmsTemplate;
@PersistenceContext
private EntityManager entityManager;
public void createGreeting(String name) {
Greeting greeting = new Greeting(name);
this.entityManager.persist(greeting);
this.jmsTemplate.convertAndSend("greetings", greeting);
…
35. Pragmatic Reactive
Life beyond Distributed Transactions
35
In general, application
developers simply do not
implement large scalable
applications assuming
distributed transactions. When
they attempt to use distributed
transactions, the projects
founder because the
performance costs and fragility
make them impractical. [..]
36. 36
Want Almost-Infinite Scaling
• More of everything… Year by year, bigger and bigger
• If it fits on your machines, multiply by 10, if that fits, multiply by 1000…
• Strive to scale almost linearly (N log N for some big log).
Assumptions
(Don’t Have to Prove These… Just Plain Believe Them)
Grown-Ups Don’t Use Distributed Transactions
•The apps using distributed transactions become too fragile…
• Let’s just consider local transactions.
! Multiple disjoint scopes of serializability
Want Scale-Agnostic Apps
• Two layers to the application:
scale-agnostic and scale-aware
• Consider scale-agnostic API
Scale Agnostic Code
Scale-Aware-Code
Application
Upper Layer
Lower Layer
Scale Agnostic API
40. Pragmatic Reactive
Distributed Transactions
40
Distributed Transactions („2PC“) are a source of
unnecessary failure and of contention.
It can usually be avoided. Generally, local transactions
and at-least-once delivery can be used instead.
The Saga Pattern provides a pragmatic solution for „all-or-
nothing“ in a distributed system.
41. Pragmatic Reactive
Food for thought
41
The data storage landscape is changing, moving towards
event sourcing and immutability. This is a great match for
reactive systems.
The „all-or-nothing“ problems are closely related to
wanting a global truth at a point in time. But what is
now… the illusion of present… result of series of events..
42. Pragmatic Reactive
Pragmatic reactive learnings cont’d
• You’ll be using sub-thread level
concurrency. Accept it, embrace it.
• Use asynchronous I/O. If you really can’t,
isolate.
• Do not use distributed transactions. If you
really must, isolate.
42
46. Pragmatic Reactive
Java EE Application Servers
46
Servlet API was developed for thread-per-
request, synchronous I/O.
Application servers are not of much use
anyway, nobody uses them as containers for
multiple applications. So effectively they’re
just a library dependency.
The ops convenience can be provided by
other tools.
47. Pragmatic Reactive
Pragmatic reactive learnings cont’d
• You’ll be using sub-thread level
concurrency. Accept it, embrace it.
• Use asynchronous I/O. If you really can’t,
isolate.
• Do not use distributed transactions. If you
really must, isolate.
• Don’t use an application server / servlet
container.
47
49. Pragmatic Reactive
Conclusion
49
If
• Threads are the smallest unit of concurrency in
your code, or
• You use blocking I/O (without clear separation), or
• You use 2-phase-commit across systems, or
• You use a Java EE Application Server / Servlet
Container
Then your application is not reactive.