微信公众号搜"智元新知"关注
微信扫一扫可直接关注哦!

php – 包含或eval的自定义流包装?

概观

我正在编写一个模板引擎.它甚至支持多种“格式”.目前它可以解析.PHP文件和.tpl(特定于此引擎).

我会给你一个例子,只是给你一个想法.

的template.PHP

Name: <?PHP echo $this->h($name) ?>
Posts: 
<?PHP foreach($posts as $post): ?>
    - <?PHP echo $this->h($post->name) ?> (<?PHP echo count($post->comments) ?> comments)
      <?PHP echo $this->render('post/shortpost',array('post' => $post)) ?>
<?PHP endforeach ?>

这基本上只是一个标准的PHP.

template.tpl

Name: {>$name}
Posts: 
{foreach($posts as $post):}
    - {>$post->name} ({=count($post->comments)} comments)
      {=:render('post/shortpost',array('post' => $post))}
{endforeach}

这个模板化的“语言”简单地被翻译成PHP.

作仪,

的eval()

目前这些模板是使用eval()解析的.

>我不必更改任何代码

反对

>当一个模板发生错误时,你只会得到一个没有用的错误信息
告诉你在哪个文件发生错误,有时行号甚至是错误的.
>安全?模板文件只需要可读取?
>很难调试代码.
>代码更难理解
>更多..?

stream包装和include()

我最近在PHP中阅读了关于流包装器.你甚至可以创建自己的.另一个解决方案不是eval,而是为每个模板“格式”创建一个自定义流包装,并使用include来解析模板.

这有以下(潜在)缺陷:

>可能会解决错误消息中显示错误文件/行号的问题(有没有经验?)
>您可以处理模板文件,确切地说要如何处理.完全控制.

反对

> allow_url_(fopen | include)必须打开?
这是慢吗? (是eval()慢吗?)
>安全无益. include的做法基本上和eval一样.
>更多…?

编辑:缓存解析文件和include()

第三个选项是将模板解析为PHP代码并缓存它们(如@ Jen-YaKovalev所建议的).

>包括缓存

反对

>如果在包含渲染的模板并发生错误时发生错误
错误消息不会指向您正确的文件/最终显示
行号错误
>您需要一个额外的tmp /目录来保存解析的文件.你需要写
PHP / webserver的权限.会更加不安全,因为黑客
会附加一些恶意代码更容易.

编辑:流过滤器和include(‘PHP:// filter’)

最近发现以下PHP.net页面

> PHP:// filter:http://php.net/manual/en/wrappers.php.php
> strea_filter_register http://fr2.php.net/manual/en/function.stream-filter-register.php

这将是解决这个问题的另一种可能性.使用include(‘PHP://filter/read=filtername/resource=file.PHP’),我可以包括一个文件,它将在执行之前先通过过滤器filtername.

>不需要像流包装器那么多的代码

反对

>没有像流包装器那么多的可能性(缓存?)
>安全性
>速度?

>使用流包装器解析模板文件或类似的经验?
>还有其他解决方案吗?
有更多的亲和矛盾吗?
>你会推荐哪一个

我认为这只是一种编码风格的味道,最好是投票或者一些东西.

>我个人认为eval是邪恶的(每种语言),
>包含PHP包装器(甚至是集成的*)有不好的经验,
>知道所有大(gish)模板系统使用编译到PHP文件(smarty,twig),这是我会使用的.

(*)在早期的项目中,我们在data-url包装中使用了一行代码(一个空类扩展),其性能非常糟糕.

版权声明:本文内容由互联网用户自发贡献,该文观点与技术仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 dio@foxmail.com 举报,一经查实,本站将立刻删除。

相关推荐