Getting an java.util.concurrent.ExecutorService from a scala.concurrent.ExecutionContext?

1,958 views
Skip to first unread message

Alexandru Nedelcu

unread,
Mar 26, 2013, 4:43:41 AM3/26/13
to scala-user
Hi,

Seeing that you can create an s.c.ExecutionContext from a
j.u.c.ExecutorService, I am interested in the other way around because
in apps I'm usually using the implicit ExecutionContext provided by
Scala or by the Play framework in Play apps.

So besides manually implementing the ExecutorService interface, is
there a shortcut for it?

--
Alexandru Nedelcu
http://bionicspirit.com

√iktor Ҡlang

unread,
Mar 26, 2013, 6:25:41 AM3/26/13
to Alexandru Nedelcu, scala-user
Yes and no. ExecutionContext is isomorphic to Executor, but ExecutorService has a ton of methods, and depending on what you'll expect when calling shutdown for instance, you can most definitely write a converter.

However, if you create your ExecutionContext from ExecutionContext.fromExecutorService, you'll get back an ExecutionContextExecutorService, which implements both.

But the real question, what do you need the ExecutorService for?

Cheers,


--
You received this message because you are subscribed to the Google Groups "scala-user" group.
To unsubscribe from this group and stop receiving emails from it, send an email to scala-user+...@googlegroups.com.
For more options, visit https://groups.google.com/groups/opt_out.





--
Viktor Klang
Director of Engineering

Twitter: @viktorklang

Alexandru Nedelcu

unread,
Mar 26, 2013, 7:54:11 AM3/26/13
to √iktor Ҡlang, scala-user
Hey √iktor, by mistake I forgot to do a reply all, so I sent the
message quoted below only to you, now forwarded to scala-user too.
Sorry.

I came up with the following implementation for an ExecutorService
that wraps an ExecutionContext, don't know if this is correct but I
think I'll end up using something like this:

https://gist.github.com/alexandru/5244811


On Tue, Mar 26, 2013 at 1:04 PM, Alexandru Nedelcu <m...@alexn.org> wrote:
> Hi Viktor, thanks for the answer.
>
> I have a web service that I need to keep lean and mean and letting
> Java libraries manage their own thread-pools is kind of a pain point.
> Many Java APIs do allow you to specify an executor service as an
> alternative to using their default and since (when working with
> Futures/Promises/Akka) I already have a default thread-pool, it would
> be nice to use it for these Java libraries too.
>
> The latest thing I want to try out is to use an
> AsynchronousFileChannel, as writing to the same file from multiple
> threads can become a real bottleneck. If you don't specify an executor
> for AsynchronousFileChannel, then it will use the default, whatever
> that is.
>
> When it comes to these Java libraries, if you specify an executor,
> they don't shut it down by themselves, as they only need the ability
> to submit tasks, so I guess I can simply throw
> UnsupportedOperationException or something on shutdown(),
> shutdownNow() and on awaitTermination().
Alexandru Nedelcu
http://bionicspirit.com

√iktor Ҡlang

unread,
Mar 26, 2013, 8:50:14 AM3/26/13
to Alexandru Nedelcu, scala-user
Hi Alexandru,

I'd probably do something like this:

import scala.concurrent.{ExecutionContext, ExecutionContextExecutorService}
import java.util.concurrent.{ AbstractExecutorService, TimeUnit }
import java.util.Collections

object ExecutionContextExecutorServiceBridge {
  def apply(ec: ExecutionContext): ExecutionContextExecutorService = ec match {
    case null => throw null
    case eces: ExecutionContextExecutorService => eces
    case other => new AbstractExecutorService with ExecutionContextExecutorService {
      override def prepare(): ExecutionContext = other
      override def isShutdown = false
      override def isTerminated = false
      override def shutdown() = ()
      override def shutdownNow() = Collections.emptyList[Runnable]
      override def execute(runnable: Runnable): Unit = other execute runnable
      override def reportFailure(t: Throwable): Unit = other reportFailure t
      override def awaitTermination(length: Long,unit: TimeUnit): Boolean = false
    }
  }
}

Cheers,

Alexandru Nedelcu

unread,
Mar 26, 2013, 9:20:57 AM3/26/13
to √iktor Ҡlang, scala-user
Oh, nice, thanks a lot.

Andy Polack

unread,
Nov 24, 2014, 9:35:30 AM11/24/14
to scala...@googlegroups.com, m...@alexn.org
√iktor,

I came across this post looking for scalaz.concurrent to scala.concurrent interop.  Since ScalaZ's concurrency is based on Java's ExecutorService, having this conversion is important, especially when applying ScalaZ in the context of Play Framework where the existing async Controller API expects a scala.concurrent.Future.

Of particular interest is being able to configure ExecutionContexts via Typesafe Config to be able to deploy service stacks with allocated execution pools to remote nodes.  Doing so will require a conversion from ExecutionContext to ExecutorService.

Here's my concern though - the way you've proxied the 'other' case in your example above would mean that the underlying ExecutionContext could never be shutdown (if it needed to be).  Is it true that the only sort of ExecutionContext that should require shutdown is one that is an ExecutionContextExecutorService to being with?  If so, then I imagine this proxy is fine.  If not though, couldn't this lead to leaky thread pools hanging around in the JVM? 

Thanks Much,
Andy

√iktor Ҡlang

unread,
Dec 13, 2014, 3:10:47 PM12/13/14
to Andy Polack, scala-user, Alexandru Nedelcu
Hi Andy,

Apologies for the late reply, I just noticed this in my drafts folder.


On Mon, Nov 24, 2014 at 3:35 PM, Andy Polack <apo...@sdlgov.com> wrote:
√iktor,

I came across this post looking for scalaz.concurrent to scala.concurrent interop.  Since ScalaZ's concurrency is based on Java's ExecutorService, having this conversion is important, especially when applying ScalaZ in the context of Play Framework where the existing async Controller API expects a scala.concurrent.Future.

Of particular interest is being able to configure ExecutionContexts via Typesafe Config to be able to deploy service stacks with allocated execution pools to remote nodes.  Doing so will require a conversion from ExecutionContext to ExecutorService.

Here's my concern though - the way you've proxied the 'other' case in your example above would mean that the underlying ExecutionContext could never be shutdown (if it needed to be).  Is it true that the only sort of ExecutionContext that should require shutdown is one that is an ExecutionContextExecutorService to being with?  If so, then I imagine this proxy is fine.  If not though, couldn't this lead to leaky thread pools hanging around in the JVM? 

who should be able to shut it down?
(I am a strong believer in the "the creator is the destroyer" philosophy here)

My main dislike for ExecutorService as a parameter is that it is impossible to know who is allowed to, and who is supposed to, shut it down, and should they use shutdownNow or not?
 
For more options, visit https://groups.google.com/d/optout.



--
Cheers,

Andy Polack

unread,
Dec 15, 2014, 5:46:51 AM12/15/14
to scala...@googlegroups.com, apo...@sdlgov.com, m...@alexn.org
√iktor,

Thanks for the reply.  We reached a similar conclusion here after posing the question through the Typesafe Subscription program.  Essentially, it sounds like so long as we let Akka create all of our ExecutionContexts and then do our conversions back and forth with those references, we can rely on Akka to stop them for us appropriately.  

Kind Regards,
Andy

√iktor Ҡlang

unread,
Dec 16, 2014, 2:49:36 PM12/16/14
to Andy Polack, scala-user, Alexandru Nedelcu
Hi Andy,

Glad Akka solves this for you.

Happy hAkking!
Reply all
Reply to author
Forward
0 new messages