Contains factory methods for creating execution contexts.
WARNING: Only ever execute logic which will quickly return control to the caller.
WARNING: Only ever execute logic which will quickly return control to the caller.
ThisExecutionContext steals execution time from other threads by having itsRunnables run on theThread which callsexecute and then yielding back control to the caller after *all* itsRunnables have been executed. Nested invocations ofexecute will be trampolined to prevent uncontrolled stack space growth.
When usingparasitic with abstractions such asFuture it will in many cases be non-deterministic as to whichThread will be executing the logic, as it depends on when/if thatFuture is completed.
Do *not* call any blocking code in theRunnables submitted to thisExecutionContext as it will prevent progress by other enqueuedRunnables and the callingThread.
Symptoms of misuse of thisExecutionContext include, but are not limited to, deadlocks and severe performance problems.
AnyNonFatal orInterruptedExceptions will be reported to thedefaultReporter.
Creates anExecutionContext from the givenExecutor.
Creates anExecutionContext from the givenExecutor.
theExecutor to use. Ifnull, a newExecutor is created withdefault configuration.
a function for error reporting
theExecutionContext using the givenExecutor
Creates anExecutionContext from the givenExecutor with thedefault reporter.
Creates anExecutionContext from the givenExecutor with thedefault reporter.
theExecutor to use. Ifnull, a newExecutor is created withdefault configuration.
theExecutionContext using the givenExecutor
Creates anExecutionContext from the givenExecutorService.
Creates anExecutionContext from the givenExecutorService.
theExecutorService to use. Ifnull, a newExecutorService is created withdefault configuration.
a function for error reporting
theExecutionContext using the givenExecutorService
Creates anExecutionContext from the givenExecutorService with thedefault reporter.
Creates anExecutionContext from the givenExecutorService with thedefault reporter.
If it is guaranteed that none of the executed tasks are blocking, a single-threadedExecutorService can be used to create anExecutionContext as follows:
import java.util.concurrent.Executorsval ec = ExecutionContext.fromExecutorService(Executors.newSingleThreadExecutor())theExecutorService to use. Ifnull, a newExecutorService is created withdefault configuration.
theExecutionContext using the givenExecutorService
The default reporter simply prints the stack trace of theThrowable toSystem.err.
The default reporter simply prints the stack trace of theThrowable toSystem.err.
the function for error reporting
The globalExecutionContext.
The globalExecutionContext. This defaultExecutionContext implementation is backed by a work-stealing thread pool. It can be configured via the following system properties:
scala.concurrent.context.minThreads = defaults to "1"
scala.concurrent.context.numThreads = defaults to "x1" (i.e. the current number of available processors * 1)
scala.concurrent.context.maxThreads = defaults to "x1" (i.e. the current number of available processors * 1)
scala.concurrent.context.maxExtraThreads = defaults to "256"
The pool size of threads is thennumThreads bounded byminThreads on the lower end andmaxThreads on the high end.
ThemaxExtraThreads is the maximum number of extra threads to have at any given time to evade deadlock, seescala.concurrent.blocking.
Theglobal execution context can be used explicitly, by defining animplicit val ec: scala.concurrent.ExecutionContext = scala.concurrent.ExecutionContext.global, or by importingExecutionContext.Implicits.global.
Asynchronous code with short-lived nested tasks is executed more efficiently when usingExecutionContext.opportunistic (continue reading to learn why it isprivate[scala] and how to access it).
ExecutionContext.opportunistic uses the same thread pool asExecutionContext.global. It attempts to batch nested task and execute them on the same thread as the enclosing task. This is ideally suited to execute short-lived tasks as it reduces the overhead of context switching.
WARNING: long-running and/or blocking tasks should be demarcated withinscala.concurrent.blocking-blocks to ensure that any pending tasks in the current batch can be executed by another thread onglobal.
This field isprivate[scala] to maintain binary compatibility. It was added in 2.13.4, code that references it directly fails to run with a 2.13.0-3 Scala library.
Libraries should not reference this field directly because users of the library might be using an earlier Scala version. In order to use the batchingExecutionContext in a library, the code needs to fall back toglobal in case theopportunistic field is missing (example below). The resultingExecutionContext has batching behavior in all Scala 2.13 versions (global is batching in 2.13.0-3).
implicit val ec: scala.concurrent.ExecutionContext = try { scala.concurrent.ExecutionContext.getClass .getDeclaredMethod("opportunistic") .invoke(scala.concurrent.ExecutionContext) .asInstanceOf[scala.concurrent.ExecutionContext]} catch { case _: NoSuchMethodException => scala.concurrent.ExecutionContext.global}Application authors can safely use the field because the Scala version at run time is the same as at compile time. Options to bypass the access restriction include:
Using a structural type (example below). This uses reflection at run time.
Writing a Scalaobject in thescala package (example below).
Writing a Java source file. This works becauseprivate[scala] is emitted aspublic in Java bytecode.
// Option 1implicit val ec: scala.concurrent.ExecutionContext = (scala.concurrent.ExecutionContext: {def opportunistic: scala.concurrent.ExecutionContextExecutor} ).opportunistic// Option 2package scala { object OpportunisticEC { implicit val ec: scala.concurrent.ExecutionContext = scala.concurrent.ExecutionContext.opportunistic }}the globalExecutionContext