大约一年前,我开始使用MVC设计模式创建Web应用程序。我用these series开始了我的旅程,它为我提供了一些创建我自己的MVC应用程序的句柄。非常基本,但很简单。
然后我偶然发现了S.O.L.I.D. Robert C. Martin定义的原则。通过分别学习每个原理,我得到了可以为将来编写可维护代码的方法。当我发现我每天都违反了所有5条原则时,但仅仅因为我的代码有效,我根本没有试图尊重它们。那么为什么不将MVC与SOLID结合起来呢? Stefan Priebsch的{{3}}给了我一些关于如何将它们混合在一起的见解。 Stefan建议为每个需要采取的动作创建一个Controller。这是有道理的,它将导致干净,易于阅读和维护的代码。现在解决我的问题。我有一个.htaccess文件,用于重写URL。例如:This presentation会创建一个用户,而http://website.com/user/create会向新用户发送一封包含帐户信息的电子邮件。这两个网址都会转到用户'控制器和执行方法'创建'和'电子邮件'。现在这违反了单一责任原则。用户'控制器都具有创建AND以向用户发送电子邮件的功能。最好更改代码并创建两个控制器:
class CreateUserController extends Controller {
public function create() {
}
}
class EmailUserController extends Controller {
public function email() {
}
}
这意味着我的网址将是http://website.com/user/email和http://website.com/CreateUserController。但那不是我想要的吗? / user / create会导致CreateUserController和/ user / email导致EmailUserController。我该怎么办呢?
这是我使用的路由器。 $ url [0]是控制器,$ url [1]是该控制器内的方法。
class App {
protected $controller = 'home';
protected $method = 'index';
protected $params = [];
public function __construct() {
$url = $this->parseUrl();
if(file_exists('../app/controllers/' . $url[0] . '.php')) {
$this->controller = $url[0];
unset($url[0]);
}
require_once '../app/controllers/' . $this->controller . '.php';
$this->controller = new $this->controller;
if(isset($url[1])) {
if(method_exists($this->controller, $url[1])) {
$this->method = $url[1];
unset($url[1]);
} else {
header('location: /home/error');
}
}
$this->params = $url ? array_values($url) : [];
call_user_func_array([$this->controller, $this->method], $this->params);
}
public function parseUrl() {
if(isset($_GET['url'])) {
return $url = explode('/', filter_var(rtrim($_GET['url'], '/'), FILTER_SANITIZE_URL));
}
}
}
class Controller {
protected function model($model, $data = []) {
require_once APP . '/models/' . $model . '.php';
return new $model($data);
}
protected function view($view, $data = []) {
require_once APP . '/views/' . $view . '.php';
}
}