Help in Converting Desktop App to Web App.
-
Thanks I understand that there is no magic and no converter and that each page is new and any variables should be as initialized when built or saved in either viewState, SessionState, ApplicationState a cookie or other external source. This does not explain why variables in the 2nd VB class (vbServHandler) has new data in it while the 1st (vbMain) does not. What would cause this?
It sounds like
vbServHandler
is usingShared
fields. You should generally avoidShared
fields in ASP.NET applications unless you really know what you're doing. For example, the data in the fields will be shared across all requests from all users, which means you could easily end up showing data meant for user A to user B by mistake.
"These people looked deep within my soul and assigned me a number based on the order in which I joined." - Homer
-
It sounds like
vbServHandler
is usingShared
fields. You should generally avoidShared
fields in ASP.NET applications unless you really know what you're doing. For example, the data in the fields will be shared across all requests from all users, which means you could easily end up showing data meant for user A to user B by mistake.
"These people looked deep within my soul and assigned me a number based on the order in which I joined." - Homer
They are NOT shared. I think it may be when a button control is hit on the page that the vbServHander is not getting re-initialized (vbServHandler variables still have data). I have done this: 1. By just click in the upload button on the vbMain button multiple times. 2. Clicking on the C# menu button (Upload) to reload the page. 3. Going back to the main page and clicking on the Upload button to reload the upload page. 4. Even refreshing the main home page via F5. In all cases the constructor for vbMain (i.e. sub new) shows data in the vbServHandler variables. I am programming around this (I actually think it is better) but just do not understand it.
-
They are NOT shared. I think it may be when a button control is hit on the page that the vbServHander is not getting re-initialized (vbServHandler variables still have data). I have done this: 1. By just click in the upload button on the vbMain button multiple times. 2. Clicking on the C# menu button (Upload) to reload the page. 3. Going back to the main page and clicking on the Upload button to reload the upload page. 4. Even refreshing the main home page via F5. In all cases the constructor for vbMain (i.e. sub new) shows data in the vbServHandler variables. I am programming around this (I actually think it is better) but just do not understand it.
If the variables are persisted between requests to your site, and they're not stored in application or session state, then either they're stored in
Shared
fields, or the instance of the containing class is stored in aShared
field somewhere.
"These people looked deep within my soul and assigned me a number based on the order in which I joined." - Homer
-
If the variables are persisted between requests to your site, and they're not stored in application or session state, then either they're stored in
Shared
fields, or the instance of the containing class is stored in aShared
field somewhere.
"These people looked deep within my soul and assigned me a number based on the order in which I joined." - Homer
They are not saved anywhere. If they are in some shared object then I do not know where it could be. Here is the definition of the object I was checking in the Sub new of vbMain. Public AccountCollection As Collection in what I was calling vbServHandler. Real name is QBAPIV3Cl which is part of DLL QBAPIV3VS2013. This is invoked via by vbMain Imports QBOAPIV3VS2013 . . Public aQB As New QBOAPIV3VS2013.QBAPIV3Cl() which is defined in a module within vbMain. . . Which is referenced by the C# Web App using vbMainDLL; In the C# program it is defined as vbMainDLL.vbMain vbMain; vbMain = new vbMain(TheRealmID,TheAccessToken,TheAccessTokenSecret, TheConsumerKey,TheConsumerSecret, TheContext,TheDataService, pOutReason: ref pOutReason); The Sub New for vbMain has aQB.accountcollection.count Referenced object has a value of nothing the first time. then 121 every other time. I would expect a value of nothing each time. The c# program has no references to the aQB class/QBOAPIV3VS2013.QBAPIV3Cl. So what am I missing?
-
They are not saved anywhere. If they are in some shared object then I do not know where it could be. Here is the definition of the object I was checking in the Sub new of vbMain. Public AccountCollection As Collection in what I was calling vbServHandler. Real name is QBAPIV3Cl which is part of DLL QBAPIV3VS2013. This is invoked via by vbMain Imports QBOAPIV3VS2013 . . Public aQB As New QBOAPIV3VS2013.QBAPIV3Cl() which is defined in a module within vbMain. . . Which is referenced by the C# Web App using vbMainDLL; In the C# program it is defined as vbMainDLL.vbMain vbMain; vbMain = new vbMain(TheRealmID,TheAccessToken,TheAccessTokenSecret, TheConsumerKey,TheConsumerSecret, TheContext,TheDataService, pOutReason: ref pOutReason); The Sub New for vbMain has aQB.accountcollection.count Referenced object has a value of nothing the first time. then 121 every other time. I would expect a value of nothing each time. The c# program has no references to the aQB class/QBOAPIV3VS2013.QBAPIV3Cl. So what am I missing?
QuickBooksDev wrote:
which is defined in a module within vbMain.
A
Module
is effectively a class in which every member isShared
. If your fields are stored in aModule
, they they'reShared
by definition.
"These people looked deep within my soul and assigned me a number based on the order in which I joined." - Homer
-
QuickBooksDev wrote:
which is defined in a module within vbMain.
A
Module
is effectively a class in which every member isShared
. If your fields are stored in aModule
, they they'reShared
by definition.
"These people looked deep within my soul and assigned me a number based on the order in which I joined." - Homer
Here is the class Public Class QBAPIV3Cl ... No Module Public AccountCollection As Collection AccountCollection is the variable that I am checking for persistence. It is references by the vbMain module as Module Common which is a separate vb source file. Module Common .. Public aCL As New vbMain.QBAPIV3Cl() So what you are saying since MODULE common is a MODULE everything in it is Shared/Static including all of aCL????
-
Here is the class Public Class QBAPIV3Cl ... No Module Public AccountCollection As Collection AccountCollection is the variable that I am checking for persistence. It is references by the vbMain module as Module Common which is a separate vb source file. Module Common .. Public aCL As New vbMain.QBAPIV3Cl() So what you are saying since MODULE common is a MODULE everything in it is Shared/Static including all of aCL????
QuickBooksDev wrote:
So what you are saying since MODULE common is a MODULE everything in it is Shared/Static including all of aCL????
Yes, that's correct.
A module has the same lifetime as your program. Because its members are all
Shared
, they also have lifetimes equal to that of the program. ... All members of a module are implicitlyShared
.
"These people looked deep within my soul and assigned me a number based on the order in which I joined." - Homer
-
QuickBooksDev wrote:
So what you are saying since MODULE common is a MODULE everything in it is Shared/Static including all of aCL????
Yes, that's correct.
A module has the same lifetime as your program. Because its members are all
Shared
, they also have lifetimes equal to that of the program. ... All members of a module are implicitlyShared
.
"These people looked deep within my soul and assigned me a number based on the order in which I joined." - Homer
So for a web app it last forever??? Is there a way of making a module non-Shared so I do not have to re-organize the program? Or what is the best way to have the module non-Shared?
-
So for a web app it last forever??? Is there a way of making a module non-Shared so I do not have to re-organize the program? Or what is the best way to have the module non-Shared?
Yes, in a web application it will last until the AppPool recycles. There's no way to make a module non-shared. However, you might be able to get away with changing the field to a property, and adding code to retrieve the value from the current session if the code is running in an ASP.NET application. Something like this should work:
Imports System.Web
Imports System.Web.HostingModule Common
' The key for the field in the session - this must be unique:
Private Const SessionKey As String = "Common::aCL"' Backing field used for non-web applications: Private aCLNonWeb As vbMain.QBAPIV3Cl Public ReadOnly Property aCL() As vbMain.QBAPIV3Cl Get If Not HostingEnvironment.IsHosted Then ' Not running in ASP.NET: If aCLNonWeb Is Nothing Then Set aCLNonWeb = New vbMain.QBAPIV3Cl() End If Return aCLNonWeb End If Dim context As HttpContext = HttpContext.Current If context Is Nothing Then Throw New InvalidOperationException("No current request.") End If Dim value As vbMain.QBAPIV3Cl = DirectCast(context.Session(SessionKey), vbMain.QBAPIV3Cl) If value Is Nothing Then value = New vbMain.QBAPIV3Cl() context.Session.Add(SessionKey, value) End If Return value End Get End Property
End Module
"These people looked deep within my soul and assigned me a number based on the order in which I joined." - Homer
-
Yes, in a web application it will last until the AppPool recycles. There's no way to make a module non-shared. However, you might be able to get away with changing the field to a property, and adding code to retrieve the value from the current session if the code is running in an ASP.NET application. Something like this should work:
Imports System.Web
Imports System.Web.HostingModule Common
' The key for the field in the session - this must be unique:
Private Const SessionKey As String = "Common::aCL"' Backing field used for non-web applications: Private aCLNonWeb As vbMain.QBAPIV3Cl Public ReadOnly Property aCL() As vbMain.QBAPIV3Cl Get If Not HostingEnvironment.IsHosted Then ' Not running in ASP.NET: If aCLNonWeb Is Nothing Then Set aCLNonWeb = New vbMain.QBAPIV3Cl() End If Return aCLNonWeb End If Dim context As HttpContext = HttpContext.Current If context Is Nothing Then Throw New InvalidOperationException("No current request.") End If Dim value As vbMain.QBAPIV3Cl = DirectCast(context.Session(SessionKey), vbMain.QBAPIV3Cl) If value Is Nothing Then value = New vbMain.QBAPIV3Cl() context.Session.Add(SessionKey, value) End If Return value End Get End Property
End Module
"These people looked deep within my soul and assigned me a number based on the order in which I joined." - Homer
Thanks will give it a try.