共享错误和密封特征的函数

时间:2015-11-26 16:24:53

标签: scala error-handling

我正在为kadmin命令实现一个库。除其他外,还有以下方法:

def changePassword(principal: String, newPassword: String): Either[ErrorCase, Boolean]
def deletePrincipal(principal: String): Either[ErrorCase, Boolean]

这两个操作可能会返回错误,因此它们的返回类型为Either[ErrorCase, Boolean]。其中ErrorCase定义为:

trait ErrorCase
case object InsufficientPermissions extends ErrorCase
case object PrincipalDoesNotExist extends ErrorCase
case object IncorrectPassword extends ErrorCase
case object PasswordTooShort extends ErrorCase
case object PasswordWithoutEnoughCharacterClasses extends ErrorCase
case object PasswordIsBeingReused extends ErrorCase
case object PasswordExpired extends ErrorCase
case object UnknownError extends ErrorCase

我的问题是:如果我将特征ErrorCase定义为一个密封的特征,我将给API的用户带来负担,以便在他/她调用其中一个时检查所有可能的ErrorCase。 API方法。这对changePassword方法有意义,因为所有这些错误情况都可能在此操作中发生。但对于deletePrincipal方法,这没有任何意义,因为与密码相关的所有错误情况都不会发生。换句话说,API方法共享错误情况,但每个方法不一定使用每个错误情况。

如何将特性密封,但不知何故指明在每种方法中只使用一些ErrorCases。

2 个答案:

答案 0 :(得分:4)

  

计算机科学中的任何问题都可以通过另一个层次来解决   间接,除了间接层次太多的问题。

sealed trait ErrorCase
sealed trait PasswordErrors extends ErrorCase
sealed trait OtherErrors extends ErrorCase

case object IncorrectPassword extends PasswordErrors
case object PasswordTooShort extends PasswordErrors
case object PasswordWithoutEnoughCharacterClasses extends PasswordErrors
case object PasswordIsBeingReused extends PasswordErrors
case object PasswordExpired extends PasswordErrors

case object InsufficientPermissions extends OtherErrors
case object PrincipalDoesNotExist extends OtherErrors
case object UnknownError extends OtherErrors

不确定最好的方式来处理UnknownErrorOtherErrors的子类,或ErrorCase的子类或其他内容),但它是什么?由你来解决这个问题。

答案 1 :(得分:0)

  

我会给API的用户带来负担,以便在他/她调用其中一种API方法时检查所有可能的ErrorCases

为什么呢?他们可以在_上匹配,以便立即处理所有错误情况。

deletePrincipal("me") match {
  case Right(bool)                 => ???
  case Left(PrincipalDoesNotExist) => ??? 
  case _                           => ???
}

我看到的唯一问题是你是否为ErrorCase(即fold方法)提供了一种解释。但话说再说一次,带有8个参数的fold非常糟糕。