EDIT2
@paradigmatic提出了重定向而不是抛出异常的好处;解决了日志记录问题。 Play 2中的问题是重定向需要在所谓的Action
范围内发生,而日期解析器调用并非总是如此。Java 7:抛出没有堆栈跟踪的异常
作为一种解决方法,我使用了Play的全局拦截器,大概相当于一个Java servlet过滤器。
val ymdMatcher = "\\d{8}".r // matcher for yyyyMMdd URI param
val ymdFormat = org.joda.time.format.DateTimeFormat.forPattern("yyyyMMdd")
def ymd2Date(ymd: String) = ymdFormat.parseDateTime(ymd)
override def onRouteRequest(r: RequestHeader): Option[Handler] = {
import play.api.i18n.Messages
ymdMatcher.findFirstIn(r.uri) map{ ymd=>
try { ymd2Date(ymd); super.onRouteRequest(r) }
catch { case e:Exception => // kick to "bad" action handler on invalid date
Some(controllers.Application.bad(Messages("bad.date.format")))
}
} getOrElse(super.onRouteRequest(r))
}
编辑
这里有一个小范围内一起工作:
// String "pimp": transforms ymdString.to_date call into JodaTime instance
class String2Date(ymd: String) {
def to_date = {
import play.api.i18n.Messages
try{ ymdFormat.parseDateTime(ymd) }
catch { case e:Exception => throw new NoTrace(Messages("bad.date.format")) }
}
val ymdFormat = org.joda.time.format.DateTimeFormat.forPattern("yyyyMMdd")
}
@inline implicit final def string2Date(ymd: String) = new String2Date(ymd)
和测试自定义异常处理程序:
public class NoTrace extends Exception {
static final long serialVersionUID = -3387516993124229948L;
@Override
public Throwable fillInStackTrace() {
return null;
}
public NoTrace(String message) {
super(message);
}
}
上调用一个无效的年月日的日期解析器字符串记录30行堆栈跟踪到日志(这发生在Play框架/ Netty容器的上游,是tter比默认的100线迹):
"20120099".to_date
ORIGINAL
有在我的application.log是越来越充满了与该应该成功提供有效的yyyyMMdd
URI日期URI日期解析器操作失误的问题。
但是,一些用户试图通过输入无效日期来避免这种情况,希望获得免费访问付费用户专用内容。这是毫无意义的,因为它根本无法工作,但无论如何,我的应用程序日志中都有这些错误跟踪的MB。
有没有办法将一个真正修剪到日志中的Exception
?我发现this SO answer,但在我的应用程序中,它看起来像容器(Netty上的Play框架)进入混合并将其自己的30行堆栈跟踪记录到日志中(30行比100好,但仍有29太多)
同样,我发现this thread在Java 7和新的选项抑制堆栈跟踪;然而,出于某种原因,尽管使用了Java 1.7,但为Java 1.7配置了Eclipse,但只有Throwable的旧2参数方法可用(并且在单击到Throwable类时可以看到4参数方法;也许是Scala 2.9.2库问题?)
无论如何,理想情况下,我可以简单地记录单行异常消息而不是厨房水槽。
写下你的代码,你可能没有打印堆栈跟踪 –
为什么在第一个地方抛出Exception?是否有可能接受任何日期(有效与否),并在无效时重定向到页面? – paradigmatic
@paradigmatic好点,问题是我相信Play 2 Scala重定向必须发生在Action范围内(例如“def index = Action {Ok.redirect(”/ foo“)}”); uri日期解析器调用站点并不总是出现在Action范围内,所以我没有办法重定向(你是对的,这是首选解决方案) – virtualeyes