【问题标题】:Where do I start when writing a new scripting "language"?编写新的脚本“语言”时从哪里开始?
【发布时间】:2011-04-13 00:45:43
【问题描述】:

我需要编写一个在 PHP 下运行的基本脚本/模板引擎。理想情况下,我将能够将我自己的标记语言与 (X)HTML 模板混合,并通过服务器端解析器运行文档,以使用数据库提供的 (X)HTML 动态替换我自己的标记。

不幸的是,就我对 PHP 和脚本的所有知识而言,我不太确定从哪里开始。我的第一直觉是通过某种正则表达式解析器运行整个文档,并将我的自定义标记映射到特定的 PHP 函数……但这对我来说似乎有点慢和笨拙。

存在哪些资源/教程/示例可以为我指明正确的方向?相比之下,我真的很喜欢用于 .NET MVC 的新 Razor 模板引擎......我不想在 PHP 项目中完全取消它,但构建类似的东西会很棒。


更新

好的,让我进一步完善我的解释……我为 WordPress 开发网站。我的很多客户都想定制他们的网站,但每当我开始谈论 PHP 时都会逃跑。这是一种脚本语言,看起来太复杂了,外行用户甚至都不想感兴趣。

我想做的是专门为 WordPress 创建自己的标记形式。因此,与其在主题文件中使用 PHP 函数调用(get_header()get_footer()if(has_posts())...),不如使用命名空间 XML(<wpml:header /><wpml:footer /><wpml:loop> ... </wpml:loop>)转换为同一件事情。将模板文件与服务器端脚本分开会做得更好(有几个主题将整个 PHP 函数直接放在主题的 PHP 模板文件中!!!)并且会使非开发人员更容易开始工作使用自定义 WordPress 主题。

考虑到这一点,TWIG 和 Mackrell 已经建议的解决方案肯定支持在文件中嵌入脚本“块”的想法,但它们并不能真正帮助我将自定义 XML/XHTML 标记解析为可识别的东西服务器端代码。

那么...在构建新的服务器端标记处理器时我应该从哪里开始?

【问题讨论】:

  • ...但是 PHP 一个“基本的脚本/模板引擎”。为什么要重新发明轮子?只需使用正则表达式从源代码中去除不允许的结构并 eval() 它。
  • Twig 没有“嵌入脚本块”,它正是您正在寻找的:一种模板语言。如果您不想使用 vanilla PHP,请不要费心编写自己的 PHP(如果以前已经编写过)。我用过它,在其中创建自己的语法非常容易。
  • @user257493 这有点极端。我正在尝试为非 PHP 开发人员开发一些东西。任何了解 PHP 的人仍然可以使用 PHP。任何不了解 PHP(并且无意学习 PHP)的人都可以使用替代语法。

标签: php xml templates scripting markup


【解决方案1】:

我会从 XML 开始,先定义典型页面标记的外观,然后继续以您选择的语言解密 XML,然后使用它并创建 HTML。

xml 应该是一组描述您的特定语言的节点。

所以...

<MyPage>
  <MyElement id="myid" type="MyType1">
    <MyElement id="myid" type="MyType1" Text="Some text"/>
  </MyElement>
  etc...

我会在互联网上更仔细地查看是否已经有适合您需求的重新构建的东西,然后再开始这样的东西,它具有成为那些摆脱的东西之一的真正潜力控制和无法维护。

【讨论】:

  • 只要用 XML 编写新的 DSL,就会杀死一只小猫。
【解决方案2】:

听起来您需要一种支持自定义标记扩展的模板语言。鉴于 PHP 本身可以满足这种需求,我猜你也想要某种沙盒。

为此,我建议TWIG

默认情况下,它使用与 Python 的 Django 和 Jinja2 或 Ruby 的 Liquid 相同的基本语法(虽然不推荐,但这是可配置的),并且它被编译为缓存的 PHP 以提高速度。

它支持沙盒和参数自动转义以及块替换和继承,您可以选择它可以访问的变量,并且您可以设置任何您想要的默认和自定义令牌和过滤器组合。

Smarty 也可能满足您的需求,但我不确定它是否具有上述所有功能,在我看来,它的语法并不优雅,而且我被告知它比它的价值更痛苦。

无论你做什么,在发明你自己的模板语言之前,都要认真思考。从长远来看,这通常是一个巨大的痛苦,而且迟早会出现在 BobX 旁边的 The Daily WTF 上。

更新:我得到的印象是你痴迷于使用命名空间 XML 进行模板。是否真的值得重新发明整个模板引擎,以便您的用户可以使用&lt;wpml:header /&gt; 而不是{{header}}? TWIG 不允许用户嵌入任意脚本......只有您明确确定的变量和流控制结构。

【讨论】:

  • 如果你没有提到 smarty,我会给出 +1。 Twig 摇滚,Smarty 很烂,就是这样。
  • @nikic:我只是想公平对待我从未亲自使用过的包。在另一个答案中,我相信我说的是“......和 ​​Smarty,因为出于我不太清楚的原因,提及它显然是强制性的”。
  • @nikic:不赞成答案,因为根据您的主观判断,“Smarty 很烂”并不完全公平。 @ssokolow 甚至提到这不如 Smarty 好。 +1 给你,先生。
  • @musicfreak:如果我说什么,我通常有理由说出来。 Twig 在性能、安全性和功能方面胜过 Smarty。因此,我认为没有理由提及 Smarty。
  • @nikic:但是 +1 应该意味着“这个答案很有用”,所以拒绝 +1,因为只有一半的事情得到了你的认可,然后明确地告诉我这只会让你看起来幼稚和恶意。您的原始帖子只是说“Smarty 很烂”而不是“Twig 在性能、安全性和功能方面胜过 Smarty。因此我认为没有理由提及 Smarty”,这无济于事。 StackOverflow 足够大,您可以放心地假设您所说的一切都可能会形成某人对您的第一印象。
【解决方案3】:

另一种选择是将您的模板解析为 xml 文档并将其转换为另一个 xml 文档,并将您的自定义标签替换为其他标签(例如 &lt;?php 处理指令)。在这种情况下,XSL 就是您要查找的内容。

【讨论】:

    【解决方案4】:

    对于自定义 XML,您可以使用 PHP XML parser 最好使用 SAX 进行表演。

    Smarty 是一个非常优秀的 PHP 模板引擎,内置标签、块和函数。您可以扩展这些以创建自己的,甚至删除内置的(对于 Smarty 3)。

    如果您需要创建自己的脚本,我建议您检查 语言解析器,如 LexYacc。您必须以those SQLite images 之类的方式定义您的语言,但不是以图形方式,而是以文本方式。还有其他grammatical language parser 可用。我给出的那些是最古老和最著名的,但它是为 C++ 完成的。

    您可能希望自己避免这样做(例如使用 RegExp)。很快你的脚本中就会出现很多不一致的地方。尽管 RegExp 本身就是一种由自动化解释的语言。

    您可以将两者混合使用:XML 解析器和通用解析器。查看Finite-state machine (FSM)

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2011-01-11
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多