diff --git a/akka-docs/src/main/paradox/actors.md b/akka-docs/src/main/paradox/actors.md index 4c161d04ba..cb5a219efc 100644 --- a/akka-docs/src/main/paradox/actors.md +++ b/akka-docs/src/main/paradox/actors.md @@ -947,7 +947,7 @@ stuck. Upon `ActorSystem.terminate()`, the system guardian actors will be stopped, and the aforementioned process will ensure proper termination of the -whole system. +whole system. See @ref:[Coordinated Shutdown](coordinated-shutdown.md). The `postStop()` hook is invoked after an actor is fully stopped. This enables cleaning up of resources: @@ -1035,112 +1035,6 @@ message, i.e. not for top-level actors. @@@ -### Coordinated Shutdown - -There is an extension named `CoordinatedShutdown` that will stop certain actors and -services in a specific order and perform registered tasks during the shutdown process. - -The order of the shutdown phases is defined in configuration `akka.coordinated-shutdown.phases`. -The default phases are defined as: - -@@snip [reference.conf](/akka-actor/src/main/resources/reference.conf) { #coordinated-shutdown-phases } - -More phases can be added in the application's configuration if needed by overriding a phase with an -additional `depends-on`. Especially the phases `before-service-unbind`, `before-cluster-shutdown` and -`before-actor-system-terminate` are intended for application specific phases or tasks. - -The default phases are defined in a single linear order, but the phases can be ordered as a -directed acyclic graph (DAG) by defining the dependencies between the phases. -The phases are ordered with [topological](https://en.wikipedia.org/wiki/Topological_sorting) sort of the DAG. - -Tasks can be added to a phase with: - -Scala -: @@snip [ActorDocSpec.scala](/akka-docs/src/test/scala/docs/actor/ActorDocSpec.scala) { #coordinated-shutdown-addTask } - -Java -: @@snip [ActorDocTest.java](/akka-docs/src/test/java/jdocs/actor/ActorDocTest.java) { #coordinated-shutdown-addTask } - -The returned @scala[`Future[Done]`] @java[`CompletionStage`] should be completed when the task is completed. The task name parameter -is only used for debugging/logging. - -Tasks added to the same phase are executed in parallel without any ordering assumptions. -Next phase will not start until all tasks of previous phase have been completed. - -If tasks are not completed within a configured timeout (see @ref:[reference.conf](general/configuration-reference.md#config-akka-actor)) -the next phase will be started anyway. It is possible to configure `recover=off` for a phase -to abort the rest of the shutdown process if a task fails or is not completed within the timeout. - -In the above example, it may be more convenient to simply stop the actor when it's done shutting down, rather than send back a done message, -and for the shutdown task to not complete until the actor is terminated. A convenience method is provided that adds a task that sends -a message to the actor and then watches its termination: - -Scala -: @@snip [ActorDocSpec.scala](/akka-docs/src/test/scala/docs/actor/ActorDocSpec.scala) { #coordinated-shutdown-addActorTerminationTask } - -Java -: @@snip [ActorDocTest.java](/akka-docs/src/test/java/jdocs/actor/ActorDocTest.java) { #coordinated-shutdown-addActorTerminationTask } - -Tasks should typically be registered as early as possible after system startup. When running -the coordinated shutdown tasks that have been registered will be performed but tasks that are -added too late will not be run. - -To start the coordinated shutdown process you can invoke @scala[`run`] @java[`runAll`] on the `CoordinatedShutdown` -extension: - -Scala -: @@snip [ActorDocSpec.scala](/akka-docs/src/test/scala/docs/actor/ActorDocSpec.scala) { #coordinated-shutdown-run } - -Java -: @@snip [ActorDocTest.java](/akka-docs/src/test/java/jdocs/actor/ActorDocTest.java) { #coordinated-shutdown-run } - -It's safe to call the @scala[`run`] @java[`runAll`] method multiple times. It will only run once. - -That also means that the `ActorSystem` will be terminated in the last phase. By default, the -JVM is not forcefully stopped (it will be stopped if all non-daemon threads have been terminated). -To enable a hard `System.exit` as a final action you can configure: - -``` -akka.coordinated-shutdown.exit-jvm = on -``` - -The coordinated shutdown process can also be started by calling `ActorSystem.terminate()`. - -When using @ref:[Akka Cluster](cluster-usage.md) the `CoordinatedShutdown` will automatically run -when the cluster node sees itself as `Exiting`, i.e. leaving from another node will trigger -the shutdown process on the leaving node. Tasks for graceful leaving of cluster including graceful -shutdown of Cluster Singletons and Cluster Sharding are added automatically when Akka Cluster is used, -i.e. running the shutdown process will also trigger the graceful leaving if it's not already in progress. - -By default, the `CoordinatedShutdown` will be run when the JVM process exits, e.g. -via `kill SIGTERM` signal (`SIGINT` ctrl-c doesn't work). This behavior can be disabled with: - -``` -akka.coordinated-shutdown.run-by-jvm-shutdown-hook=off -``` - -If you have application specific JVM shutdown hooks it's recommended that you register them via the -`CoordinatedShutdown` so that they are running before Akka internal shutdown hooks, e.g. -those shutting down Akka Remoting (Artery). - -Scala -: @@snip [ActorDocSpec.scala](/akka-docs/src/test/scala/docs/actor/ActorDocSpec.scala) { #coordinated-shutdown-jvm-hook } - -Java -: @@snip [ActorDocTest.java](/akka-docs/src/test/java/jdocs/actor/ActorDocTest.java) { #coordinated-shutdown-jvm-hook } - -For some tests it might be undesired to terminate the `ActorSystem` via `CoordinatedShutdown`. -You can disable that by adding the following to the configuration of the `ActorSystem` that is -used in the test: - -``` -# Don't terminate ActorSystem via CoordinatedShutdown in tests -akka.coordinated-shutdown.terminate-actor-system = off -akka.coordinated-shutdown.run-by-actor-system-terminate = off -akka.coordinated-shutdown.run-by-jvm-shutdown-hook = off -akka.cluster.run-coordinated-shutdown-when-down = off -``` - ## Become/Unbecome diff --git a/akka-docs/src/main/paradox/additional/rolling-updates.md b/akka-docs/src/main/paradox/additional/rolling-updates.md index 4ab997a0e7..8a40776c10 100644 --- a/akka-docs/src/main/paradox/additional/rolling-updates.md +++ b/akka-docs/src/main/paradox/additional/rolling-updates.md @@ -58,7 +58,7 @@ overhead several times. ### Graceful shutdown -For rolling updates it is best to leave the Cluster gracefully via @ref:[Coordinated Shutdown](../actors.md#coordinated-shutdown), +For rolling updates it is best to leave the Cluster gracefully via @ref:[Coordinated Shutdown](../coordinated-shutdown.md), which will run automatically on SIGTERM, when the Cluster node sees itself as `Exiting`. Environments such as Kubernetes send a SIGTERM, however if the JVM is wrapped with a script ensure that it forwards the signal. @ref:[Graceful shutdown](../cluster-sharding.md#graceful-shutdown) of Cluster Singletons and Cluster Sharding similarly happen automatically. diff --git a/akka-docs/src/main/paradox/cluster-sharding.md b/akka-docs/src/main/paradox/cluster-sharding.md index c92ea464c7..4094689291 100644 --- a/akka-docs/src/main/paradox/cluster-sharding.md +++ b/akka-docs/src/main/paradox/cluster-sharding.md @@ -221,7 +221,7 @@ to the `ShardRegion` actor to hand off all shards that are hosted by that `Shard During this period other regions will buffer messages for those shards in the same way as when a rebalance is triggered by the coordinator. When the shards have been stopped the coordinator will allocate these shards elsewhere. -This is performed automatically by the @ref:[Coordinated Shutdown](actors.md#coordinated-shutdown) and is therefore part of the +This is performed automatically by the @ref:[Coordinated Shutdown](coordinated-shutdown.md) and is therefore part of the graceful leaving process of a cluster member. diff --git a/akka-docs/src/main/paradox/cluster-usage.md b/akka-docs/src/main/paradox/cluster-usage.md index 8609bd4d46..e68c38d8aa 100644 --- a/akka-docs/src/main/paradox/cluster-usage.md +++ b/akka-docs/src/main/paradox/cluster-usage.md @@ -261,7 +261,7 @@ Java You can do some clean up in a `registerOnMemberRemoved` callback, which will be invoked when the current member status is changed to 'Removed' or the cluster have been shutdown. -An alternative is to register tasks to the @ref:[Coordinated Shutdown](actors.md#coordinated-shutdown). +An alternative is to register tasks to the @ref:[Coordinated Shutdown](coordinated-shutdown.md). @@@ note diff --git a/akka-docs/src/main/paradox/coordinated-shutdown.md b/akka-docs/src/main/paradox/coordinated-shutdown.md new file mode 100644 index 0000000000..93e489d797 --- /dev/null +++ b/akka-docs/src/main/paradox/coordinated-shutdown.md @@ -0,0 +1,106 @@ +# Coordinated Shutdown + +Under normal conditions when `ActorSystem` is terminated or the JVM process is shut down certain +actors and services will be stopped in a specific order. + +This is handled by an extension named `CoordinatedShutdown`. It will run the registered tasks +during the shutdown process. The order of the shutdown phases is defined in configuration `akka.coordinated-shutdown.phases`. +The default phases are defined as: + +@@snip [reference.conf](/akka-actor/src/main/resources/reference.conf) { #coordinated-shutdown-phases } + +More phases can be added in the application's configuration if needed by overriding a phase with an +additional `depends-on`. Especially the phases `before-service-unbind`, `before-cluster-shutdown` and +`before-actor-system-terminate` are intended for application specific phases or tasks. + +The default phases are defined in a single linear order, but the phases can be ordered as a +directed acyclic graph (DAG) by defining the dependencies between the phases. +The phases are ordered with [topological](https://en.wikipedia.org/wiki/Topological_sorting) sort of the DAG. + +Tasks can be added to a phase with: + +Scala +: @@snip [ActorDocSpec.scala](/akka-docs/src/test/scala/docs/actor/ActorDocSpec.scala) { #coordinated-shutdown-addTask } + +Java +: @@snip [ActorDocTest.java](/akka-docs/src/test/java/jdocs/actor/ActorDocTest.java) { #coordinated-shutdown-addTask } + +The returned @scala[`Future[Done]`] @java[`CompletionStage`] should be completed when the task is completed. The task name parameter +is only used for debugging/logging. + +Tasks added to the same phase are executed in parallel without any ordering assumptions. +Next phase will not start until all tasks of previous phase have been completed. + +If tasks are not completed within a configured timeout (see @ref:[reference.conf](general/configuration-reference.md#config-akka-actor)) +the next phase will be started anyway. It is possible to configure `recover=off` for a phase +to abort the rest of the shutdown process if a task fails or is not completed within the timeout. + +In the above example, it may be more convenient to simply stop the actor when it's done shutting down, rather than send back a done message, +and for the shutdown task to not complete until the actor is terminated. A convenience method is provided that adds a task that sends +a message to the actor and then watches its termination: + +Scala +: @@snip [ActorDocSpec.scala](/akka-docs/src/test/scala/docs/actor/ActorDocSpec.scala) { #coordinated-shutdown-addActorTerminationTask } + +Java +: @@snip [ActorDocTest.java](/akka-docs/src/test/java/jdocs/actor/ActorDocTest.java) { #coordinated-shutdown-addActorTerminationTask } + +Tasks should typically be registered as early as possible after system startup. When running +the coordinated shutdown tasks that have been registered will be performed but tasks that are +added too late will not be run. + +To start the coordinated shutdown process you can invoke @scala[`run`] @java[`runAll`] on the `CoordinatedShutdown` +extension: + +Scala +: @@snip [ActorDocSpec.scala](/akka-docs/src/test/scala/docs/actor/ActorDocSpec.scala) { #coordinated-shutdown-run } + +Java +: @@snip [ActorDocTest.java](/akka-docs/src/test/java/jdocs/actor/ActorDocTest.java) { #coordinated-shutdown-run } + +It's safe to call the @scala[`run`] @java[`runAll`] method multiple times. It will only run once. + +That also means that the `ActorSystem` will be terminated in the last phase. By default, the +JVM is not forcefully stopped (it will be stopped if all non-daemon threads have been terminated). +To enable a hard `System.exit` as a final action you can configure: + +``` +akka.coordinated-shutdown.exit-jvm = on +``` + +The coordinated shutdown process can also be started by calling `ActorSystem.terminate()`. + +When using @ref:[Akka Cluster](cluster-usage.md) the `CoordinatedShutdown` will automatically run +when the cluster node sees itself as `Exiting`, i.e. leaving from another node will trigger +the shutdown process on the leaving node. Tasks for graceful leaving of cluster including graceful +shutdown of Cluster Singletons and Cluster Sharding are added automatically when Akka Cluster is used, +i.e. running the shutdown process will also trigger the graceful leaving if it's not already in progress. + +By default, the `CoordinatedShutdown` will be run when the JVM process exits, e.g. +via `kill SIGTERM` signal (`SIGINT` ctrl-c doesn't work). This behavior can be disabled with: + +``` +akka.coordinated-shutdown.run-by-jvm-shutdown-hook=off +``` + +If you have application specific JVM shutdown hooks it's recommended that you register them via the +`CoordinatedShutdown` so that they are running before Akka internal shutdown hooks, e.g. +those shutting down Akka Remoting (Artery). + +Scala +: @@snip [ActorDocSpec.scala](/akka-docs/src/test/scala/docs/actor/ActorDocSpec.scala) { #coordinated-shutdown-jvm-hook } + +Java +: @@snip [ActorDocTest.java](/akka-docs/src/test/java/jdocs/actor/ActorDocTest.java) { #coordinated-shutdown-jvm-hook } + +For some tests it might be undesired to terminate the `ActorSystem` via `CoordinatedShutdown`. +You can disable that by adding the following to the configuration of the `ActorSystem` that is +used in the test: + +``` +# Don't terminate ActorSystem via CoordinatedShutdown in tests +akka.coordinated-shutdown.terminate-actor-system = off +akka.coordinated-shutdown.run-by-actor-system-terminate = off +akka.coordinated-shutdown.run-by-jvm-shutdown-hook = off +akka.cluster.run-coordinated-shutdown-when-down = off +``` diff --git a/akka-docs/src/main/paradox/general/actor-systems.md b/akka-docs/src/main/paradox/general/actor-systems.md index d033633f51..1f46651025 100644 --- a/akka-docs/src/main/paradox/general/actor-systems.md +++ b/akka-docs/src/main/paradox/general/actor-systems.md @@ -107,8 +107,8 @@ while Akka does the heavy lifting under the hood. ## Terminating ActorSystem When you know everything is done for your application, you can have the user guardian - actor stop, or call the `terminate` method of `ActorSystem`. That will run @ref:[`CoordinatedShutdown`](../actors.md#coordinated-shutdown) + actor stop, or call the `terminate` method of `ActorSystem`. That will run @ref:[`CoordinatedShutdown`](../coordinated-shutdown.md) stopping all running actors. If you want to execute some operations while terminating `ActorSystem`, -look at @ref:[`CoordinatedShutdown`](../actors.md#coordinated-shutdown). +look at @ref:[`CoordinatedShutdown`](../coordinated-shutdown.md). diff --git a/akka-docs/src/main/paradox/project/migration-guide-2.5.x-2.6.x.md b/akka-docs/src/main/paradox/project/migration-guide-2.5.x-2.6.x.md index 4ac2d78bfe..413743f834 100644 --- a/akka-docs/src/main/paradox/project/migration-guide-2.5.x-2.6.x.md +++ b/akka-docs/src/main/paradox/project/migration-guide-2.5.x-2.6.x.md @@ -411,7 +411,7 @@ Akka Typed. No migration is needed but it is mentioned here because it is a change in behavior. -When `ActorSystem.terminate()` is called, @ref:[`CoordinatedShutdown`](../actors.md#coordinated-shutdown) +When `ActorSystem.terminate()` is called, @ref:[`CoordinatedShutdown`](../coordinated-shutdown.md) will be run in Akka 2.6.x, which wasn't the case in 2.5.x. For example, if using Akka Cluster this means that member will attempt to leave the cluster gracefully. diff --git a/akka-docs/src/main/paradox/stream/operators/Source/unfoldResource.md b/akka-docs/src/main/paradox/stream/operators/Source/unfoldResource.md index fc2ebd7a6a..b09e7d2561 100644 --- a/akka-docs/src/main/paradox/stream/operators/Source/unfoldResource.md +++ b/akka-docs/src/main/paradox/stream/operators/Source/unfoldResource.md @@ -40,9 +40,6 @@ Scala Java : @@snip [UnfoldResource.java](/akka-docs/src/test/java/jdocs/stream/operators/source/UnfoldResource.java) { #unfoldResource-blocking-api } -## Reactive Streams semantics - - Let's see how we use the API above safely through `unfoldResource`: Scala diff --git a/akka-docs/src/main/paradox/typed/actor-lifecycle.md b/akka-docs/src/main/paradox/typed/actor-lifecycle.md index d077aa5f90..1c9b1b8273 100644 --- a/akka-docs/src/main/paradox/typed/actor-lifecycle.md +++ b/akka-docs/src/main/paradox/typed/actor-lifecycle.md @@ -72,7 +72,10 @@ For very simple applications the guardian may contain the actual application log handles more than one concern the the guardian should instead just bootstrap the application, spawn the various subsystems as children and monitor their lifecycles. -When the guardian actor stops this will stop the `ActorSystem`. +When the guardian actor stops this will stop the `ActorSystem`. + +When `ActorSystem.terminate` is invoked the @ref:[Coordinated Shutdown](../coordinated-shutdown.md) process will +stop actors and services in a specific order. @@@ Note diff --git a/akka-docs/src/main/paradox/typed/cluster.md b/akka-docs/src/main/paradox/typed/cluster.md index 05209112ac..7af0bc99b0 100644 --- a/akka-docs/src/main/paradox/typed/cluster.md +++ b/akka-docs/src/main/paradox/typed/cluster.md @@ -232,7 +232,7 @@ configured `seed-node-timeout`. The joining of given seed nodes will by default be retried indefinitely until a successful join. That process can be aborted if unsuccessful by configuring a -timeout. When aborted it will run @ref:[Coordinated Shutdown](../actors.md#coordinated-shutdown), +timeout. When aborted it will run @ref:[Coordinated Shutdown](../coordinated-shutdown.md), which by default will terminate the ActorSystem. CoordinatedShutdown can also be configured to exit the JVM. It is useful to define this timeout if the `seed-nodes` are assembled dynamically and a restart with new seed-nodes should be tried after unsuccessful @@ -262,7 +262,7 @@ be allowed to join. There are a few ways to remove a member from the cluster. 1. The recommended way to leave a cluster is a graceful exit, informing the cluster that a node shall leave. - This is performed by @ref:[Coordinated Shutdown](../actors.md#coordinated-shutdown) when the `ActorSystem` + This is performed by @ref:[Coordinated Shutdown](../coordinated-shutdown.md) when the `ActorSystem` is terminated and also when a SIGTERM is sent from the environment to stop the JVM process. 1. Graceful exit can also be performed using @ref:[HTTP](../additional/operations.md#http) or @ref:[JMX](../additional/operations.md#jmx). 1. When a graceful exit is not possible, for example in case of abrupt termination of the the JVM process, the node @@ -270,7 +270,7 @@ There are a few ways to remove a member from the cluster. Graceful leaving will offer faster hand off to peer nodes during node shutdown than abrupt termination and downing. -The @ref:[Coordinated Shutdown](../actors.md#coordinated-shutdown) will also run when the cluster node sees itself as +The @ref:[Coordinated Shutdown](../coordinated-shutdown.md) will also run when the cluster node sees itself as `Exiting`, i.e. leaving from another node will trigger the shutdown process on the leaving node. Tasks for graceful leaving of cluster including graceful shutdown of Cluster Singletons and Cluster Sharding are added automatically when Akka Cluster is used, i.e. running the shutdown @@ -317,7 +317,7 @@ If a crashed node is restarted with the same hostname and port and joining the c of that member will be downed and removed. The new join attempt with same hostname and port is used as evidence that the previous is not alive any more. -If a node is still running and sees its self as `Down` it will shutdown. @ref:[Coordinated Shutdown](../actors.md#coordinated-shutdown) will automatically +If a node is still running and sees its self as `Down` it will shutdown. @ref:[Coordinated Shutdown](../coordinated-shutdown.md) will automatically run if `run-coordinated-shutdown-when-down` is set to `on` (the default) however the node will not try and leave the cluster gracefully. diff --git a/akka-docs/src/main/paradox/typed/index.md b/akka-docs/src/main/paradox/typed/index.md index b99a7fb59a..6e30a112c2 100644 --- a/akka-docs/src/main/paradox/typed/index.md +++ b/akka-docs/src/main/paradox/typed/index.md @@ -9,6 +9,7 @@ project.description: Using Akka to build reliable multi-core applications distri * [actors](actors.md) * [actor-lifecycle](actor-lifecycle.md) +* [coordinated-shutdown](../coordinated-shutdown.md) * [interaction patterns](interaction-patterns.md) * [fault-tolerance](fault-tolerance.md) * [actor-discovery](actor-discovery.md)