术语
- 用户: 访客。
- 客户端: 安装在特定计算机上的特定于Web的软件。
了解会议
为了了解如何使会话安全,您必须首先了解会话的工作方式。
让我们看一下这段代码:
session_start();
调用后,PHP将查找名为
PHPSESSID(默认情况下)的cookie 。如果找不到,它将创建一个:
PHPSESSID=h8p6eoh3djplmnum2f696e4vq3
如果找到它,它将采用值,
PHPSESSID然后加载相应的会话。该值称为
session_id。
那是客户唯一会知道的。您添加到会话变量中的任何内容都将保留在服务器上,并且永远不会传输到客户端。如果您更改的内容,则该变量不会更改
$_SESSION。在您销毁它或超时之前,它始终保持不变。因此,尝试
$_SESSION通过散列或其他方式来混淆内容是没有用的,因为客户端从不接收或发送该信息。
然后,在新会话的情况下,您将设置变量:
$_SESSION['user'] = 'someuser';
客户将永远不会看到该信息。
问题
当恶意用户窃取
session_id其他用户的安全性时,可能会出现安全问题。如果没有某种检查,他将可以自由地模拟该用户。我们需要找到一种唯一标识客户端(而非用户)的方法。
一种策略(最有效)涉及检查启动会话的客户端的IP是否与使用会话的人的IP相同。
if(logging_in()) { $_SESSION['user'] = 'someuser'; $_SESSION['ip'] = $_SERVER['REMOTE_ADDR'];}// The Check on subsequent loadif($_SESSION['ip'] != $_SERVER['REMOTE_ADDR']) { die('Session MAY have been hijacked');}该策略的问题在于,如果客户端使用负载平衡器,或者(在长时间会话中)用户具有动态IP,则会触发错误警报。
另一种策略涉及检查客户端的用户代理:
if(logging_in()) { $_SESSION['user'] = 'someuser'; $_SESSION['agent'] = $_SERVER['HTTP_USER_AGENT'];}// The Check on subsequent loadif($_SESSION['agent'] != $_SERVER['HTTP_USER_AGENT']) { die('Session MAY have been hijacked');}该策略的缺点是,如果客户端升级其浏览器或安装插件(某些插件已添加到用户代理),则用户代理字符串将更改并且将触发错误警报。
另一种策略是
session_id每5个请求轮换一次。这样一来,
session_id理论上停留的时间就不足以被劫持。
if(logging_in()) { $_SESSION['user'] = 'someuser'; $_SESSION['count'] = 5;}// The Check on subsequent loadif(($_SESSION['count'] -= 1) == 0) { session_regenerate_id(); $_SESSION['count'] = 5;}您可以根据需要组合所有这些策略,但同时也要组合不利因素。
不幸的是,没有解决方案是万无一失的。如果您
session_id受到侵害,那么您就已经做好了。以上策略只是权宜之计。



