在我解释这个问题之前,我知道使用eval的风险,但是对于我的系统构建方式没有其他方法可以做到,而且它也只适用于个人项目。 (它是一个自定义的cms,当我发布它为我制作物理文件时,我只是通过db创建它所以我不需要在不工作远程时上传文件而且它很简单。)
让我解释一下我的问题,我有一个处理所有页面的主要php文件,所有页面都存储在带有代码的数据库中,并且正在通过eval执行。 并且该系统还有一个函数include_db,它基本上与来自db的php normaly包含相同。
但是当我访问第一个eval(主页面)中定义的变量时,它无法从db中包含的eval中读出。 奇怪的是,通过第二个评估可以读出函数。
是否可以从主页eval中生成的包含eval中正常访问变量? (我认为必须这样做,因为这些变量不是全局的,而是在函数中执行,但我不知道如何使每个变量都是全局的:()
提前致谢!
主页上正在评估的代码:
$skill = isset($_REQUEST['skill']) && is_string($_REQUEST['skill']) && isValidSkill($_REQUEST['skill']) ? $_REQUEST['skill'] : 'overall';
if(!isset($_REQUEST['player']))
include_db('highscore_overview');
else
include_db('highscore_player');
在概述的包含中,我转储了get_defined_vars()并且不返回我设置的$技能,只包括在主index.php(数据库等)中声明的变量
答案 0 :(得分:1)
首先是免责声明:您永远不应该从数据库执行代码。这是一个很大的安全风险。这意味着只要有人成功获得对数据库的访问权限(例如使用sql-injection),现在还可以通过更改数据库中的代码来执行php中的任意代码。 你真的不应该这样做!
如果您使用数据库中的代码来实现自定义(电子邮件)模板,请考虑使用模板引擎,例如twig。模板引擎的大多数语法都是以一种你无法突破它们并使用原始php代码执行任意代码的方式构建的。
那就是说,我现在试着回答原来的问题(因为我不能阻止你做你不应该做的事情)。就变量范围而言,eval的行为类似于函数。如果您希望在其中定义的变量是全局变量,则必须手动在eval global中定义每个变量。
你可以通过在eval中执行的每个代码附加一个代码片段来实现这一点,该代码获取每个本地(在eval中定义的)变量并将其写入全局范围。
<?php
function include_db() {
# ... get $code from db here ...
# get's executed after code from db, globalizes all variables
$code .= ';foreach (get_defined_vars()) as $newGlobalName) {';
$code .= ' $GLOBALS[$newGlobalName] = $$newGlobalName;';
$code .= '}';
eval($code);
}