对于潜在的运行时故障,例如数据库查询,似乎必须使用某种形式的Either[String, Option[T]]
才能准确捕获以下结果:
选项根本没有足够的选项。
我想我需要潜入scalaz,但是现在它是直的,除非我在上面遗漏了什么。
使用我的DAO实现将自己装入一个角落,仅使用Either进行写操作,但现在看到一些Either写入依赖于Option读取(例如检查新用户注册时是否存在电子邮件),这是一个非常糟糕的赌博。
在我全押之前,是否有人有替代解决方案来处理成功/失败/异常的运行时三分之一?
答案 0 :(得分:8)
从精彩的Box
框架中尝试lift
。它提供了你想要的东西。
有关详细信息,请参阅this wiki(以及顶部的链接)。幸运的是,升力项目很好地模块化,使用Box
的唯一依赖是net.lift-web % lift-common
答案 1 :(得分:5)
对案例Option[T]
和records found
使用no records found
,并在SQLException的情况下抛出异常。
只需将异常包装在您自己的异常类型中,例如PersistenceException
,这样就不会出现漏洞。
我们这样做是因为我们不能也不想从意外的数据库异常中恢复。在这种情况下,异常会被捕获到顶层,我们的Web服务会返回500 Internal server error
。
如果我们想恢复,我们会使用scalaz中的Validation
,这很像Lift Box
。
答案 2 :(得分:0)
这是我的修订方法
保留返回查询写操作(对于我们想要回滚的事务块,对于理解左结果很有用)。
然而,对于Option返回查询读取而不是吞下异常(并记录它),我创建了一个500错误屏幕,让异常冒泡。
为什么在使用查询异常等运行时故障时,默认情况下不使用任何结果类型?选项[T]读取更方便使用vs [Why-Fail,Option [T]],你必须折叠/映射才能得到T。离开要么写操作简化了事情(更多因此,鉴于应用程序当前的设置方式,不需要重构; - ))
唯一需要的其他更改是AJAX请求。我们不是在AJAX状态div容器中显示整个500错误页面响应,而是检查状态类型并相应地显示500错误消息。
if(data.status == 500)
$('#status > div').html("an error occurred, please try again")
可能在发送响应之前执行isAjax检查服务器端;在这种情况下,我只能发回状态+消息而不是错误页面本身。