Catching multiple exceptions at once in Scala

Catching multiple exceptions at once in Scala

You can bind the whole pattern to a variable like this:

try {
   throw new java.io.IOException(no such file)
} catch {
   // prints out java.io.IOException: no such file
   case e @ (_ : RuntimeException | _ : java.io.IOException) => println(e)
}

See the Scala Language Specification page 118 paragraph 8.1.11 called Pattern alternatives.

Watch Pattern Matching Unleashed for a deeper dive into pattern matching in Scala.

As you have access to the full pattern matching capabilities of scala in the catch clause, you can do a lot :

try {
  throw new IOException(no such file)
} catch {
  case _ : SQLException | _ : IOException => println(Resource failure)
  case e => println(Other failure);
}

Note that if you need to write the same handlers time and time again you can create your own control structure for that :

def onFilesAndDb(code: => Unit) { 
  try { 
    code 
  } catch {
    your handling code 
  }
}

Some such methods are available in object scala.util.control.Exceptions. failing, failAsValue, handling may be just what you need

Edit : Contrary to what is said below, alternative patterns can be bound, so the proposed solution is needlessly complex. See @agilesteel solution

Unfortunately, with this solution, you have no access to the exception where you use the alternative patterns. To my knowledge, you cannot bind on an alternative pattern with case e @ (_ : SqlException | _ : IOException). So if you need access to the exception, you have to nest matchers :

try {
  throw new RuntimeException(be careful)
} catch  {
  case e : RuntimeException => e match {
    case _ : NullPointerException | _ : IllegalArgumentException => 
      println(Basic exception  + e)
    case a: IndexOutOfBoundsException => 
      println(Arrray access  + a)
    case _ => println(Less common exception  + e)
  }
  case _ => println(Not a runtime exception)
}

Catching multiple exceptions at once in Scala

You can also use scala.util.control.Exception:

import scala.util.control.Exception._
import java.io.IOException

handling(classOf[RuntimeException], classOf[IOException]) by println apply { 
  throw new IOException(foo) 
}

This specific example might not be the best example to illustrate how you can use it, but I find it pretty useful in many occasions.

Leave a Reply

Your email address will not be published.