在我正在构建的框架中,我正朝着使我的代码更具可测试性的方向发展,因为我以前沉迷于 MVC+Singleton 模式并且拥有大量的静态类。从那时起,我开始更多地了解单元测试和 TDD,因此它促使我重构了很多代码。这种重构的一部分促使我尝试在 PHP 中正确使用 Extension 类,即不仅仅是抛出 Exception 类,而是抛出更多相关的异常。
我有以下课程:
<?php
namespace Framework;
class Uri {
public static function new_from_http() {
$uri = '';
if (isset($_SERVER['REQUEST_URI'])) {
$uri = $_SERVER['REQUEST_URI'];
} elseif (isset($_SERVER['PATH_INFO'])) {
$uri = $_SERVER['PATH_INFO'];
}
return static::new_from_string($uri);
}
public static function new_from_string($string) {
return new static(explode('/', $string));
}
protected $uri = [];
public function __construct(array $uri) {
$this->uri = array_values(array_filter($uri));
}
public function get_segment($offset, $default = null) {
if (!is_int($offset)) {
throw new \InvalidArgumentException(
sprintf('%s requires argument 1 to be an integer, %s given.',
__METHOD__,
gettype()
)
);
}
return isset($this->uri[$offset - 1])
? $this->uri[$offset - 1]
: $default;
}
}
一切都很好,正如您所看到的,get_segment 方法需要一个整数,否则它会引发 InvalidArgumentException。问题是,我想创建更多的方法,这些方法也需要整数作为参数,并且我不想在任何地方剪切和粘贴该代码。合并所有这些类型的参数检查的最佳选择是什么,以便我可以在不同的类和方法中使用它们,同时保持消息彼此一致。
我的想法之一是在框架命名空间下扩展异常类,并让构造函数采用不同的参数,例如:
namespace Framework;
class InvalidArgumentException extends \InvalidArgumentException {
public function __construct($method, $argument, $value) {
parent::__construct(
sprintf('%s requires argument 1 to be an integer, %s given.',
$method,
gettype($value)
)
);
}
}
这将被称为:
if (!is_int($arg)) {
throw new \Framework\InvalidArgumentException(__METHOD__, 1, $arg);
}
还可以改进的是可以通过回溯\Framework\InvalidArgumentException
获取值。__METHOD__
我还有哪些其他选择,最好的选择是什么?