【问题标题】:php exception handling setting message afterwards之后的php异常处理设置消息
【发布时间】:2011-06-12 11:54:42
【问题描述】:

我们通常在实例化时设置消息,像这样:

throw new Exception($msg);`

但我的情况是,我有一个默认异常对象存储在一个实例变量中,并在对象的整个生命周期中使用它,如下所示:

throw $this->my_exception;

由于我重复使用同一个对象,我需要能够在抛出异常之前随时设置消息,你明白吗?

【问题讨论】:

  • 到底为什么它会这样工作?如果您重用异常,那么行号可能是错误的,因为您已经抛出了它?扔一个新的有什么问题?
  • 如果我可以问:你这样做是为了什么?
  • @jakenoble:客户端代码需要能够注入他/她偏好的异常对象;我知道这听起来很奇怪,但我需要它......

标签: php exception exception-handling instance-variables throw


【解决方案1】:

创建自定义异常:

class MyException extends Exception
{
    public function setMessage($message) {
        $this->message = $message;
    }
}

然后你可以创建并抛出这个异常

$this->exception = new MyException;
// ...
$this->exception->setMessage('Bad stuff happened');
throw $this->expection;

虽然我真的不明白你为什么会做那样的事情。

【讨论】:

  • @jakenoble:有时在异常消息前面加上一个字符串来识别发生异常的逻辑块是很有用的:$e->setMessage(sprintf('Cannot enqueue work: %s', $e->getMessage));。因此,如果您在同一个块中有多个 throws 影响“排队工作”,它会使调试更容易一点,提供异常上下文而无需为所有异常消息添加相同的前缀。
【解决方案2】:

不要那样做。它使跟踪异常变得更加困难(因为堆栈跟踪不包括重新抛出)。相反,如果您使用的是 5.3+,请使用 $previous parameter 并创建一个新例外:

throw new Exception("message", 0, $this->my_exception);

即使你使用的是低于 5.3 的版本,你也可以扩展异常类并添加它...

编辑:好的,根据您的 cmets,我知道您现在要做什么。你想让你的类抛出一个可配置的异常。我会做的是在其中获取一个字符串类名并将其存储。所以$this->my_exception 将是一个字符串。你应该在存储它之前验证它是一个异常类,因为你不能抛出不从Exception扩展的东西:

if (!is_subclass_of($this->my_exception, 'Exception')) {
    //Error out, since you can't throw that class name
}

那么,该扔的时候了:

$class = $this->my_exception;
throw new $class("MyMessage");

它仍然不是很好,因为异常应该具有语义含义(因此存在 LogicExceptionInvalidArgumentException),但如果这是一个要求,那不是一种可怕的方式(但预先实例化一个异常是一种可怕的做法)...

【讨论】:

  • 我认为他不会重新投掷。他简单地创建了异常而不抛出它并在以后抛出它。
  • @nikic:那更糟……@Fabio:你为什么要这么做?滥用异常是一个非常糟糕的主意。仅在特殊情况下正确使用它们。没有真正的理由在抛出异常之前实例化它(或者至少不以抛出的直接意图实例化)。它们并不便宜,所以除非你需要,否则不要使用它们......
  • @ircmaxell:我也这么认为。我想不出在时间有任何好处之前创建异常的情况......
  • 怎么做 $exception = get_class($this->my_exception);抛出新的 $exception($msg);这很糟糕吗?
  • @ircmaxell:非常感谢,就是这样!我不得不传递一个异常对象并且这样做是为了利用类型提示,但是因为您可以检查给定名称是否是异常类的子类型......我的问题现在解决了; )
猜你喜欢
  • 1970-01-01
  • 2013-07-05
  • 1970-01-01
  • 2013-07-19
  • 2011-09-16
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2019-01-24
相关资源
最近更新 更多