首页 > 解决方案 > 如何在 PHP 中配置基于会话的超时选项?

问题描述

我有一个基于 PHP 的内部 Web 应用程序,我为它创建了一个简单的登录系统,并且正在使用 session_start() 来初始化 $_SESSION 对象并检查 Web 目录中的其他页面(如果用户已登录)。如果没有给出标准的 403 如果是这样加载页面。

现在我们设置网页的方式是一个标准一致的首页,它承载登录,以及用于访问其他页面的导航菜单。此首页的正文及其所有内容是使用 POST/API 选项来指示要显示哪个页面的更改,例如:www.example.com/frontPage.php ?page=someOtherWebpage

在 frontPage.php 页面上,我创建了一个会话并允许用户在加载适当的 frontPage 正文内容之前登录。在 $_POST 和 $_SESSION 之间,我可以访问必要的信息来决定是否允许用户访问 Web 目录的各个部分。

现在这是我不确定我是否正确执行此操作的地方。为了保持安全完整性,root 中的每个单独的网页也都有一个 session_start(),所以它可以拉 $_SESSION 并检查我声明的名为“LOGGED”的变量是真还是假。如果为 false、403 等。这样做是为了如果没有登录但以某种方式访问​​或知道其中某些网页的直接 URL 的人,他们不登录就无法访问它。这对我来说是正确的解决方案,现在它的工作原理就像我尝试直接导航到我的 web 目录中的任何给定页面而不登录我得到 403。可能有更好或更标准化的方式来做到这一点,我当然愿意接受建议,一种更“标准化”的方式可能是我最终要描述的问题的解决方案。

当用户登录时,我们没有准确计时,但在 15-45 分钟之间他们必须再次登录。在 frontPage.php 上,我尝试将 cookie_lifetime 设置为以秒为单位的一天(86400),我还检查了我的 php.ini 文件中的这些设置:

oci8.persistent_timeout - 为了允许空闲的持久连接,我们将其设置为 -1 以表示永远

session.cookie_lifetime - cookie 生命周期的默认服务器配置当前设置为 0,直到浏览器重新启动。

session.gc_maxlifetime - 当存储的数据被认为是垃圾并被清理时,垃圾收集的最大生命周期(这是我希望我需要进行更改的地方,但我对垃圾清理不够熟悉,不知道这如何与 cookie 及其生命周期交互)它目前设置为 1440 或 24 分钟,因此这属于预期的时间范围

gc_maxlifetime 是我希望增加的配置选项,以防止有人因不活动而被踢吗?还是我们设置会话的方式存在固有问题?还是我没有考虑/不知道的其他原因或选择?

如果对某人的回答很重要,我们使用 LDAP 登录与我们的本地 AD 服务器通信并检查用户、通行证和 AD 组。

我感谢任何人可以提供的任何答案。

谢谢你。

标签: php

解决方案


通常会话应该是短暂的(默认为 30 分钟)。您在会话生命周期较长时往往面临的问题是它们容易受到冲突的影响。特别是在有很多会话的繁忙服务器上。PHP 没有针对会话冲突的保护。可以通过简单的 DoS 攻击来利用此问题,例如卷曲您网站上的任何页面,从而在循环中生成会话。如果他们可以用足够的会话淹没您的会话存储,则它们会增加冲突的可能性,从而获得一个已经处于活动状态的会话。PHP 不会验证是否随机生成的会话 id。因此,如果session_start()碰巧生成了与现有会话 ID 相同的会话 ID,它将向用户返回一个已经存在的会话 ID,从而授予他们访问该会话数据的权限。

还存在会话固定问题的可能性,其中用户可以获得不重新验证幂等数据的会话。您可以使用session_create_id()PHP 7.1 来帮助防止此类漏洞。

session_create_id()用于为当前会话创建新的会话 ID。它返回无冲突会话 ID。

如果会话未激活,则忽略冲突检查。

会话 ID 是根据 php.ini 设置创建的。

为 GC 任务脚本使用与 Web 服务器相同的用户 ID 很重要。否则,您可能会遇到权限问题,尤其是文件保存处理程序。

虽然没有针对碰撞攻击的保护措施。只是缓解。所以通常的想法是保持gc.max_lifetime相当低,并考虑到这也会影响诸如针对垃圾收集问题的 DoS 攻击之类的事情,这在 PHP 中在默认文件会话保存处理程序中非常糟糕。


推荐阅读