用户login时需要在php会话中存储什么内容?

目前当用户login时,我创build了2个会话。

$_SESSION['logged_in'] = 1; $_SESSION['username'] = $username; // user's name 

所以,那些需要login的页面,我只是这样做:

 if(isset($_SESSION['logged_id'])){ // Do whatever I want } 

有没有安全漏洞? 我的意思是,打破我的会议很容易? 人们如何攻击会议? 我该如何预防呢?

编辑:

刚刚发现这个:

http://www.xrvel.com/post/353/programming/make-a-secure-session-login-script

http://net.tutsplus.com/tutorials/php/secure-your-forms-with-form-keys/

刚刚find链接,那些方法够好? 请给出你的意见。 我还没有得到最好的答案。

术语

  • 用户:访客。
  • 客户端:在特定机器上安装特定的支持networking的软件。

了解会话

为了了解如何确保会话安全,您必须先了解会话的工作方式。

让我们看看这段代码:

 session_start(); 

只要你打电话,PHP会寻找一个名为PHPSESSID的cookie(默认)。 如果找不到,就会创build一个:

 PHPSESSID=h8p6eoh3djplmnum2f696e4vq3 

如果find,则取PHPSESSID的值,然后加载相应的会话。 该值被称为session_id

这是客户唯一知道的事情。 无论你添加到会话variables保留在服务器上,也不会传输到客户端。 如果更改$_SESSION的内容,该variables不会更改。 它总是保持不变,直到你摧毁它或超时。 因此,尝试通过哈希或其他方式来混淆$_SESSION的内容是没有用的,因为客户永远不会收到或发送该信息。

然后,在新会话的情况下,您将设置variables:

 $_SESSION['user'] = 'someuser'; 

客户永远不会看到这些信息。


问题

恶意用户盗取其他用户的session_id时可能会出现安全问题。 如果没有进行某种检查,他就可以自由冒充该用户。 我们需要find唯一标识客户端(而不是用户)的方法。

一种策略(最有效的)涉及检查开始会话的客户的IP是否与使用会话的人的IP相同。

 if(logging_in()) { $_SESSION['user'] = 'someuser'; $_SESSION['ip'] = $_SERVER['REMOTE_ADDR']; } // The Check on subsequent load if($_SESSION['ip'] != $_SERVER['REMOTE_ADDR']) { die('Session MAY have been hijacked'); } 

这种策略的问题是,如果客户端使用负载平衡器,或者(长时间会话)用户有一个dynamicIP,它将触发虚假警报。

另一个策略是检查客户端的用户代理:

 if(logging_in()) { $_SESSION['user'] = 'someuser'; $_SESSION['agent'] = $_SERVER['HTTP_USER_AGENT']; } // The Check on subsequent load if($_SESSION['agent'] != $_SERVER['HTTP_USER_AGENT']) { die('Session MAY have been hijacked'); } 

该策略的缺点是,如果客户端升级它的浏览器或安装一个插件(一些添加到用户代理),用户代理string将会改变,并会触发虚假警报。

另一个策略是在每个请求上轮换session_id 。 那样的话, session_id理论上就不会长久被劫持。

 if(logging_in()) { $_SESSION['user'] = 'someuser'; $_SESSION['count'] = 5; } // The Check on subsequent load if(($_SESSION['count'] -= 1) == 0) { session_regenerate_id(); $_SESSION['count'] = 5; } 

你可以按照你的意愿把这些策略结合起来,但是你也可以把缺点结合起来。

不幸的是,没有解决scheme是不错的。 如果你的session_id被攻破了,你已经完成了。 以上策略只是权宜之计。

这是荒唐的。

当(通常是通过跨站点脚本攻击)某人拦截了sessionId(这是一个由浏览器自动发送到Web服务器的cookie)时,就会发生会话劫持。

有人发布了这个例子:

所以当用户login时:

//不是最安全的哈希! $ _SESSION ['checksum'] = md5($ _ SESSION ['username']。$ salt);

进入敏感区域之前:

if(md5($ _ SESSION ['username']。$ salt)!= $ _SESSION ['checksum']){
handleSessionError(); }

让我们看看这个有什么问题

  1. 盐 – 没有错,但毫无意义。 没有人正在破坏你该死的md5,谁在乎它是否被盐渍
  2. 将SESSIONvariables的md5与SESSION中存储的相同variables的md5进行比较 – 您正在比较会话与会话。 如果东西被劫持,这将无能为力。
 $_SESSION['logged_in'] = 1; $_SESSION['username'] = $username; // user's name $_SESSION['hash'] = md5($YOUR_SALT.$username.$_SERVER['HTTP_USER_AGENT']); 

/ /用户名称散列,以避免操纵

避免被谁操纵? 神奇的会话? 您的会话variables将不会被修改,除非您的服务器受到威胁。 散列只是为了将你的string很好地压缩成一个48个字符的string(用户代理可以有点长)。

至less我们现在正在检查一些客户端数据,而不是检查SESSION到SESSION数据,他们检查了HTTP_USER_AGENT(这是一个标识浏览器的string),这可能足以保护你,但你必须意识到如果这个人已经在某个方面已经采用了sessionId,那么你也有可能向坏人服务器发送了一个请求,并将这个坏人给了你的用户代理,这样一个聪明的黑客就会欺骗你的用户代理并破坏这个保护。

你到底是哪一个可悲的事实?

只要你的会话ID被泄露,你就走了。 您可以检查请求的远程地址,并确保在所有请求中都保持不变(如我所做的那样),并且对于99%的客户端来说,这是完美的。 然后有一天,你会得到一个使用负载均衡代理服务器的用户的呼叫,请求将通过一组不同的IP(有时甚至在错误的networking)从这里出来,他会失去他的会议左右中心。

你可以在这里find关于会话安全的指南。

您可以存储IP地址,浏览器签名等以识别用户。 在每个请求,检查它与当前值,看看是否有任何可疑的事情发生。

请注意,有些人使用绝对dynamicIP地址的提供商,所以这些人可能会经常注销。

我想第二个需要'logged_in'?

有关会话安全的一些资源:

phpsec

shiflett

你可以通过javascript(XSS-> crossside scripting attack)来窃取会话。你应该总是使用一个盐腌的 MD5 Hash来保护你的会话。

为了避免会话劫持,您应该放置用户代理

$ _ SERVER [ 'HTTP_USER_AGENT']

进入哈希以及。

在你的例子中:

 $_SESSION['logged_in'] = 1; $_SESSION['username'] = $username; // user's name $_SESSION['hash'] = md5($YOUR_SALT.$username.$_SERVER['HTTP_USER_AGENT']); // user's name hashed to avoid manipulation 

在使用会话之前,请确保它使用正确的散列:

 if (!$_SESSION['hash']==md5($YOUR_SALT.$username.$_SERVER['HTTP_USER_AGENT'])){ die ('session hash not corrected') } 

为了防止会话固定,这基本上是猜测SID或使用各种方法窃取它。 不pipe你的会话逻辑有多复杂,它在一定程度上肯定会受到偷偷摸摸的攻击。 这就是为什么你每次做重要事情都必须重新生成ID。 例如,如果您要发布post或更改pipe理员中的设置,请首先运行session-regenerate-id。 那么黑客必须经历再次黑客攻击的过程。 这基本上给黑客一次一个身份证,一直在浪费他的时间。

http://us.php.net/manual/en/function.session-regenerate-id.php

或者你可以每轮都改变一次

if($ _ SESSION ['counter'] == 3){session_regenerate_id(); $ _ SESSION ['counter'] == 0}

另外,$ _SERVER ['HTTP_USER_AGENT']不是很可靠。 尽量避免它,不仅因为这个原因,而且因为它对黑客很方便,他们知道代理被广泛用于此。 而是尝试使用$ _SESSION ['id_token'] = sha1(一些疯狂的信息,如文件内存,文件名,时间)。

这是通常的login代码,可以进行一些改进,使其更难以破解。 首先,您可以使用用户名和login时间或预定义的string(或盐)进行校验和,并将其存储在会话中,然后进行比较。

所以当用户login时:

 // not the most secure hash! $_SESSION['checksum'] = md5($_SESSION['username'].$salt); 

进入敏感区域之前:

 if (md5($_SESSION['username'].$salt) != $_SESSION['checksum']) { handleSessionError(); } 

默认情况下,会话通常作为文件存储在服务器端,并在用户的浏览器上放置一个cookie来logging要引用的文件。 谈到会话黑客攻击,黑客以某种方式检索足够的信息来复制login或通过使用来自cookie的信息设法更改会话数据。

您可以使用数据库编写自己的会话处理以增加安全性。 一些更严格的CMS,如Joomla,也loggingIP。 但是,这对使用某些ISP的人造成了问题

当我在构buildSugarCRM的时候遇到这个问题的时候,我跟踪并validation了用户的IP地址(除了一些其他的东西)。 我只比较了IP地址的前三个部分。 这允许大部分本地variablesIP地址。 我也可以closuresIP地址的主要变化是常见的安装的IP地址validation。 我认为只有比较IP地址的开头才能帮助您提高安全性,而不会对您的应用程序增加如此严重的限制。

例如:“###。###。### .—”只有标有'#'的IP地址部分才会被validation。

192.168.1.101
192.168.1.102
192.168.1.XXX

都被认为是平等的。

雅各