检查 PHP 会话是不是已经开始
Posted
技术标签:
【中文标题】检查 PHP 会话是不是已经开始【英文标题】:Check if PHP session has already started检查 PHP 会话是否已经开始 【发布时间】:2011-09-09 03:11:54 【问题描述】:我有一个 php 文件,有时从已启动会话的页面调用,有时从未启动会话的页面调用。因此,当我在此脚本上有session_start()
时,有时会收到“会话已开始”的错误消息。为此,我写了以下几行:
if(!isset($_COOKIE["PHPSESSID"]))
session_start();
但这次我收到了这条警告信息:
注意:未定义变量:_SESSION
有没有更好的方法来检查会话是否已经开始?
如果我使用@session_start
,它会让事情正常工作并关闭警告吗?
【问题讨论】:
how do i check if session_start has been entered?的可能重复 另见 *** 的这个答案:***.com/questions/1545357/… 【参考方案1】:PHP >= 5.4.0 , PHP 7
版本的推荐方式if (session_status() === PHP_SESSION_NONE)
session_start();
参考:http://www.php.net/manual/en/function.session-status.php
对于 PHP
的版本if(session_id() == '')
session_start();
【讨论】:
我认为 PHP session_start();session_write_close();: 的代码,则 if 条件失败但我们没有打开会话... @Nicolo Martini 据我了解:脚本退出时以session_start()
开头的会话将关闭,或者在脚本退出之前调用session_write_closed()
时关闭。 IE。当数据写入会话 cookie 并且会话被解锁以供另一个也调用“session_start”的脚本访问时,会话关闭。因此,CLOSING 并不意味着会话被销毁。您可以通过退出当前脚本或调用session_write_close()
来关闭会话,也可以通过调用session_start()
再次打开它。至少我的理解。
这仍然是开始会话的好方法吗?因为在链接中没有与此答案相关的内容
@csandreas1 您将从链接中看到 session_status 的描述及其预期的返回值。你的问题的答案是肯定的!
我在某些情况下失败了 - 我使用 if(!isset($_SESSION)) 成功【参考方案2】:
对于 PHP 5.4.0 之前的 PHP 版本:
if(session_id() == '')
// session isn't started
不过,恕我直言,如果您不知道会话是否已启动,您真的应该考虑重构会话管理代码...
也就是说,我的意见是主观的,并且在某些情况下(示例在下面的 cmets 中进行了描述)可能无法知道会话是否已启动。
【讨论】:
不知道你的会话是否开始并不一定是坏事。如果您是延迟加载(仅在第一次需要时才开始会话),那么您的答案中的测试会非常好。 另外,在某些环境中,apache 设置了会话自动启动 测试 session_id() 是否在包含文件中返回空字符串的示例: 关于重构会话管理的评论如果你不知道它是否是 tarted 的话并不真正相关。例如,如果将高级功能编码到 WordPress 主题中,您将永远不会知道插件是否已经开始使用会话而不进行检查。编码世界并不总是那么黑白:P 嗯,确实不错。我承认我的 cmets 非常主观 - 我会修改我的答案以反映这一点。【参考方案3】:PHP 5.4 引入了session_status(),比依赖session_id()
更可靠。
考虑以下 sn-p:
session_id('test');
var_export(session_id() != ''); // true, but session is still not started!
var_export(session_status() == PHP_SESSION_ACTIVE); // false
所以,要检查会话是否启动,现在 PHP 5.4 中推荐的方法是:
session_status() == PHP_SESSION_ACTIVE
【讨论】:
在可用时使用 session_status 而在不可用时使用旧方法的代码 sn-p 在这里似乎是完美的顺便说一句,提示提示 :) 感谢本杰明的更新。很高兴知道从 PHP 5.4 开始可以使用新方法。 这是一种更好的检查方式,您并不总是知道您是否启动了会话,尤其是当用户在浏览网站的过程中清除 cookie 时...我总是为 2 岁的孩子编写代码,你永远不知道用户会做什么;-) 至于我自己,我有一个小的 Config.php 文件,我的所有脚本都会调用它来设置变量和其他信息,所以只需将其添加到该文件中始终确保会话在需要时启动【参考方案4】:你可以做到,而且非常简单。
if (!isset($_SESSION)) session_start();
【讨论】:
@zloctb:我想不出我会在什么情况下做$_SESSION=array();
,所以这个答案似乎还可以。
@halfer 查看 Ryan 的回答。如果session_destroy()
已经被调用,那么$_SESSION
仍然可以被设置。此外,在单元测试中,您可以直接设置$_SESSION
。但我赞成这一点,因为对于大多数实际情况,这个答案应该足够好(直到 PHP 5.3 再也见不到......)【参考方案5】:
if (version_compare(phpversion(), '5.4.0', '<'))
if(session_id() == '')
session_start();
else
if (session_status() == PHP_SESSION_NONE)
session_start();
【讨论】:
【参考方案6】:在 PHP 5.4 之前,除了设置全局标志之外,没有可靠的方法。
考虑:
var_dump($_SESSION); // null
session_start();
var_dump($_SESSION); // array
session_destroy();
var_dump($_SESSION); // array, but session isn't active.
或者:
session_id(); // returns empty string
session_start();
session_id(); // returns session hash
session_destroy();
session_id(); // returns empty string, ok, but then
session_id('foo'); // tell php the session id to use
session_id(); // returns 'foo', but no session is active.
因此,在 PHP 5.4 之前,您应该设置一个全局布尔值。
【讨论】:
【参考方案7】:适用于所有 php 版本
if ((function_exists('session_status')
&& session_status() !== PHP_SESSION_ACTIVE) || !session_id())
session_start();
【讨论】:
同理,if ((defined('PHP_SESSION_ACTIVE') && session_status() !== PHP_SESSION_ACTIVE) || !session_id())
【参考方案8】:
检查一下:
<?php
/**
* @return bool
*/
function is_session_started()
if ( php_sapi_name() !== 'cli' )
if ( version_compare(phpversion(), '5.4.0', '>=') )
return session_status() === PHP_SESSION_ACTIVE ? TRUE : FALSE;
else
return session_id() === '' ? FALSE : TRUE;
return FALSE;
// Example
if ( is_session_started() === FALSE ) session_start();
?>
来源http://php.net
【讨论】:
【参考方案9】:使用session_id(),如果没有设置则返回一个空字符串。比查$_COOKIE
更可靠。
if (strlen(session_id()) < 1)
session_start();
【讨论】:
【参考方案10】:if (session_id() === "") session_start();
希望对你有帮助!
【讨论】:
【参考方案11】:这应该适用于所有 PHP 版本。它确定 PHP 版本,然后检查会话是否基于 PHP 版本启动。然后,如果会话没有启动,它就会启动它。
function start_session()
if(version_compare(phpversion(), "5.4.0") != -1)
if (session_status() == PHP_SESSION_NONE)
session_start();
else
if(session_id() == '')
session_start();
【讨论】:
【参考方案12】:你唯一需要做的就是:
<?php
if(!isset($_SESSION))
session_start();
?>
【讨论】:
这是我多年来一直使用的。有人建议不要使用这个吗?当然,有时检查会话是否启动是件好事——在某些环境中,apache 设置了会话自动启动、延迟加载(仅在第一次需要时启动会话)或者只是有时需要快速破解跨度> 上面的回答是一样的 (@miyuru)【参考方案13】:不确定这种解决方案的效率,但这是来自工作项目 如果您需要定义默认语言,这也可以使用
/**
* Start session
* Fall back to ukrainian language
*/
function valid_session()
if(session_id()=='')
session_start();
$_SESSION['lang']='uk';
$_SESSION['lang_id']=3;
return true;
【讨论】:
【参考方案14】:@
在函数调用之前抑制函数调用期间可能报告的任何错误。
在session_start
之前添加@
告诉PHP 避免打印错误消息。
例如:
在您已经向浏览器打印某些内容后使用session_start()
会导致错误,因此 PHP 将显示类似“无法发送标头:从(第 12 行)开始”之类的内容,@session_start()
在这种情况下仍然会失败,但屏幕上没有打印错误信息。
在包含文件或重定向到新页面之前使用exit()
函数,否则会报错。
此代码可用于所有情况:
<?php
if (session_status() !== PHP_SESSION_ACTIVE || session_id() === "")
session_start();
?>
【讨论】:
【参考方案15】:在 PHP 5.3 上这对我有用:
if(!strlen(session_id()))
session_name('someSpecialName');
session_start();
那么你有。如果您不将 not at if 语句开头,会话将以任何方式开始,我不知道为什么。
【讨论】:
【参考方案16】:响应基于@Meliza Ramos 响应(见第一个响应)和http://php.net/manual/en/function.phpversion.php,
动作:
如果不存在则定义 PHP_VERSION_ID 定义基于PHP_VERSION_ID检查版本的函数 将函数定义为安全的 openSession()只使用 openSession()
// PHP_VERSION_ID is available as of PHP 5.2.7, if our
// version is lower than that, then emulate it
if (!defined('PHP_VERSION_ID'))
$version = explode('.', PHP_VERSION);
define('PHP_VERSION_ID', ($version[0] * 10000 + $version[1] * 100 + $version[2]));
// PHP_VERSION_ID is defined as a number, where the higher the number
// is, the newer a PHP version is used. It's defined as used in the above
// expression:
//
// $version_id = $major_version * 10000 + $minor_version * 100 + $release_version;
//
// Now with PHP_VERSION_ID we can check for features this PHP version
// may have, this doesn't require to use version_compare() everytime
// you check if the current PHP version may not support a feature.
//
// For example, we may here define the PHP_VERSION_* constants thats
// not available in versions prior to 5.2.7
if (PHP_VERSION_ID < 50207)
define('PHP_MAJOR_VERSION', $version[0]);
define('PHP_MINOR_VERSION', $version[1]);
define('PHP_RELEASE_VERSION', $version[2]);
// and so on, ...
function phpVersionAtLeast($strVersion = '0.0.0')
$version = explode('.', $strVersion);
$questionVer = $version[0] * 10000 + $version[1] * 100 + $version[2];
if(PHP_VERSION_ID >= $questionVer)
return true;
else
return false;
function openSession()
if(phpVersionAtLeast('5.4.0'))
if(session_status()==PHP_SESSION_NONE)
session_start();
else // under 5.4.0
if(session_id() == '')
session_start();
【讨论】:
【参考方案17】:if (version_compare(PHP_VERSION, "5.4.0") >= 0)
$sess = session_status();
if ($sess == PHP_SESSION_NONE)
session_start();
else
if (!$_SESSION)
session_start();
其实,既然已经解决了,现在在这里解释已经太迟了。 这是我的一个项目的 .inc 文件,您可以在其中通过选择菜肴并删除/添加或更改订单来为餐厅配置菜单。 我工作的服务器没有实际版本,所以我让它更灵活。这取决于作者是否愿意使用并尝试一下。
【讨论】:
【参考方案18】:这段代码 sn-p 适合你吗?
if (!count($_SESSION)>0)
session_start();
【讨论】:
【参考方案19】:这是我用来确定会话是否已开始的。通过使用empty和isset如下:
if (empty($_SESSION) && !isset($_SESSION))
session_start();
【讨论】:
这个答案与 2013 年的任何答案都没有什么不同。【参考方案20】:您应该重新组织您的代码,以便在每次执行页面时只调用一次session_start()
。
【讨论】:
在某些情况下可能不希望每次执行页面只调用一次。 如果您要终止会话以重新创建它,那么当然可以,但这是一种特殊情况。一般来说,应用程序的代码应该在一开始就运行一次,这就是 session_start() 的所在。 例如,一个应用程序将会话存储在一个文件中,并且需要加载2个并发的慢速数据请求,这些请求都不需要会话,但是一个会阻塞另一个,因为 session_start 锁定了会话文件。 没错。 @YuriKolovsky 是对的。亚历克斯的问题很中肯,因为这些情况可能会发生,而且并不少见。 -1,大多数网站都是 CMS 驱动的,并且有主题和插件之类的东西,通常由不同的各方编写,永远不知道彼此的代码是否已启动会话。这只是一个代码组织问题的暗示是错误的。【参考方案21】:PHP_VERSION_ID 自 PHP 5.2.7 起可用,因此请先检查此内容,如有必要,请创建它。
session_status
自 PHP 5.4 起可用,所以我们也必须检查一下:
if (!defined('PHP_VERSION_ID'))
$version = explode('.', PHP_VERSION);
define('PHP_VERSION_ID', ($version[0] * 10000 + $version[1] * 100 + $version[2]));
else
$version = PHP_VERSION_ID;
if($version < 50400)
if(session_id() == '')
session_start();
else
if (session_status() !== PHP_SESSION_ACTIVE)
session_start();
【讨论】:
【参考方案22】:根据我的实践,在访问$_SESSION[]
之前,您需要每次调用session_start
才能使用该脚本。手册见以下链接。
http://php.net/manual/en/function.session-start.php
至少对我来说,session_start
是一个令人困惑的名字。 session_load
可以更清楚。
【讨论】:
【参考方案23】:我最终对状态进行了双重检查。 php 5.4+
if(session_status() !== PHP_SESSION_ACTIVE)session_start();;
if(session_status() !== PHP_SESSION_ACTIVE)die('session start failed');;
【讨论】:
【参考方案24】:session_start();
if(!empty($_SESSION['user']))
//code;
else
header("location:index.php");
【讨论】:
【参考方案25】:您可以使用以下解决方案来检查 PHP 会话是否已经开始:
if(session_id()== '')
echo"Session isn't Start";
else
echo"Session Started";
【讨论】:
有效答案更详细。【参考方案26】:将session_start();
替换为:
if (!isset($a))
a = False;
if ($a == TRUE)
session_start();
$a = TRUE;
【讨论】:
它包含代码错误,并且只有在同一个文件被包含多次时才有效,但如果在闭包中则无效。以上是关于检查 PHP 会话是不是已经开始的主要内容,如果未能解决你的问题,请参考以下文章