2016-12-08 24 views
5

我使用一些的WebMethods在System.Web.UI.Page来处理一些Ajax请求,和我试图存储对象的会话在多个ajax请求中保留信息,甚至在离开页面并返回之后。HttpContext.Current.Session在一个共享的方法不更改保存

我正在通过HttpContext.Current.Session("foo")访问会话,如果没有,我通过HttpContext.Current.Session("foo") = New Bar()进行设置。

我遇到的问题是,它被设置后,下一次我打的方法,它已被重置。我试着改变别处设置的其他会话变量,并且它们也被恢复。这告诉我,我正在获取会话状态的副本,而不是一个可以更新的引用,并可以从请求到请求持续存在。我反复检查的WebMethod的EnableSession属性为True,但仍然改变会话状态不被保存。

方法声明:

<System.Web.Services.WebMethod(EnableSession:=True)> 
Public Shared Function foo(ByVal woNum As String, ByVal workCenter as String) As ToolingModel 
    Return ToolingModel.getSessionTooling(woNum, workCenter) 
End Function 

getSessionTooling:

Public Shared Function getSessionTooling(woNum As String, workCenter As String) As ToolingModel 
    Dim tooling As ToolingModel = HttpContext.Current.Session(TOOLING_MODEL_SESSION_KEY) 

    If tooling Is Nothing Then 
     tooling = New ToolingModel(woNum, workCenter) 
     HttpContext.Current.Session(TOOLING_MODEL_SESSION_KEY) = tooling 
    ElseIf tooling.woNum <> woNum OrElse tooling.workCenter <> workCenter Then 
     tooling.woNum = woNum 
     tooling.workCenter = workCenter 
     tooling.assets.Clear() 
    End If 

    Return tooling 
End Function 

我怎样才能让我的更改应用于持久会话状态,从共享的WebMethod访问它?

编辑:发现我的问题,一个星期为时已晚。 .aspx的第1行:

<%@ Page Language="VB" AutoEventWireup="false" CodeFile="foo.aspx.vb" 
    Inherits="foo" MaintainScrollPositionOnPostback="true" 
    MasterPageFile="~/mstrFoot.master" EnableSessionState="ReadOnly" %> 

该页面设置为只读会话,该会话将覆盖PageMethod的EnableSession设置。 [facepalm]

+0

你可以发布函数声明吗?看起来,如果你添加正确的属性,它应该工作:http://stackoverflow.com/questions/4758575/how-can-i-access-session-in-a-webmethod'[的WebMethod(EnableSession =真)]' – ps2goat

+0

它可能是一个配置问题?也许与POST与GET的问题?当用户登录时,我们设置了一堆会话变量,并且它们保持得很好,但如果我在此处执行操作,则无法对会话进行更改。 –

+0

什么版本。网你正在与,只是这样我可以更准确地测试这个? – ps2goat

回答

1

IIS将默认利用多核CPU。在多处理器环境中,web.config中的默认InProc SessionState设置随机处理不同线程(每个处理器/内核的单独线程)上的请求。更多详细信息,请参阅:https://msdn.microsoft.com/en-us/library/ms998549.aspx#scalenetchapt06_topic8

仅供参考,尽管过去我也自己完成了这项工作,但在维护Web API(SOAP/REST)请求之间的会话状态方面却不尽人意,因为它代表难以扩展的服务器开销。在会话状态下存储复杂对象也需要该对象/属性/字段的每个方面都可序列化,这可能非常棘手。这就是说......

根据您所提供的信息,你需要设置你的web应用程序使用StateServer模式,并启用ASP.NET状态服务的一些机器上,以便通过单独的线程来处理多个请求将保持跨CPU的会话。 https://msdn.microsoft.com/en-us/library/ms178586.aspx

+0

SessionState当前设置为SQLServer模式,这是否与StateServer完成相同? –

+0

如果您已验证会话持续到SQL Server,那么是的,这与StateServer完成相同的事情。您可能还必须为自定义对象实现自定义序列化。 阅读本文的“out-pro-proc”会话以确保您的自定义对象将被正确序列化/反序列化:http://www.hanselman.com/blog/TroubleshootingExpiredASPNETSessionStateAndYourOptions.aspx –

1

如果您的会话没有超时,最可能的原因是ASP.NET在您的webmethod请求和您的(aspx?)页面调用之间生成了不同的sessionID。您可能在两个Web方法调用之间有相同的会话可用(如果没有超时并启用了Cookie),但不能跨越页面调用和web方法。

Cannot get session in webmethod in asp.net

+0

我可以获取会话变量(例如用户的姓名,电子邮件地址等),这些都是在应用程序的其他地方设置的,但是我在WebMethod中更改的任何内容都不会存在。 –

+0

getSessionTooling定义在哪里?您没有将httpcontext传递给该方法,它可能不会为请求获取正确的httpcontext。尝试将上下文传递给方法调用。 – Vivek

+0

它在我的'ToolingModel'类中定义。我曾尝试从WebMethod传入会话,但我在会话中遇到了与保留更改不同的问题。 –