2

在PHP中苦苦掙扎。 我關注增長看完這部之後更大: https://www.youtube.com/watch?v=RlfLCWKxHJ0PHP MVC數字萬用表使用路由器,控制器和模型的實用實例

根據毀滅之王我的路由器類應該只知道請求URI來加載適當的Controller類。但是我的Conroller應該知道應該使用哪個Model類和一個View類來呈現數據。或者更好,控制器應該知道ModelFactory將使用選定的數據存儲來處理對象創建。

這一切都打破LoD給我。

所以我的問題是:

  1. 如何路由器應該初始化控制器類,不知道這 參數需要?即使它是DI容器,我們也不知道 要傳遞給Router內部構造函數的對象參數。如果我們將DI容器傳遞給路由器構造函數(或任何其他類),我們將返回到服務定位器。這應該怎麼做?

也許這是完全錯誤的,但我的出發點是:

// ... retrieve settings, available languages, start session,... 

$router  = new Router($settings); 
$router->loadController(); 

Router.php

class Router 
{ 
    public function __construct(Settings $settings) 
    { 
     $this->settings = $settings; 
    } 

    // some other methods 

    public function loadController() 
    { 
     try 
     { 
      // Loading controller 
      $controller = $this->getController(); 

      if (is_callable(array($controller, $this->method)) == false) 
       $this->method = 'init'; 

      // Running controller 
      $controller->{$this->method}(); 
     } 
     catch (Exception $e) 
     { 
     $e->displayMessage(); 
     } 
    } 
} 

而且從這裏我可以做什麼我的控制器類裏面,因爲我需要撥打新模型,新視圖並且必須在構造函數或方法內部明確地執行,這是不好的。

更多的問題:

  • 如何,我應該得到模型類的實例在控制器?我應該使用靜態方法來加載視圖?
  • 回答

    1

    首先,模型是一個圖層,而不是一個特定的類。控制器本身將啓動必要的類以開始處理應用程序的業務邏輯。

    看看這些答案。第二屆有這些類是如何被稱爲一些例子...

    How should a model be structured in MVC?

    Properly calling the database from Model in an MVC application?

    其次,路由器只路由請求的URL到一個特定的控制器和視圖。有不同的方法可以做到這一點,但是我的路由器根據現有資源地圖匹配進行檢查。基於其他一些事情,它將返回頁面的成功「資源」名稱,未找到頁面的資源名稱或重定向資源等。

    某些基本代碼來自引導程序以供說明..

    //snip 
    
    $routeLoader = new \Routing\RouteLoader(); 
    $match = $routeLoader->getMatchedRoute($request['pageName']); 
    
    $router = new \Routing\Router($request); 
    $resource = $router->getResource($match); 
    
    //snip 
    
    $viewName  = '\View\\' . $resource . 'View'; 
    $controllerName = '\Controller\\' . $resource . 'Controller'; 
    
    $view = new $viewName(); 
    $controller = new $controllerName($view, $request); 
    $controller->{$router->getCommand()}(); 
    
    $view->response(); 
    

    所以,要直接回答你的問題..

    1)不要在路由器類中啓動控制器和視圖。在自舉中做。

    此外,對於Web應用程序,您可能需要也可能不需要DI,服務工廠,甚至需要使用特定的設計模式。對於大多數人來說,我認爲它的過度殺傷並增加了不必要的複雜性

    2)控制器將啓動類來開始處理業務邏輯(如果它的甚至是必要的。)

    ADDITIONAL

    要添加的數據庫連接到上述和其注入控制器,下面是1種方式..

    $DCM = new \Database\DatabaseConnectionManager(new \Config\DatabaseConfig()); 
    $AppCache = new \Cache\AppCache(); 
    $DAM = new \DataAccess\DataAccessManager($AppCache, $DCM); 
    

    在上面的代碼中,DataAccessManager對象將負責檢索先從緩存中獲取數據,然後再從數據庫獲取數據。這$ DAM對象現在可以注入到控制器,像這樣......

    $controller = new $controllerName($DAM, $view, $request); 
    

    而是連接到數據庫中的引導和繞過應用程序的連接,我喜歡使用DataAccessManager,這將僅在實際需要時才進行連接。一旦需要,PDO對象(或其他)被啓動並存儲在要檢索的對象中,並在必要時再次使用。如果需要,我也可以連接到其他數據庫..

    // method from DataAccessManager class 
    
    private function connectToDatabase($server = 'slave') 
    { 
        if (!array_key_exists($server, $this->dbObject)) { 
         // use the DataConnectionManager to connect and store the connection here 
         $this->dbObject[$server] = $this->DCM->connect($server); 
        } 
    
        return $this->dbObject[$server]; 
    } 
    
    +0

    這是一個很好的例子,正是我想到的。但是,這並沒有給我一個關於如何將模型注入控制器的答案。或者,也許,我只是過於複雜,並且只需要使用新的ModelClass()。在我的特殊情況下,我需要幾個模型在控制器中實例化。此外,我試圖實現數據傳輸層,所以我需要一種動態注入依賴關係的方式。再一次,我會嘗試將它全部移到引導程序,但它不適用於幾個模型類。 – 2015-02-20 17:11:51

    +0

    在上述解決方案中,您不會。 「模型」類一般將在控制器中啓動。爲了動態注入任何類,您可能需要使用一個好的DI容器。但是,一個異常可能是您的數據庫連接。我會添加更多的答案來說明.. – user2430012 2015-02-21 11:38:58

    相關問題