ASP.NET用户控件点击事件触发后DataSource属性被重置问题求解
可行解决方案
1. 进程内Session存储(无需序列化)
如果你的站点Session采用默认**InProc(进程内)**配置,不需要对象支持序列化即可存储,操作如下:
- 父控件给DataSource赋值时,同步存入Session:
' 父控件初始化数据源时执行 childControl.DataSource = bondList Session("CurrentBondDataSource_" + Page.UniqueID) = bondList
- 点击事件中直接读取:
Public Sub lnkBtnSelect_Click(ByVal sender As Object, ByVal e As EventArgs) Handles lnkBtnSelect.Click Dim source = TryCast(Session("CurrentBondDataSource_" + Page.UniqueID), List(Of Model.Bond)) ' 业务逻辑执行完可主动释放Session避免占用内存 Session.Remove("CurrentBondDataSource_" + Page.UniqueID) End Sub
注:加Page.UniqueID作为键前缀是为了避免用户打开多个同页面标签时数据冲突。
2. 回发时重新初始化数据源
如果数据源可通过数据库、接口等快速查询获取,直接在Page的Page_Load事件中,无论是否是回发都给子控件DataSource重新赋值即可,这是最符合ASP.NET生命周期的实现方式,无额外存储开销:
' 父控件的Page_Load事件 Protected Sub Page_Load(ByVal sender As Object, ByVal e As System.EventArgs) Handles Me.Load Dim bondList = 你的数据源查询逻辑() childControl.DataSource = bondList childControl.DataBind() End Sub
3. 关键标识隐藏域存储
如果仅需要操作选中项的核心数据,不需要完整的Bond对象集合,可在数据绑定时把所有Bond的主键(如ID)拼接为分隔符分隔的字符串,存入runat="server"的隐藏域中:
<!-- file1.ascx 新增隐藏域 --> <asp:HiddenField ID="hfBondIds" runat="server" />
' 数据绑定时存ID Private Sub gvBondDialog_DataBinding(ByVal sender As Object, ByVal e As System.EventArgs) Handles bondList.DataBinding If DataSource IsNot Nothing Then CType(bondList.FindControl("gvBondDialog"), GridView).DataSource = DataSource ' 拼接所有ID存入隐藏域 hfBondIds.Value = String.Join(",", DataSource.Select(Function(b) b.Id.ToString())) End If End Sub
回发事件中读取ID集合,需要完整对象时再通过ID单独查询即可,开销极低。
4. 缓存存储
如果该数据源是多用户共用的公共数据,可存入HttpRuntime.Cache,设置合理的过期时间,同样InProc模式下无需序列化:
' 存缓存 Cache.Insert("PublicBondDataSource", bondList, Nothing, DateTime.Now.AddMinutes(10), TimeSpan.Zero) ' 取缓存 Dim source = TryCast(Cache("PublicBondDataSource"), List(Of Model.Bond))
内容的提问来源于stack exchange,提问作者Ystalio Di Staniovich
相关产品推荐
相关产品推荐

