PHP 5.3.3 - 在子目录中运行session_start()会杀死现有会话

时间:2011-11-20 06:41:45

标签: php session

自从我的webhost升级到PHP 5.3.3之后,我一直在尝试追踪一些讨厌的会话问题。我已确定如果存在活动会话,则从子目录调用session_start()会终止现有会话。例如,我启动一个会话,用户登录到domain.com/index.php,然后用户导航到domain.com/members/,它会触发start_session()...用户的会话丢失。

我为此挖了一下,找不到类似的东西。是否存在可以解释此行为的PHP配置?

6 个答案:

答案 0 :(得分:3)

使用该版本的PHP多次调用session_start()不会导致任何问题,但是还有其他可能的原因。

一种可能的解释是客户端的浏览器没有将会话ID发送回服务器。您可以通过比较两个页面生成的会话ID来测试它。假设您有一个可以正确测试的受控环境,您可以使用session_id()来获取会话。

也可能是用户正在点击其他网络服务器。由于(默认情况下)PHP将会话存储到磁盘,因此多个服务器无法共享会话信息。如果这是一个共享主机,那么这可能不太可能。但是,您可以使用phpinfo()对此进行测试。它应该为您提供足够的信息来确定它是否是相同的服务器。对于多服务器系统,我会考虑在memcache或mysql中存储会话。

答案 1 :(得分:2)

如果您的会话在同一目录中正常运行(从您的问题中不清楚),则存在这种行为的唯一可能原因,非常明显的一个:“目录”cookie参数。
它似乎设置为有些不寻常的值,而不是默认的“/”为会话cookie参数 你必须检查出来。

无论如何,在没有 HTTP交换日志的情况下尝试任何会话/ cookie相关问题几乎没用。 你必须使用一些HTTP嗅探器,比如LiveHTTPHeaders Firefox插件,看看服务器发送了什么cookie头,客户端返回了哪一个。 否则一切都将在黑暗中拍摄。


好的,从您的yonder评论看来,会话ID保持不变,因此,没有HTTP问题可能是原因。这个问题变得有点棘手。 你能在这里发布你的测试脚本吗?

答案 2 :(得分:0)

  

是否存在可以解释此行为的PHP配置?

是的,如果会话数据的存储在这些调用之间有所不同,则$_SESSION内容也会有所不同。可以配置存储,有关会话的所有配置选项,请参阅http://php.net/manual/en/session.configuration.php

如果PHP无法读取会话存储,那么您将获得一个空数组。

我不能告诉你这是否是你的问题的问题,但可能它有用。

BTW,调用session_start()而不是空$_SESSION通常表示已创建新会话。如果您为会话使用Cookie并输出headers_listDocs

,则可以验证这一点
echo '<pre>', var_dump(headers_list());

如果它包含会话的新cookie,则会使用此请求创建会话。

答案 3 :(得分:0)

这里有很多好的建议。感谢大家。我花了很多时间在周末挖掘这个并且无法直接解决它。我最终向我的webhost演示了这个问题发生在他的两个托管站点上,并且不会发生在PHP的默认安装中。为了解决这个问题,我最终将所有的登录和会话逻辑都移到了一个类中。

答案 4 :(得分:0)

我花了很长时间搜索,尝试,测试看起来像是同样的问题。谷歌一直把我送到这里,我认为分享解决方案可能有助于其他人(虽然我在2011年的问题上发帖很奇怪):

/bar.php中设置的会话变量未在/foo/foobar.php中设置。

当我终于发现http://www.example.com/bar.php中的链接指向http://example.com/foo/foobar.php(缺少www)时,它意识到该问题与文件夹/子文件夹无关。

更正html链接中的URL解决了问题。没有时间深入挖掘,我能弄清楚的是(在我的配置中) Apache没有任何区别,并且在有www和没有example.com的情况下无关紧要地提供页面,而PHP没有在它认为是两个不同的域www.example.com和{{1}}之间共享会话。

答案 5 :(得分:0)

想要分享另一个答案,在此SO中找到: Session variables not accessible in subdirectory clayRay 回答。

我的回答是我有一个习惯&#34; php.ini&#34;保存在根目录中的文件,将这些指令移动到ini_set()次调用解决了它。如果您的主持人允许,您也可以将其推到.htaccess