PHP仿tp實現mvc架構基本設計思路與實現方法

來源:互聯網
上載者:User
這篇文章主要介紹了PHP仿tp實現mvc架構基本設計思路與實現方法,簡單講述了php實現tp架構的原理,並結合執行個體形式分析了相關控制器、視圖及URL訪問操作技巧與注意事項,需要的朋友可以參考下

本文執行個體講述了PHP仿tp實現mvc架構基本設計思路與實現方法。分享給大家供大家參考,具體如下:

仿tp mvc基本設計與簡單實現

一:檔案載入常識

變數 常量 函數 類
檔案載入的函數或者使用命名空間:require(); require_once(); include(); include_once();
常量:define("DEFINE",""); const constant = "value";
函數:function fun(){} // global 使用全域變數 局部變數不被外部調用。
類:

<?phpclass A{  public $a = 10;  public function aa(){  // 不能使用一個a是因為,new A 之後 方法a會被自動執行,所以方法名不可以和類名衝突。    echo $this->a; // 輸出屬性.  }  public function __construct(){ // 構造方法,執行個體化後自動執行,    echo $this->bb(); // 調用方法。  }  public function bb(){    echo "我是bb";  }}$a = new A;$a->aa();class B extends A{ // 繼承 A ,類A是類B的父級。繼承public的,}$b = new B;$b->aa(); // 可以輸出類A裡面的屬性。

原廠模式參閱:http://www.jb51.net/article/140658.htm

//-----------------------------原廠模式-------------------------//class A{  public $class;   // public $class = $_GET['c']; //類名  public $method; // public $method = $_GET['m']; //方法  public function __construct($class,$method){    // 或者通過 $_SERVER['PATH_INFO']; 轉換得到類名或者方法名(下面講解)。    $this->class = ucfirst(strtolower($class)).'Controller'; //對類名進行安全處理,並加上控制器尾碼    $this->method = strtolower($method);   //對方法名進行安全處理    $this->work($this->class,$this->method);  }  public function work($class,$method){    // 把檔案命名成 (類名.class.php的形式),就可以通過類名找到檔案。    //include '檔案名稱(檔案在別的地方)';    #例如 include './index.php'; 引入檔案然後執行個體化類。    $c = new $class;  //執行個體化類    $c->$method();  //訪問類的方法  }}

至此我們可以通過url的 $_GET 參數來解決

例如:http://mvc.com/index.php?h=home&v=Index&c=index.html

h為前後台,v為控制器,c為模板。

$v = $_GET['v'];$c = rtrim($_GET['c'],".html");new A($v,$c); // 根據繼承關係再次負載檔案。// extract($arr);  //extract 的作用:從數組中將變數匯入到當前的符號表,鍵做變數,值做值!// compact(); // — 建立一個數組,包括變數名和它們的值// assign display 實現參閱:http://www.jb51.net/article/140661.htm

class Controller{  public $array;  public $key;  public $val;  public function assign($key,$val){    if(array($val)){      $this->array["$key"] = $val;    }else{      $this->array["$key"] = compact($val);    }  }  public function display($tpl = ''){ // 模板為空白自動載入。    $this->assign($this->key,$this->val);    extract($this->array);    // 如果模板為空白就在這雷根據get參數添加或者通過 $_SERVER['PATH_INFO']; 轉換得到。(下面講解)    if(file_exists($tpl)){ //模板存在就負載檔案。      include $tpl;    }  }}//繼承總model。這個model名字和控制器model的名字是一樣的。繼承方法同Controller,總model必須需要加上一個return。資料處理的indexmodel可以加return,也可以不加。class IndexModel extends Model{  public function index(){    // 資料處理。    // 需要返回資料就加上return。  }}class IndexController extends Controller{ // 繼承  public function index(){    $m = Model("index");    echo '執行個體化後的index方法<br>';    $this->assign('m',$m); // 分配資料。    $this->display('index.html'); // 模板  }}

mvc雖然實現但是不夠人性化,因為每次都要加上get參數,變得很冗長,解決的關鍵在於$_SERVER['PATH_INFO'];

用這個替換掉h m v三個參數。

1. 當輸入url為:http://mvc.com/index.php/home/index/index.html
這種情況下 index.php 斜線後面的apache會自動認為是一個路徑。
$_SERVER['PATH_INFO'] = /home/index/index.html
第1個斜線 /home 前後台
第2個斜線 /index 控制器
第3個斜線 /index.html 模板檔案
如果後面加有參數例如:?a=18&b=38 他不會被加到$_SERVER['PATH_INFO']裡面。$_POST 或者 $_GET 也不會加入$_SERVER['PATH_INFO']裡面的內容,這樣就可以讓控制參數和資料的參數互不衝突。

2. U 方法的實現。重新改寫$_SERVER['PATH_INFO'] 參數,改變為一個資料。array( 'home', 'Index', 'index');

每次進入入口檔案index.php都把他的PHP_INFO參數轉換為數組,在控制器或者其他的地方只要調用這個參數就行了。

// 這裡如果做了大小寫轉換,總控制器裡面就不用了。function bca(){  $arr = explode('/',ltrim($_SERVER['PATH_INFO'],'/'));  if(count($arr) == 3){    $arr[0] = strtolower($arr[0]);    $arr[1] = ucfirst(strtolower($arr[1]));    // 判斷尾碼是不是 .html    if(substr($arr[2],-5,strlen($arr[2])) == '.html'){      $a = explode('.',$arr['2']);      $arr[2] = strtolower($a[0]);    }else{      $arr[2] = strtolower($arr[2]);    }    $_SERVER['PATH_INFO'] = $arr;  }}// url方法做控制器或前背景跳轉。第三個參數是輸出還是return。預設是直接輸出。function U($string = '',$method = '',$bool = true){ // true 是直接輸出或者返回,  // 擷取系統變數。  $path_info = $_SERVER['PATH_INFO'];  $script_name = $_SERVER['SCRIPT_NAME'];  // 判斷中間有沒有 / 以確定參數個數。  if(strpos($string,'/')){    $arr = explode('/',$string);    if(count($arr) == 2){  // 兩個參數的情況。      $arr[0] = ucfirst(strtolower($arr[0]));      $arr[1] = strtolower($arr[1]);      $url = "/{$path_info[0]}/{$arr[0]}/{$arr[1]}.html";    }else if(count($arr) == 3){ // 三個參數的情況。      $arr[0] = strtolower($arr[0]);      $arr[1] = ucfirst(strtolower($arr[1]));      $arr[2] = strtolower($arr[2]);      $url = "/{$arr[0]}/{$arr[1]}/{$arr[2]}.html";    }  }else{    $arr = strtolower($string); // 一個參數的情況。    $url = "/{$path_info[0]}/{$path_info[1]}/{$arr}.html";  }  // url 路徑的拼接。  if($method != ''){    $u = $script_name.$url.'?'.$method;    if($bool == true){     echo $u;    }else{     return $u;   }  }else{    $u = $script_name.$url;    if($bool == true){     echo $u;    }else{     return $u;   }  }}

3. url重寫,去掉 index.php

開啟apache設定檔重寫模組,LoadModule rewrite_module modules/mod_rewrite.so

根下加入的改寫檔案 .htaccess

內容:

<IfModule mod_rewrite.c> Options +FollowSymlinks RewriteEngine On RewriteCond %{REQUEST_FILENAME} !-d RewriteCond %{REQUEST_FILENAME} !-f RewriteRule ^(.*)$ index.php/$1 [QSA,PT,L]</IfModule>

在瀏覽器輸入url:http://mvc.com/home/index/index.html?a=19b=38
[REDIRECT_STATUS] => 200 重寫狀態ok。

發現 $_SERVER['REDIRECT_URL'];$_SERVER['PATH_INFO']; 參數相同。所以參數後面就可以去掉index.php這安全的問題。

4. 模板替換(思路)

我們會發現有一個我們書寫的模板,裡面有 {$arr} <include file="" /> 等,我們把模板檔案讀取後通過正則還有字串把他轉換成正常的php檔案。對檔案名稱加密後放到替換後的檔案夾下,每次url訪問的時候查看是否有快取檔案,判斷最後修改時間等驗證,

5. 資料緩衝(思路)

json_encode() json_decode() file_get_contents() file_put_contents(); unserialize(); serialize(); 等存文檔案裡面或者memcache redis 等儲存。

聯繫我們

該頁面正文內容均來源於網絡整理,並不代表阿里雲官方的觀點,該頁面所提到的產品和服務也與阿里云無關,如果該頁面內容對您造成了困擾,歡迎寫郵件給我們,收到郵件我們將在5個工作日內處理。

如果您發現本社區中有涉嫌抄襲的內容,歡迎發送郵件至: info-contact@alibabacloud.com 進行舉報並提供相關證據,工作人員會在 5 個工作天內聯絡您,一經查實,本站將立刻刪除涉嫌侵權內容。

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.