runphp 是 DedeCMS 模板引擎一个非常强大且核心的功能,它允许你在模板文件(通常是 .htm 文件)中直接嵌入 PHP 代码,从而实现复杂的逻辑判断、数据处理和动态内容生成。

runphp 的基本语法
runphp 主要通过两个核心的底层函数实现:GetOnePara() 和 array()
{dede:field name='phpcode' function='GetOnePara(@me, "code")' /}
这是最常用、最标准的 runphp 写法。
{dede:field ...}: 这是 DedeCMS 的字段调用标签。name='phpcode': 这里phpcode是一个虚拟字段名,它本身并不存在于数据库中,我们只是借用这个标签的结构来承载我们的 PHP 代码。function='GetOnePara(@me, "code")': 这是关键部分。function: 指定要对字段值执行的函数。GetOnePara(): 这是 DedeCMS 的一个底层函数,用于处理@me变量并返回结果。@me: 这是一个特殊的变量,代表当前字段的原始值,在这个例子里,因为我们用的是虚拟字段,@me初始值为空 。"code": 这是传递给GetOnePara函数的第二个参数,它告诉函数,我们接下来要执行的是一段 PHP 代码。
代码块如何写?
紧跟在标签后面的 phpcode 字段值,就是你想要执行的 PHP 代码。注意:这里的代码块必须使用双引号 包裹。
示例:

