使用GET执行数据库操作的快速,简单且安全的方法

时间:2010-04-11 22:37:14

标签: php mysql post get

这里有一些方法/最佳实践问题,我确信已经解决,但我找不到基于我输入的模糊搜索词的解决方案。

我知道以“快速而简单”的方式开始提问可能会引起一些叹息,所以我道歉。

这是合约。

我有一个登录区域,其中ADMIN可以执行大量POST操作以输入与其配置文件相关的数据。我对数据结构的方式非常独特,并且在大多数表格中都有很好的细分,因为它与管理员的ID有关。

现在,我有一个表,我将一种类型的数据转储到其中,并通过为每条记录分配ADMIN的唯一ID来区分这些数据。换句话说,所有ADMIN都有这种类型的数据写入此表。我只是通过每个记录的ADMIN ID来区分。

计划让ADMIN通过点击带有查询字符串的链接来删除这些记录 - 显然是使用GET。显然,查询结构位于链接中,因此任何登录的管理员都可以利用该URL并删除竞争对手的记录。

是通过POST安全地执行此操作的唯一方法,还是应该通过包含密码的会话信息并根据请求删除的ADMIN ID对其进行验证?

这对我来说显然要多得多。

正如他们在我曾经工作过的汽车维修业中所说的那样,有三种方法可以做到:快速,良好,便宜。你一次只能有两个。快速便宜也不会好。好又便宜不会有快速转机。快速和好不会便宜。哈哈

我想这适用于此......一下子永远不会有快速,简单和安全;)

提前致谢...

3 个答案:

答案 0 :(得分:3)

作为一般规则,任何改变状态(无论是会话状态还是数据库状态)的操作都应该使用POST。这意味着您可以使用GET执行的唯一“安全”SQL操作是SELECT。即使您只使用后端管理员,也不应该使用get。想象一下,重新打开浏览器,发现上次关闭firefox时,你的'删除所有'GET->删除页面会导致所有内容再次被删除。

其中一个主要原因是阻止跨站点请求伪造。例如,如果您的网页采用了http://example.com/account?action=logout等GET变量,则攻击者可以在您的网站上发布图片,如下所示:

<img src="http://example.com/account?action=logout" />

任何打开包含该图片代码的网页的人都会立即退出,即使他们是管理员也是如此。然后在原始数据库中搜索该数据并将其删除会非常烦人。

虽然POST操作“几乎”容易伪造,但作为任何Web安全问题的一般规则,权衡是速度/简单性与安全性,因此您将不得不选择其中一个或另一个

答案 1 :(得分:2)

您应该设置某种会话。

就安全性而言,使用POST over GET使得你没有任何实际意义。 POST可以像GET一样伪造。

因此,假设您的管理员登录后,您在会话中获得了某种标识符,您只需利用它。

考虑与此类似的内容:

<?PHP
session_start();

if (empty ($_SESSION['admin_id'])) die("Log in, son.");

if (empty($_GET['record_id'])) die("You've got to tell me which record to delete!");

if (! is_numeric($_GET['record_id'])) die("Invalid record ID");

//just to be totally safe, even though we just enforced that it's numeric.
$record_id = mysql_real_escape_string($_GET['record_id']));

$sql = "DELETE FROM table WHERE record_id='{$record_id}' AND admin_id = {$_SESSION['admin_id']}";

mysql_query($sql);

echo "Record was deleted (assuming it was yours in the first place)";
?>

在该示例中,我们通过利用DELETE查询中的WHERE子句来避免“删除其他人的记录”问题。当然,为了更加用户友好,您需要先获取记录,然后将记录中的admin_id与$ _SESSION中的admin_id进行比较,如果它们不匹配,则抱怨,记录某些内容,抛出错误,等

HTH

答案 2 :(得分:0)

您说的是:“如果管理员123直接访问管理员321的网址,从而删除他的内容会怎样?”没有?

如果是这样,那么每个登录的管理员都应该至少有一个会话,该管理员具有一些唯一标识符。如果没有,他首先不应该在管理部分。你不能只是将URL中的标识符与会话中的标识符进行比较吗?

如果任何用户(而不仅仅是管理员)访问这些“删除我”网址,他应该被会话识别为该数据的原始“所有者”(管理员)。