【问题标题】:Why do we call session_start() before any other content in the web page?为什么我们在网页中的任何其他内容之前调用 session_start() ?
【发布时间】:2016-10-28 08:41:16
【问题描述】:

我想知道为什么我们在网页中的任何其他内容之前调用 session_start() ?

【问题讨论】:

  • 在该页面上使用SESSION

标签: php session web session-management


【解决方案1】:

让我试着描述一下,HTTP 协议是如何工作的。

来自浏览器的请求如下所示:

GET /somefolder/somescript.php HTTP/1.1
Host: www.yourhost.com
Connection: keep-alive
Cache-Control: max-age=0
Upgrade-Insecure-Requests: 1
User-Agent: Your_Useragent
Accept: text/html,application/xhtml+xml,application/xml;q=0.9,image/webp;q=0.8
Referer: http://testreferer.com/
Accept-Encoding: gzip, deflate, sdch, br
Accept-Language: ru-RU,ru;q=0.8,en-US;q=0.6,en;q=0.4,bg;q=0.2
Another-Header: Value1
Another-Header1: Value2

来自服务器的请求看起来几乎是这样的:

HTTP/1.1 200 OK
Cache-Control: max-age=21600
Strict-Transport-Security: max-age=15552000; includeSubdomains; preload
Content-Security-Policy: upgrade-insecure-requests
Some-Other-Header: Value1
And-Another-Header: Value2\n\n
<YOUR WEBPAGE CONTENTS>

所以第一台服务器最后发送标头和\n\n,然后才开始发送您的网页内容。 但是session_start() 正在发送“它自己的”标头,但是当标头已经完成发送时,您不能发送任何标头!

例子:

<?php
Header("SomeCoolHeader: Value1"); //Sending custom headers
session_start(); //Sending session header
Header("AnotherHeader: Value2"); //Sending custom headers

echo "Some text"; //Header sending automatically finished and sent some html text
?>

示例 2(有错误):

<?php
Header("CustomHeader1: Value1"); //sending custom headers

echo "Some text"; //Header sending automatically finished and sent some html text

Header("CustomHeader2: Value2"); //Cannot add header information - headers already sent
?>

示例 3(有错误):

<?php
Header("CustomHeader1: Value1"); //sending custom headers

echo "Some text"; //Header sending automatically finished and sent some html text

session_start(); //Cannot add header information - headers already sent
?>

如果您还有任何问题 - 您可以在 cmets 中问我。

【讨论】:

    【解决方案2】:

    session_start() 根据通过 GET 或 POST 请求或通过 cookie 传递的会话标识符创建会话或恢复当前会话。

    当 session_start() 被调用或会话自动启动时,PHP 将调用打开和读取会话保存处理程序。这些将是默认提供的内置保存处理程序或由 PHP 扩展(例如 SQLite 或 Memcached)提供;或者可以是 session_set_save_handler() 定义的自定义处理程序。读取回调将检索任何现有的会话数据(以特殊的序列化格式存储)并将被反序列化并用于在读取回调将保存的会话数据返回给 PHP 会话处理时自动填充 $_SESSION 超全局。

    要使用命名会话,请在调用 session_start() 之前调用 session_name()。

    启用 session.use_trans_sid 后,session_start() 函数将注册一个内部输出处理程序以进行 URL 重写。

    如果用户使用 ob_gzhandler 或类似的 ob_start(),函数顺序对于正确输出很重要。例如,ob_gzhandler 必须在开始会话之前注册。

    【讨论】:

      【解决方案3】:

      我们知道 cookie 存储在我们的浏览器中,会话存储在服务器中。会话中没有大小限制。 为了解决这个问题,我们必须看看 PHP 在内部是如何工作的。查看 php.ini 文件,您可以在 session 下看到如下内容,

      [Session]
      session.save_handler = files
      session.save_path = "/tmp"
      session.use_cookies = 1
      session.use_only_cookies = 1
      session.name = PHPSESSID
      session.auto_start = 0
      

      在默认配置中,php 将会话存储为服务器中的文件,默认路径是“/tem”。在 tmp 中,您可以看到名为“sess_4b1e384ad74619bd212e236e52a5a174If”的文件,这只是一个会话文件。在正常情况下,有许多用户同时访问同一个 Web。然后tmp文件夹里面有很多这样的文件。当 php 在 tmp 文件夹中创建文件时,php 在客户端浏览器中将 cookie 设置为 PHPSESSID 作为名称和值。此 cookie 显示在下图中。 enter image description here

      对于每个请求,浏览器都会将此 cookie 发送到服务器。 enter image description here

      【讨论】:

        猜你喜欢
        • 2013-12-25
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 2014-11-08
        • 1970-01-01
        相关资源
        最近更新 更多