{dede:field name='phpcode' function='GetOnePara(@me, "
$a = 10;
$b = 20;
$c = $a + $b;
echo $c;
")' /}
输出结果:
30
{dede:array name='phpcode'} ... {/dede:array}
这种写法适用于需要执行多行 PHP 代码,并且希望代码块结构更清晰的情况,它会把 PHP 代码块作为 array 标签的内容。
语法结构:
{dede:array name='phpcode'}
// 你的 PHP 代码写在这里
{/dede:array}
示例:

{dede:array name='phpcode'}
$str = "Hello, DedeCMS!";
$str .= " This is a test.";
echo $str;
{/dede:array}
输出结果:
Hello, DedeCMS! This is a test.
runphp 的核心应用场景
runphp 的真正威力在于处理数据,尤其是在列表页和内容页中。
场景1:列表页 - 处理文章摘要/描述
字段 description 存储的是一段长文本,我们想在列表页只显示前 50 个字符,并在末尾加上 "..."。
不使用 runphp 的做法(笨拙): 需要在后台手动截取,或者修改程序。
使用 runphp 的做法(灵活):
在列表模板 list_articel.htm 中:
[field:description function='GetOnePara(@me, "
if(strlen(@me) > 50){
@me = cn_substr(@me, 50) . '...';
}
")'/]
代码解析:
@me:@me代表当前文章的description字段的原始值。strlen(@me): 获取摘要的长度。cn_substr(@me, 50): 这是 DedeCMS 提供的函数,用于安全地截取中文字符串,避免乱码,它比 PHP 原生的substr更适合处理中文。@me = ...: 将处理后的结果重新赋值给@me,DedeCMS 会输出@me的最终值。
场景2:内容页 - 动态生成文章链接
假设你的文章有不同的类型,存放在不同的栏目,并且它们的链接规则不同。
- 普通文章:
/a/2025/123.html - 产品文章:
/products/123.html
我们可以通过文章的一个自定义字段(typeid)来判断。
模板 article_articel.htm 中:**
假设我们有一个自定义字段 linktype,值为 1 表示普通文章,值为 2 表示产品文章。
{dede:field name='phpcode' function='GetOnePara(@me, "
$linktype = @me; // 先获取当前文章的linktype值
$aid = @me; // 注意:在内容页,@me默认是文章ID,所以这里可以直接用
if($linktype == 1){
@me = '/a/'.date('Ym', @me).$aid.'.html';
} elseif($linktype == 2){
@me = '/products/'.$aid.'.html';
} else {
@me = '/a/'.$aid.'.html'; // 默认链接
}
")'/}
注意: 上面这个例子是一个简化的逻辑,在实际内容页中,获取文章ID和栏目ID有更规范的方式,{dede:field.id/} 和 {dede:fieldtypeid/},这个例子只是为了演示 runphp 的条件判断能力。
场景3:内容页 - 处理时间格式
默认的时间格式可能不满足需求,比如想显示为 "2025年10月27日 星期五"。 模板中:**
发布时间:{dede:field name='pubdate' function='GetOnePara(@me, "
@me = date('Y年m月d日 星期w', @me);
$week = array('日','一','二','三','四','五','六');
@me = str_replace('星期w', '星期'.$week[date('w', @me)], @me);
")'/}
更简单的写法(推荐):
DedeCMS 已经内置了 MyDate 函数来处理日期格式,runphp 不是最佳选择,除非有更复杂的逻辑,但如果要用 runphp,上面的代码是可行的。
runphp 中可用的函数和变量
在 runphp 代码块中,你可以使用:
- PHP 原生函数:如
strlen(),substr(),explode(),array()等。 - DedeCMS 全局函数:
cn_substr($string, $length): 安全截取中文字符串。MyDate($format, $timestamp): 格式化日期时间。GetMkTime($dtime): 将日期字符串转为时间戳。- 等等。
- DedeCMS 全局变量:
@me: 当前字段的值。$cfg_系列变量: 如$cfg_cmspath(CMS路径),$cfg_indexurl(首页URL) 等。$dsql: DedeCMS 的数据库操作对象,可以直接用来查询数据库(不推荐在模板中直接查询,性能差)。
重要注意事项与最佳实践
-
性能问题:
- 避免在循环中执行复杂查询:
runphp会在模板渲染时执行,如果你在列表页的{dede:list}循环里对每篇文章都执行一次runphp,runphp内部有数据库查询,这会导致页面加载极慢,因为 N 次循环就会执行 N 次数据库查询。 - 替代方案:对于需要额外数据的情况,最佳实践是在PHP 程序文件(如
include/inc_arcpart_view.php)中通过Join查询一次性获取所有需要的数据,然后将处理好的数据通过ParseTempletsFirst()等方法赋值给模板变量,这样只需要一次数据库查询。
- 避免在循环中执行复杂查询:
-
安全性问题:
runphp是一个“后门”,因为它允许在模板中执行任意 PHP 代码。- 不要在面向公众的模板系统中过度使用,特别是如果网站允许用户上传或修改模板。
- 在管理后台,默认情况下
runphp可能是关闭的,你需要开启它:进入 系统 -> 系统基本参数 -> 核心设置,找到 “模板引擎禁用标签”,确保里面没有php,如果禁用了php,runphp也将无法工作。
-
代码可读性:
- 对于非常复杂的逻辑,
runphp会让模板文件变得难以阅读和维护。 - 遵循“模板只负责展示,逻辑交给程序”的原则,如果逻辑过于复杂,应该考虑修改程序文件,而不是把所有逻辑都塞进模板里。
- 对于非常复杂的逻辑,
-
调试:
runphp中的 PHP 代码出错时,错误信息可能不会直接显示在页面上,或者被 DedeCMS 的错误处理机制吞掉。- 调试技巧:使用
echo或print_r来输出中间变量,看看代码执行到哪一步,变量的值是什么。 echo "Debug: Here!";或者print_r($my_array);
runphp 是 DedeCMS 提供给开发者的一个“瑞士军刀”,它极大地增强了模板的灵活性。
- 优点:快速实现简单的逻辑处理,无需修改程序文件,对非程序员友好。
- 缺点:可能影响性能,降低代码可维护性,存在安全风险。
最佳实践建议:
- 多用:用于简单的字符串处理、条件判断、格式化。
- 慎用:避免在循环中进行数据库查询。
- 少用:将复杂的业务逻辑留给 PHP 程序文件。
掌握 runphp 能让你在修改和定制 DedeCMS 网站时事半功倍。
