Error Handling in Scala

Có nhiều cách để Error Handling trong Scala, chúng ta sẽ cùng nhau tìm hiểu.
Hãy nhìn ví dụ dưới đây:

  val coffeePrice = 10

  def buyCoffee(money: Float): Coffee= {
    if(money < coffeePrice) {
    try {
      buyCoffee(5)
    } catch {
      case e: Exception => e.getMessage
    }

Khi gọi hàm buyCoffee với tham số truyền vào là 5, hệ thống sẽ throw ra exception:

    buyCoffee(5) //>Exception in thread "main" java.lang.Exception: Not enough money to buy a coffee, need 10

OK, theo cách truyền thống chúng ta sẽ sử dụng try/catch để xử lý:

    try {
      buyCoffee(5)
    } catch {
      case e: Exception => e.getMessage
    }

Look good, nhưng nhìn lại chúng ta đang code theo cách của Java :P.

Chúng ta sẽ viết lại đoạn code trên theo cách của Scala!

import scala.util.Try
    ...

  val coffeePrice = 10

  def buyCoffee(money: Float): Try[Coffee] = {
    Try {
      if(money < coffeePrice) {
        throw new Exception(s"Not enough money to buy a coffee, need $coffeePrice")
      } else {
        new Coffee
      }
    }
  }

Chúng ta sử dụng Try block trong hàm buyCoffee và kiểu trả về của hàm này sẽ là Try[Coffee]. Hàm buyCoffee lúc này không cần thực hiện “Error Handling”, nó trả ra Success(Coffee) hoặc Failure(java.lang.Exception: Not enough money to buy a coffee, need 10).
Có nhiều cách khác nhau để extract giá trị của lệnh gọi hàm buyCoffee(5),

    val coffee = buyCoffee(5)
    if(coffee.isSuccess) coffee.get else "OK! I will back!"

Hoặc bạn có thể dùng getOrElse

    val coffee = buyCoffee(5)
    coffee.getOrElse("OK! I will back!")

Hoặc bạn có thể sử dụng Pattern Matching:

    buyCoffee(5) match {
      case Success(result) => result
      case Failure(result) => "OK! I will Back!"
    }

Nhưng mình thích nhất là cách này,

    buyCoffee(5).map { coffee =>
      coffee
    }.recover{
      case e: Exception => "OK! I will Back!"
    }

Sử dụng recover để bắt trường hợp Try trả ra Failure

OK! Hẹn gặp lại các bạn trong các bài chia sẻ tiếp theo.

Add a Comment

Scroll Up