php mvc及模板引擎
PHP MVC 及模板引擎 MVC, 引擎, 模板, PHPPHP MVC 及模板引擎 By 深空, 2009 年09 月16 日 23:00模板引擎,这四个字听起来很高深的样子,一般用到“引擎”两字都会感觉比较高级,类 似游戏3D 引擎、Zend 引擎等,其实都是唬人的,骗外行人的。所以在我初学 PHP 的那会, 也因为这四个字导致了我觉得很难而没有去看他到底是什么样一个东西,直到很长时间以后 使用 Smarty 才真正了解模板引擎的原理和作用。Smarty(), PHP 官方模板引擎,看名字给人感觉应该很快,其实很慢,即使他有预编译(另一个看起来 很高级的名词,同样也是唬人的,下面我会讲到这个)。[注:我刚才点开 Smarty 发现他说 他已经不是一个 PHP 子项目了,汗,看来确实唬人,哈玩笑^_^] 。其实在 PHP 里,模板 引擎扮演着 View(其实通俗说就是页面,看英文有时候会给人很高级的错觉)的角色,这是 一个很重要的角色,因为用户的交互啊,界面效果啊等等都在这里,这是最终用户看到的你 的系统的样子。开头就说模板引擎,只是跟大家说明一下这个东西其实没有什么难理解的,明白其原理 以后你会发现他是纸老虎,所以你要有信心你会很轻松看完此文。为了更好的说明模板引擎所扮演的角色,我不得不也谈谈 MVC。这个话题恐怕互联网 上谈及的很多,我也只能根据我的理解来描述,可能有不恰当的地方,欢迎讨论。通常的 MVC 是指 Model 、View 和 Controller。也就是模型、视图和控制器。我理解 MVC 也是 在学了 PHP 不短时间后了,当时请教老廖(),才恍然大悟。先来说说 Controller ,也就是控制器,控制器是个什么东西呢?在 PHP 里他是扮演一 个接收用户请求,把用户请求定位到指定数据模型的角色。解释起来感觉不是很好解释,来 看一个简单的留言本的例子: [php] //用户请求可能是 $module = $_GET[ module ]; switch ($module) {case list :require_once list.php ;break;case add :require_once add.php ;break;case del :require_once del.php ;break;default:require_once list.php ;break;} [/php]是不是看起来很简单好像没什么东西呀,只是根据用户的请求参数包含不同的文件而已。 没错,确实很容易,这个 switch 语句其实就一个最简单的控制器的实现。他控制什么?他 控制你根据不同的用户请求参数调用不同的数据模型处理用户请求。那么这里的 list 可能是 一个留言列表,add 是添加留言,del 是删除留言。Controller 的传统实现可以这么简单, 当然现在的很多技巧包括根据不同的用户请求包含不同的业务逻辑处理类,比如 list 自动定 位到/model/List.class.php 这样的一些技巧性操作等。再来说说 Model ,其实我们一般花比较长时间设计和编写的也是这块内容,也就是具 体的业务逻辑实现。比如一个留言列表要处理些什么,都是在这里实现。还是直接看一个 Model 例子比较直观: [php] //Guest_List.class.php class Guest_List {public $page = 1;public function __construct() {$this->db = DB::init($GLOBALS[ dsn ]);$this->page = (int) $_GET[ page ];}public function getList() {$begin = $this->page * 10;$sql = “SELECT * FROM guest ORDER BY addTime DESC LIMIT $begin, 10“;return $this->db->getAll($sql);} } [/php]这里的 Guest_List 就是一个简单的 Model 实现,构造函数取得页数 page 参数, getList 方法查询留言列表并返回结果集。那么在 list.php 里可能是这样调用的: //list.php require_once Guest_List.class.php ; $model = new Guest_List(); $lists = $model->getList();嗯,其实很多 MVC 框架都是这么实现的,只不过可能加了一些自动调用的机制,会根 据用户请求自动调用类,自动执行方法,呵呵。Model 大功告成。这里需要明确一点就是, Model 只是返回视图上所可能需要用到的数据,他不负责任何和显示有关的事情,那么显 示相关的就交给 View 来做了。我们是不是不知不觉已经把表现和业务逻辑分离了?没错, 分离就是这么简单。好了,来看看 View 怎么利用 Model 返回的数据来显示页面吧。最简单的例子,我们只需要在 list.php 里增加一行即可。 //list.php require_once Guest_List.class.php ; $model = new Guest_List(); $lists = $model->getList(); //上面是 Model,那么下面就是 View require_once list.html ;来看看 View 都做些什么吧,我们用 list.html 来表示留言列表所展现给用户的界面文 件,用 html 来命名看起来会更直观一些,他好像是个 html 文件,负责输出 html 代码给 浏览器。来看看 list.html 可能长什么样子: [php][/php]不难看出来这个文件所做的只不过是遍历留言数组$lists,然后输出每一行的留言,对 留言的内容处理做了 htmlspecialchars 和 date 转换(与显示相关的处理),除了和显示相 关的操作,他没有再做任何业务逻辑了(也不应该有) 。我发现写到这里真的没有什么好写的了,MVC 就是这些(或者再做一些扩展),至于怎 么做到表现和业务分离,那么就是在你的 Model 里只返回数据,也就是你 View 所需要用 到的数据,而你的 View 拿到这些数据后负责去显示他就可以了,不应该在你的 Model 里 做显示和视觉相关的操作,也不应该在你的 View 里做一些业务逻辑相关的操作,把这两者 分清楚,就自然而然的表现与业务分离了。接下来说说负责 View 的模板引擎吧,其实你在上面应该已经看到了一个最简陋的模板 引擎,那就是 View 部分的 require_once 语句。厄,实在是太简单了,模板引擎其实是 调度并解析模板的东西,其中调度模板由 require_once 搞定了,那么解析呢?这里由 PHP