自研 PHP 框架 1.1_模板引擎

模板引擎

这一说明文档,主要用来说明如何从0开始引入第三方库,并在自己的项目中正常使用。

1.1 版本中,我使用的 smarty 模板引擎,并没有什么特别的理由(就像 1.0 文档中所说,很多设计只是开发的灵光一闪,并没有那么多的为什么)

决策流程

当确定了自己需要模板引擎之后,我是如何查找信息并作出决策,最重要的问题是,实践操作是如何做的。

我看过很多的书籍、文档和博客,其中很多作者给我的感觉很像高中时听数学老师讲课。

顺着老师的思路走你觉得这个问题很简单,但是当自己来做的时候,你会发现很多的细节问题,完全无从下手。

其中的原因在于,老师在讲解时,很多分叉口(比如,某个问题需要套用哪个公式)并没有给你指出来,因为在他看来这是如此简单,简单到是一个不需要思考的问题,所以很多细节直接被跳过。当我们自己接手的时候,每一个分叉口都是一个巨大的难题,往往会不知所措,实践的难度比期望值大太多,结果就是失败或者放弃。

所以,我希望提供更详尽的信息(日志级别的思考记录),不仅仅只是流程,还会掺杂大量的思考,大量的操作细节。

下面列举的是我的解决步骤:

  1. Google,PHP template engine
    会看到一篇 Top7 的文章,点进去,浏览了一遍,随便选了一个排第二的 smarty

  2. Packagist.org 查找 smarty
    packagist.org 搜索 samrty 就会找到相关信息,按照说明安装即可(按照说明安装,这样说法就是省略细节的说明,很像老师说的 就用这个公式就可以了)。
    这里可能存在两个问题:

    • 1.全英文,看不懂。

      chrome浏览器支持翻译,这算是个解决办法。终极办法,还是要开始学英语,这是必经之路,如果想变得更好的话。

    • 2.composer是啥

      简单的说,叫包管理工具,关键字都告诉你了,使用搜索引擎吧。
      这里吐槽下很多人的信息查找能力,最最最最最显著的一点,有问题不知道先百度一下么?!
      虽然,百度可能百度不出来你想要的东西,但是解决问题的步骤应该是这么一个步骤,最起码自己先查一下,找不到再问吧。百度的正确用法,或者说搜索引擎的正确用法的前提是,你要知道关键词,直白点说你要知道你要找的是什么东西,关键词有了,答案距你也就不远了(后续涉及到额外知识的部分,会提供关键词)。

  3. 在IDE中的项目根目录下打开终端,使用 composer 命令安装
    可能存在如下几个问题:

    • 什么是IDE?
    • 项目根目录下打开终端怎么搞?

      根据你使用的IDE不同,也有不同的方式,终极方法直接命令行到项目根目录,windows下就是cmd。

    • composer命令安装如何使用?

      使用 composer require xxxx,这样使用的前提条件是:1.有安装 composer;2.PATH路径中包含了 composer

  4. 如何使用安装的第三方库
    使用 composer 安装完成之后,会在根目录下创建一个 vendor 文件夹,所有通过 composer 安装的第三库都会统一放置在这里。

这里复习一下 1.0 版本中曾经提及过的,每一次请求最终 PHP 引擎其实只执行了一个文件 index.php,框架的作用只是将一个超级大文件,分解成了各个部分,最终还是要组装在一起,对外就是单个文件 index.php

一个类或者方法如果要被使用,先得被定义。

也就是说,第三库如果要使用,我们就必须在使用之前加载到 index.php 中(使用 include 或者 require),这里有一个位置问题,1.1 版本中放置在这里:

<?php
...
// 加载第三方库文件
include(VENDOR.'autoload.php');

$class_name = $obj->get('controller');
$func = $obj->get('func');

$namesapce = 'app.dmin.ontroller.'.$class_name;
//这里是我们业务逻辑,也就是 APP 文件夹下的文件
$app = new $namesapce;
$app->$func();

很显然,第三方库文件如果放到业务逻辑之后肯定行不通。

而且,这里的加载方式也显得很简单 inlcude(VENDOR.'autoload.php') ,简单的一行就解决了第三方库的加载问题,按照我们之前的方式,每一个文件都要 includerequire,这里很自然会有一个问题:

为什么到这里只要加载一个文件就可以?

