Z-Blog 主题里读自定义字段,Metas 老是取不到值
主题里想给文章加个「阅读时长」字段,后台填了,前台死活读不出来。我一开始以为是字段没存进去,翻数据库才发现数据好好躺在 metacms 表里。 问题在读取方式上。 先确认 Metas 到底挂在哪个对象上 Z-Blog 的自定义字段是跟着 P
主题里想给文章加个「阅读时长」字段,后台填了,前台死活读不出来。我一开始以为是字段没存进去,翻数据库才发现数据好好躺在 metacms 表里。
问题在读取方式上。
先确认 Metas 到底挂在哪个对象上
Z-Blog 的自定义字段是跟着 Post 走的,键名大小写敏感这件事其实还好,真正坑的是取值时机。模板里这样写:
{$article.Metas.readtime}
如果 $article 是从列表页循环出来的对象,是能拿到的。但如果是在 template/post-single.php 里通过 $zbp->GetPostByID() 之类自己又查了一遍,得到的对象可能没带 Metas——具体带不带,我没法给你打包票,不同版本有差异。
保险的写法是显式调 Metas->Get():
{/* post-single.php */}
{php}
$readtime = $article->Metas->Get( 'readtime' );
{/php}
{ if $readtime }
{ $readtime } 分钟
{ /if }
注意 { 和变量之间加空格,不然有些编辑器的语法高亮会抽搐。功能上不加也行。
Metas 没注册的键,Get 返回空字符串
这点挺关键。Metas->Get() 对不存在的键不抛错,安安静静返回 ''。所以如果你后台其实没填过这个字段,你永远不知道是代码错了还是数据空了。
排查时先打印整个数组:
{php}
var_dump( $article->Metas->GetData() );
{/php}
能看到键名列表就说明对象是对的,列表里没有你要的键就说明根本没写进去——那个就是保存逻辑的问题了,跟模板无关。
想让主题在后台有个输入框
手工去数据库插字段当然也行,但我一般给主题挂个钩子,在文章编辑页下面加个自定义表单。用的钩子是 Filter_Plugin_Admin_ArticleMng_SubMenu(这个是后台菜单位置的,加表单区更常用的是编辑页的扩展点,名字我记不太准,建议先 list_hooks 查一遍再动手)。
表单提交后顺手把值塞进 Metas:
$article->Metas->readtime = (int) $readtime;
$article->Save();
这里 Metas->xxx = ... 这种直接赋值是能用的,因为 Metas 类实现了魔术方法。但如果你写 $article->Metas['readtime'],我就不确定了,没试过数组访问方式。
最后一句提醒:改完主题文件记得清缓存,Z-Blog 会编译模板,不清的话你会对着旧版本代码调试半天。这事儿我上个月刚干过。