php - 在 Controller 之间切换(MVC)

标签 php oop model-view-controller

我正在尝试了解并找出一种在我的自定义框架中的 Controller 之间切换的好方法。以下示例是我目前的想法,出于演示目的进行了简化,但如果有更好的方法,我将非常感谢专家的建议?

class BaseController() {
    function __construct() {
        $this->model = new ModelFactory();
        $this->view = new View();

        if(isset($_SERVER['QUERY_STRING'])) {
            list($controller, $action) = explode('=', $_SERVER['QUERY_STRING']);
            self::process($controller);
        }
    }

    public function process($controller) {
        switch($controller) {
            case 'user':
                $user = new UserController($action);
            break;

            case 'forum':
                $forum = new ForumController($action);
            break;

            default:
                // use base controller
                switch($action) {
                    case 'contact':
                        $this->view->load($action);
                    break;
                }
        }
    }
}

// inside UserController.php
switch($action) {
    case 'register':
    break;

    case 'login':
    break;
}

// inside ForumController.php
switch($action) {
    case 'new_thread':
    break;

    case 'edit_post':
    break;
}

最佳答案

这确实是一个部分答案,希望能给您一些好的建议。我相信会有更好答案的人出现。

  1. 您示例中的 BaseController 可能命名有误。你所拥有的使它看起来更像是一个 Controller 工厂,而不是所有其他 Controller 类可能派生自的基本 Controller 。看起来这更像是一个“路由”类,因此您应该考虑为其工作取一个更合适的名称。

  2. 如果您希望您的框架用户使用自定义操作创建自定义 Controller :

    a) 您肯定希望至少为所有要实现的 Controller 类创建一个接口(interface)。称它为 IController 或类似名称。这将在下一步中使用。

    b) 您将不得不满足于使用字符串作为类名来创建对象。 IE $controllerObject = new $controller(); 在您的“Route”处理程序类中。原因是要运行的 Controller 和操作名称直接来自请求 URL。有办法为这部分起别名,但这完全是另一个问题。不要忘记验证和/或将这些从客户端传入的“ Controller ”类名列入白名单。验证:使用 PHP 函数 class_exists($controller) 然后如果 true,检查以确保 Controller 类使用 PHP 的内置实现 IController -in class_implements($controller)。只有然后您才应该执行 $controllerObject = new $controller(); 来实际创建 Controller 对象。

    然后您的“路由”process 方法变得更像(请记住这是一个非常简化的示例):

    public function process($controller, $action) {
        if (!class_exists($controller)) {
            throw new Exception('Controller class does not exist.');
        }
        if (!in_array("IController", class_implements($controller))) {
            throw new Exception('Route is not a valid controller.');
        }
        if (!method_exists($controller, $action)) {
            throw new Exception('No such action for requested controller.');
        }
        $ctrl = new $controller();
        return $ctrl->$action();
    }
    

    c) 不要让您的 Controller 声明任何您不希望客户端使用上述设计模式直接执行的方法(即以任何$action 的值命名)。希望您的框架用户也能理解这一点。请务必正确记录其内部工作原理,让您的框架用户了解。

当然还有比这更多的方法,但这取决于您 - 框架设计者。此外,操作应该对使用什么“ View ”拥有最终决定权。如果操作没有明确说明要使用的 View ,则有一些方法可以设置默认值。但同样,那将是另一个问题。

关于php - 在 Controller 之间切换(MVC),我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/14299014/

相关文章:

python - 添加我的类的两个实例

对象的 Javascript 浅拷贝未定义?

c - 卢阿 :new from C API

java - Swing 中的 MVC 线程安全吗

php - mod_php vs cgi vs fast-cgi

php - 用户操作后更新数据库

java - 如何在应用程序启动时触发 servlet 执行?

angularjs - 前端和后端使用MVC框架

PHP scandir递归

php - 类似于 niftyplayer 的可编写脚本的 mp3 播放器