【问题标题】:How to maintain global session in PHP?如何在 PHP 中维护全局会话?
【发布时间】:2012-04-21 13:11:31
【问题描述】:

我目前正在使用 PHP 中的一个应用程序,我需要在其中维护一个购物车。一切正常。

当一个项目被添加到购物车时,我需要在 每个页面的标题上显示一条消息,例如“购物篮中有 1 个项目”,如果购物车包含一件商品。

当添加(或删除)其他商品时,消息应该会相应更改无需刷新页面,例如“购物篮中有 2 件商品”等等。

我面临的问题是,当某些商品被删除或添加到购物车时,我需要刷新页面(然后只有这样我才能在页面的标题上看到更新的商品)

例如,假设购物车现在包含 2 件商品,现在又添加了一件商品,标题上的消息仍将显示“购物篮中有 2 件商品” ”,而不是在页面刷新之前显示“购物篮中有 3 件商品”。


在 Java 中,SessionListener 如下所示。

package sessionListener;

import javax.servlet.annotation.WebListener;
import javax.servlet.http.HttpSession;
import javax.servlet.http.HttpSessionEvent;
import javax.servlet.http.HttpSessionListener;

@WebListener()
public class SessionListener implements HttpSessionListener
{
    private HttpSession session=null;        

    @Override
    public void sessionCreated(HttpSessionEvent se)
    {
        session=se.getSession();
        //Use this session            
    }

    @Override
    public void sessionDestroyed(HttpSessionEvent se)
    {

    }
}

我可以使用sessionCreated() 方法来满足要求,因为它是在首次创建会话时只执行一次的方法。

在 .NET 中类似,我们有 Global.asax 应用程序文件,例如

<%@ Application Language="C#" %>

<script runat="server">

    protected void Application_AuthenticateRequest(Object sender, EventArgs e)
    {

    }

    void Application_Start(object sender, EventArgs e) 
    {
        // Code that runs on application startup

    }

    void Application_End(object sender, EventArgs e) 
    {
        //  Code that runs on application shutdown            
    }

    void Application_Error(object sender, EventArgs e) 
    { 
        // Code that runs when an unhandled error occurs

    }

    void Session_Start(object sender, EventArgs e) 
    {
        // Code that runs when a new session is started
        Session.Add("Message", SomeValue);            
    }

    void Session_End(object sender, EventArgs e) 
    {
        // Code that runs when a session ends. 
        // Note: The Session_End event is raised only when the sessionstate mode
        // is set to InProc in the Web.config file. If session mode is set to StateServer 
        // or SQLServer, the event is not raised.

        Session.Abandon();

    }

</script>

我可以使用void Session_Start(object sender, EventArgs e) 方法来满足要求,因为这是在会话开始时只调用一次的方法(每个用户的会话一次)。

但是在 PHP 中,我找不到在创建新会话时只执行一次的类似概念(我现在没有使用 PHP 中的任何框架)。

如果是这样,当购物车状态更新而根本没有刷新页面时,如何在每个页面的标题上显示上述指定消息?

【问题讨论】:

    标签: php session


    【解决方案1】:

    要在不刷新的情况下更改页面的一部分,您需要一种客户端语言。 Javascript 可以帮助您,尤其是 AJAX 调用:您调用一个 PHP 脚本,该脚本返回您购物车中的商品数量。

    即使用户在浏览器中打开多个选项卡,您也可以每 X 分钟调用一次来刷新项目计数。

    【讨论】:

    • 确实如此。 @Bhavesh - 无论您使用哪种服务器语言,情况都是如此。即使对于 Java 或 .net,您仍然需要刷新页面或 JS 小部件来修改 DOM。
    • 在 Java 和 .NET 中,确实不需要刷新页面,因为在添加到购物车时,页面会自动重定向(或在从购物车中删除商品或更新购物车时重新加载)导致标题上的消息相应更改,因为项目计数在上述 sn-p 中提到的全局方法中维护。这种事情在 PHP 中不会发生,因为我们不能有一个只启动一次的全局(会话)变量。
    • 正是由于这个原因,据我所知,在使用 PHP 时,购物车是在数据库表中维护的,这确实是一个错误的概念,因为这涉及到对数据库的额外操作。在 Java 中,购物车可以简单地保存在 Collection, Hashtable, List 或类似的 SessionListener 中。在 .NET 中,它可以保存在 Globlal.asax 应用程序文件中的 DataTable 中,当且仅当订单得到客户确认后才能最终插入数据库中,这需要对数据库的操作较少。
    【解决方案2】:

    您可以使用 JavaScript 的 AJAX 调用向服务器发出请求,而无需刷新页面。

    但请注意,某些浏览器不支持(或已禁用)JavaScript。因此,请确保您的脚本在页面刷新后仍然有效。

    【讨论】:

      【解决方案3】:

      正如我在一个项目中所做的那样:购物车在每次更改时都会在两个地方更新:在服务器上和加载的页面中,动态更新。

      单击购物车项目的 +/- 按钮以更改其数量将触发 JavaScript 事件,该事件执行以下操作:

      1. 向服务器发送ajax call,让它知道购物车的内容已更改;
      2. 更新加载页面中显示的购物车。

      例如,看看像 jQueryMootools 这样的 JS 库。它们使 JS 脚本编写比从头开始编写代码容易得多!还有很多其他类似的库。

      【讨论】:

        猜你喜欢
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 2018-10-22
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 2015-03-28
        相关资源
        最近更新 更多