From ab262f4b3fd2054d6a166efe57e2e878a4bfe62a Mon Sep 17 00:00:00 2001 From: Patrik Nordwall Date: Wed, 3 Apr 2013 07:50:12 +0200 Subject: [PATCH] Link to old migration guides instead of embedding, see #2774 * Otherwise the embedded old migration guide might have wrong version variable replacements (scala, config lib) when changed versions are changed in master --- .../project/migration-guide-1.3.x-2.0.x.rst | 2 +- .../project/migration-guide-2.0.x-2.1.x.rst | 497 +----------------- .../project/migration-guide-2.1.x-2.2.x.rst | 2 +- 3 files changed, 4 insertions(+), 497 deletions(-) diff --git a/akka-docs/rst/project/migration-guide-1.3.x-2.0.x.rst b/akka-docs/rst/project/migration-guide-1.3.x-2.0.x.rst index 104a353f22..0ffa5e245e 100644 --- a/akka-docs/rst/project/migration-guide-1.3.x-2.0.x.rst +++ b/akka-docs/rst/project/migration-guide-1.3.x-2.0.x.rst @@ -5,6 +5,6 @@ ################################ Migration from 1.3.x to 2.0.x is described in the -`documentation of 2.0 `_. +`documentation of 2.0 `_. diff --git a/akka-docs/rst/project/migration-guide-2.0.x-2.1.x.rst b/akka-docs/rst/project/migration-guide-2.0.x-2.1.x.rst index 1b6840a696..d354811bbb 100644 --- a/akka-docs/rst/project/migration-guide-2.0.x-2.1.x.rst +++ b/akka-docs/rst/project/migration-guide-2.0.x-2.1.x.rst @@ -4,498 +4,5 @@ Migration Guide 2.0.x to 2.1.x ################################ -Some parts of the 2.0 API have changed in the Akka 2.1 release. This guide lists the the changes and -explains what you will need to do to upgrade your program to work with Akka 2.1. - -Migrating from Akka 2.0.x to Akka 2.1.x is relatively straightforward. In Akka 2.1 the API has -undergone some basic housekeeping, for example some package names have changed, but otherwise usage -is largely unchanged. User programs will generally only need simple, mechanical changes in order to -work with Akka 2.1. - -If you are migrating from Akka 1.3.x you will need to follow the instructions for -`migrating from Akka 1.3.x to 2.0.x `_ -before following the instructions in this guide. - -Scala Version -============= - -Akka 2.1 uses a new version of Scala. -Change your project build and dependencies to Scala version ``@scalaVersion@``. - -Config Dependency -================= - -Akka's configuration system has graduated from Akka to become the `Typesafe config -`_ project. The configuration system was previously embedded -within ``akka-actor.jar``, now it is specified as a dependency of ``akka-actor.jar``. - -If your are using a build tool with automatic dependency resolution, such as sbt or Maven, then you -will not notice a difference. Otherwise you will need to ensure that -`config-1.0.0.jar `_ -is present on your classpath. - -Pieces Moved to Scala Standard Library -====================================== - -Change the following import statements. - -==================================== ==================================== -Search Replace with -==================================== ==================================== -``akka.dispatch.Await`` ``scala.concurrent.Await`` -``akka.dispatch.Future`` ``scala.concurrent.Future`` -``akka.dispatch.Promise`` ``scala.concurrent.Promise`` -``akka.dispatch.ExecutionContext`` ``scala.concurrent.ExecutionContext`` -``akka.util.Duration`` ``scala.concurrent.duration.Duration`` -``akka.util.duration`` ``scala.concurrent.duration`` -``akka.util.Deadline`` ``scala.concurrent.duration.Deadline`` -``akka.util.NonFatal`` ``scala.util.control.NonFatal`` -``akka.japi.Util.manifest`` ``akka.japi.Util.classTag`` -==================================== ==================================== - -Scheduler Dispatcher -==================== - -The ``ExecutionContext`` to use for running scheduled tasks must now be specified. -You can use an Akka ``Dispatcher`` for this purpose. - -Scala: - -:: - - import context.dispatcher // Use this Actors' Dispatcher as ExecutionContext - context.system.scheduler.scheduleOnce(10 seconds, self, Reconnect) - - import system.dispatcher // Use ActorSystem's default Dispatcher as ExecutionContext - system.scheduler.scheduleOnce(50 milliseconds) { - testActor ! System.currentTimeMillis - } - -Java: -:: - - // Use this Actors' Dispatcher as ExecutionContext - getContext().system().scheduler().scheduleOnce(Duration.create( - 10, TimeUnit.SECONDS), getSelf(), new Reconnect(), - getContext().getDispatcher()); - - // Use ActorSystem's default Dispatcher as ExecutionContext - system.scheduler().scheduleOnce(Duration.create(50, TimeUnit.MILLISECONDS), - new Runnable() { - @Override - public void run() { - testActor.tell(System.currentTimeMillis()); - } - }, system.dispatcher()); - - -API Changes to Future - Scala -============================= - -v2.0:: - - def square(i: Int): Future[Int] = Promise successful i * i - -v2.1:: - - def square(i: Int): Future[Int] = Future successful i * i - -v2.0:: - - val failedFilter = future1.filter(_ % 2 == 1).recover { - case m: MatchError => //When filter fails, it will have a MatchError - } - -v2.1:: - - val failedFilter = future1.filter(_ % 2 == 1).recover { - // When filter fails, it will have a java.util.NoSuchElementException - case m: NoSuchElementException => - } - -A ``Promise`` is no longer also a ``Future``, obtain the reference to its Future by calling ``promise.future``. - -v2.0:: - - Await.result(promise, duration) - -v2.1:: - - Await.result(promise.future, duration) - -API Changes to Future - Java -============================ - -v2.0:: - - ExecutorService yourExecutorServiceGoesHere = Executors.newSingleThreadExecutor(); - ExecutionContextExecutorService ec = - ExecutionContexts.fromExecutorService(yourExecutorServiceGoesHere); - - // Use ec with your Futures - Future f1 = Futures.successful("foo", ec); - - // Then you shut the ec down somewhere at the end of your application. - ec.shutdown(); - -v2.1:: - - ExecutorService yourExecutorServiceGoesHere = Executors.newSingleThreadExecutor(); - ExecutionContext ec = - ExecutionContexts.fromExecutorService(yourExecutorServiceGoesHere); - - //No need to pass the ExecutionContext here - Future f1 = Futures.successful("foo"); - - // Then you shut the ExecutorService down somewhere at the end of your application. - yourExecutorServiceGoesHere.shutdown(); - -v2.0:: - - Future f1 = future(new Callable() { - public String call() { - return "Hello" + "World"; - } - }, system.dispatcher()); - -v2.1:: - - final ExecutionContext ec = system.dispatcher(); - - Future f1 = future(new Callable() { - public String call() { - return "Hello" + "World"; - } - }, ec); - -v2.0:: - - Future future1 = Futures.successful("value", system.dispatcher()).andThen( - new OnComplete() { - public void onComplete(Throwable failure, String result) { - if (failure != null) - sendToIssueTracker(failure); - } - }).andThen(new OnComplete() { - public void onComplete(Throwable failure, String result) { - if (result != null) - sendToTheInternetz(result); - } - }); - -v2.1:: - - final ExecutionContext ec = system.dispatcher(); - Future future1 = Futures.successful("value").andThen( - new OnComplete() { - public void onComplete(Throwable failure, String result) { - if (failure != null) - sendToIssueTracker(failure); - } - }, ec).andThen(new OnComplete() { - public void onComplete(Throwable failure, String result) { - if (result != null) - sendToTheInternetz(result); - } - }, ec); - -A ``Promise`` is no longer also a ``Future``, obtain the reference to its Future by calling ``promise.future()``. - -v2.0:: - - Await.result(promise, duration); - -v2.1:: - - Await.result(promise.future(), duration); - -API changes to DynamicAccess -============================ - -All methods with scala.Either[Throwable, X] have been changed to use scala.util.Try[X]. - -DynamicAccess.withErrorHandling has been removed since scala.util.Try now fulfills that role. - -API changes to Serialization -============================ - -All methods with scala.Either[Throwable, X] have been changed to use scala.util.Try[X]. - -Empty Props -=========== - -v2.0 Scala:: - - val router2 = system.actorOf(Props().withRouter( - RoundRobinRouter(routees = routees))) - -v2.1 Scala:: - - val router2 = system.actorOf(Props.empty.withRouter( - RoundRobinRouter(routees = routees))) - -v2.0 Java:: - - ActorRef router2 = system.actorOf(new Props().withRouter( - RoundRobinRouter.create(routees))); - -v2.1 Java:: - - ActorRef router2 = system.actorOf(Props.empty().withRouter( - RoundRobinRouter.create(routees))); - -Props: Function-based creation -============================== - -v2.0 Scala:: - - Props(context => { case someMessage => context.sender ! someMessage }) - -v2.1 Scala:: - - Props(new Actor { def receive = { case someMessage => sender ! someMessage } }) - -Failing Send -============ - -When failing to send to a remote actor or an actor with a bounded or durable mailbox the message will -now be silently delivered to ``ActorSystem.deadletters`` instead of throwing an exception. - -Graceful Stop Exception -======================= - -If the target actor of ``akka.pattern.gracefulStop`` isn't terminated within the -timeout then the ``Future`` is completed with a failure of ``akka.pattern.AskTimeoutException``. -In 2.0 it was ``akka.actor.ActorTimeoutException``. - -getInstance for Singletons - Java -==================================== - -v2.0:: - - import static akka.actor.Actors.*; - - if (msg.equals("done")) { - myActor.tell(poisonPill()); - } else if (msg == Actors.receiveTimeout()) { - -v2.1:: - - import akka.actor.PoisonPill; - import akka.actor.ReceiveTimeout; - - if (msg.equals("done")) { - myActor.tell(PoisonPill.getInstance()); - } else if (msg == ReceiveTimeout.getInstance()) { - - -Testkit Probe Reply -=================== - -v2.0:: - - probe.sender ! "world" - -v2.1:: - - probe.reply("world") - -log-remote-lifecycle-events -=========================== - -The default value of akka.remote.log-remote-lifecycle-events has changed to **on**. -If you don't want these events in the log then you need to add this to your configuration:: - - akka.remote.log-remote-lifecycle-events = off - -Stash postStop -============== - -Both Actors and UntypedActors using ``Stash`` now override postStop to make sure that -stashed messages are put into the dead letters when the actor stops. Make sure you call -super.postStop if you override it. - -Forwarding Terminated messages -============================== - -Forwarding ``Terminated`` messages is no longer supported. Instead, if you forward -``Terminated`` you should send the information in your own message. - -v2.0:: - - context.watch(subject) - - def receive = { - case t @ Terminated => someone forward t - } - -v2.1:: - - case class MyTerminated(subject: ActorRef) - - context.watch(subject) - - def receive = { - case Terminated(s) => someone forward MyTerminated(s) - } - - -Custom Routers and Resizers -=========================== - -The API of ``RouterConfig``, ``RouteeProvider`` and ``Resizer`` has been -cleaned up. If you use these to build your own router functionality the -compiler will tell you if you need to make adjustments. - -v2.0:: - - class MyRouter(target: ActorRef) extends RouterConfig { - override def createRoute(p: Props, prov: RouteeProvider): Route = { - prov.createAndRegisterRoutees(p, 1, Nil) - -v2.1:: - - class MyRouter(target: ActorRef) extends RouterConfig { - override def createRoute(provider: RouteeProvider): Route = { - provider.createRoutees(1) - -v2.0:: - - def resize(props: Props, routeeProvider: RouteeProvider): Unit = { - val currentRoutees = routeeProvider.routees - val requestedCapacity = capacity(currentRoutees) - - if (requestedCapacity > 0) { - val newRoutees = routeeProvider.createRoutees(props, requestedCapacity, Nil) - routeeProvider.registerRoutees(newRoutees) - } else if (requestedCapacity < 0) { - val (keep, abandon) = currentRoutees.splitAt(currentRoutees.length + - requestedCapacity) - routeeProvider.unregisterRoutees(abandon) - delayedStop(routeeProvider.context.system.scheduler, abandon)( - routeeProvider.context.dispatcher) - } - - -v2.1:: - - def resize(routeeProvider: RouteeProvider): Unit = { - val currentRoutees = routeeProvider.routees - val requestedCapacity = capacity(currentRoutees) - - if (requestedCapacity > 0) routeeProvider.createRoutees(requestedCapacity) - else if (requestedCapacity < 0) routeeProvider.removeRoutees( - -requestedCapacity, stopDelay) - -Duration and Timeout -==================== - -The :class:`akka.util.Duration` class has been moved into the Scala library under -the ``scala.concurrent.duration`` package. Several changes have been made to tighten -up the duration and timeout API. - -:class:`FiniteDuration` is now used more consistently throught the API. -The advantage is that if you try to pass a possibly non-finite duration where -it does not belong you’ll get compile errors instead of runtime exceptions. - -The main source incompatibility is that you may have to change the declared -type of fields from ``Duration`` to ``FiniteDuration`` (factory methods already -return the more precise type wherever possible). - -Another change is that ``Duration.parse`` was not accepted by the Scala library -maintainers; use ``Duration.create`` instead. - -v2.0:: - - final Duration d = Duration.parse("1 second"); - final Timeout t = new Timeout(d); - -v2.1:: - - final FiniteDuration d = Duration.create(1, TimeUnit.SECONDS); - final Timeout t = new Timeout(d); // always required finite duration, now enforced - -Package Name Changes in Remoting -================================ - -The package name of all classes in the ``akka-remote.jar`` artifact now starts with ``akka.remote``. -This has been done to enable OSGi bundles that don't have conflicting package names. - -Change the following import statements. Please note that serializers are often referenced from -configuration files. - -Search -> Replace with:: - - akka.routing.RemoteRouterConfig -> - akka.remote.routing.RemoteRouterConfig - - akka.serialization.ProtobufSerializer -> - akka.remote.serialization.ProtobufSerializer - - akka.serialization.DaemonMsgCreateSerializer -> - akka.remote.serialization.DaemonMsgCreateSerializer - - -Package Name Changes in Durable Mailboxes -========================================= - -The package names of all classes in the ``akka-file-mailbox.jar`` artifact now start with ``akka.actor.mailbox.filebased``. -This has been done to enable OSGi bundles that don't have conflicting package names. - -Change the following import statements. Please note that the ``FileBasedMailboxType`` is often referenced from configuration. - -Search -> Replace with:: - - akka.actor.mailbox.FileBasedMailboxType -> - akka.actor.mailbox.filebased.FileBasedMailboxType - - akka.actor.mailbox.FileBasedMailboxSettings -> - akka.actor.mailbox.filebased.FileBasedMailboxSettings - - akka.actor.mailbox.FileBasedMessageQueue -> - akka.actor.mailbox.filebased.FileBasedMessageQueue - - akka.actor.mailbox.filequeue.* -> - akka.actor.mailbox.filebased.filequeue.* - - -Actor Receive Timeout -===================== - -The API for setting and querying the receive timeout has been made more -consistent in always taking and returning a ``Duration``; the wrapping in -``Option`` has been removed. - -(Samples for Java, Scala sources are affected in exactly the same way.) - -v2.0:: - - getContext().setReceiveTimeout(Duration.create(10, SECONDS)); - final Option timeout = getContext().receiveTimeout(); - final isSet = timeout.isDefined(); - resetReceiveTimeout(); - -v2.1:: - - getContext().setReceiveTimeout(Duration.create(10, SECONDS)); - final Duration timeout = getContext().receiveTimeout(); - final isSet = timeout.isFinite(); - getContext().setReceiveTimeout(Duration.Undefined()); - -ConsistentHash -============== - -``akka.routing.ConsistentHash`` has been changed into an immutable data structure. - -v2.0:: - - val consistentHash = new ConsistentHash(Seq(a1, a2, a3), replicas = 10) - consistentHash += a4 - val a = consistentHash.nodeFor(data) - -v2.1:: - - var consistentHash = ConsistentHash(Seq(a1, a2, a3), replicas = 10) - consistentHash = consistentHash :+ a4 - val a = consistentHash.nodeFor(data) - +Migration from 2.0.x to 2.1.x is described in the +`documentation of 2.1 `_. \ No newline at end of file diff --git a/akka-docs/rst/project/migration-guide-2.1.x-2.2.x.rst b/akka-docs/rst/project/migration-guide-2.1.x-2.2.x.rst index fef4462db8..1a30507ecc 100644 --- a/akka-docs/rst/project/migration-guide-2.1.x-2.2.x.rst +++ b/akka-docs/rst/project/migration-guide-2.1.x-2.2.x.rst @@ -8,7 +8,7 @@ The 2.2 release contains several structural changes that require some simple, mechanical source-level changes in client code. When migrating from 1.3.x to 2.1.x you should first follow the instructions for -migrating `1.3.x to 2.0.x `_ and then :ref:`2.0.x to 2.1.x `. +migrating :ref:`1.3.x to 2.0.x ` and then :ref:`2.0.x to 2.1.x `. Immutable everywhere ====================