是因为只有一个文件吗?很显然不是,单 smarty 一个库就有几十上百个文件,更别说其他的依赖库了,这里如何解决的呢?

这里引入一个知识点,自动加载。完成了前面的加载步骤,接下来我们就需要进行实际使用

以前没用过 smarty 模板引擎,该怎么办?

最有效的方法不是百度,而是去看官方文档,官方文档都会有指导手册,指导你如何使用,当然了,又是全英文。

比如说 smarty 模板引擎如何使用,可以看这里 smarty引擎官方使用手册,知道了模板要如何写,我们继续往下。

在方法中如何使用?

<?php
/**
 * 使用 smarty 模板引擎
 */
public function html_smarty()
{
    $smarty = new .marty();
    return $smarty->display(VIEW.'index/html_smarty.tpl');
}

上述的示例只是一个简单的 demo,只是用来跑通业务,不需要复杂的逻辑。(这里说一下,当学习一个新东西时,弄懂流程和原理最重要,不需要太多、太复杂的逻辑,逻辑说到底只是对工具的组合使用)

下面详细介绍,我是如何知道要这么写,以及为什么要这么写。

我是如何知道要怎么写的

因为我是第一次使用,根本就不知道要创建一个什么名字(也就是这里的 smarty)的对象,有人可能连要创建对象都不知道,更别说要使用 display 方法来生成 html 文件了。

那我是如何知道的呢?

如果你是用 IDE 阅读(推荐这样阅读)的,顺着这个路径 vendor/smarty/smarty/demo/index.php 打开这个文件,你就知道要怎么写了(毕竟别人都给了你示例,照着写总归是可以的)。

如果没有 demo 文件可供你参考,README.md 就必须要看了,可以从中找到如何使用或者教你如何使用的教程。

下面要说明的是为什么写成 new .marty(),而不是 new Smarty()。这个需要结合命名空间来看。

首先,smarty 库中的文件本身是没有使用命名空间的,这就意味着其被加载到 index.php 之后,就相当于我们在根域中定义的类,加之 html.php 我们使用了命名空间 app.dmin.ontroller,这导致 html.php 文件本身在 app.dmin.ontroller 这个域中(参看命名空间,里面有详细说明),如果使用 new Smarty(),系统会自动给其加上前缀,实际使用时就变成了这样 new app.dmin.ontroller.marty(),前面我们说过,smarty 库文件其实被加载到了根域下,这样就找不到指定的文件。

这里因为 smarty 库本身没有使用命名空间,如果使用命名空间那又该如何使用呢?

回到根目录下 index.php 的加载过程,如果第三方库使用了命名空间,加载之后的第三库文件并不在根域中,而是在第三方库使用的命名空间的指定域(假设为 namespace smarty; ,方便演示说明)中。

那么在控制器文件中使用时有下面两种写法

<?php
...
//不使用 use
public function html_smarty()
{
    $smarty = new smarty.marty();
    ...
}

<?php
...
//使用use
use smarty.marty;
public function html_smarty()
{
    $smarty = new Smarty();
    ...
}

请仔细比较两者之间的区别,如果没有使用 use 那么就需要给解析引擎指明完整的路径,也就是 smarty.marty(),如果使用了 use,在解析引擎的眼中,new Smarty()new smarty.marty() 是等价的,也就是前面不使用 use 所展示出来的样子,这样比较之后,可以很明显的看出,use 其实起到的就是一个简化的作用,推而广之,任何支持别名的语言,别名所起到的作用也是为了简化,为了使用更方便,无需过度关注如何实现这种细节。

PS:本系列文章最佳阅读方式,IDE + 本地运行环境,IDE 中阅读可配合 demo 运行增进理解,GitHub 地址

本作品采用《CC 协议》,转载必须注明作者和本文链接
城里的野山参
讨论数量: 3

请问, smarty 解决了什么问题呢 ?你又用过多长时间的 smarty 呢,为什么模板引擎要作为框架的一部分呢,不用不行么。

1年前 评论
城里的野山参 (楼主) 1年前
dvaknheo (作者) 1年前

这个点看起来好不舒服

1年前 评论

@NiZerin 能否具体点,想要什么样的

1年前 评论

讨论应以学习和精进为目的。请勿发布不友善或者负能量的内容,与人为善,比聪明更重要!