I also understand that resetting a recordsouirce requires resetting all the column properties. That is hundreds of lines of code. In VFP there is an easy workaround for that, but not in FiC.
I also understand that I can requery views.
Unfortunately none of that answers my main question. I simply need to issue a SET FILTER TO against the currently open table. I can do all kinds of operations against tables and FiC properly restores the datasession. But set filter to causes the datasessions to get mixed up.
In any web application, data session needs be 'reconstructed', or 'restored' on each user request.
wConnect's basic principle is to
always OPEN DATABASE and USE tables/views at the beginning of the request, and close them at the end.
This is called a 'stateless' server: each request writes on a new blank page.
FoxInCloud makes no exception to that principle, though it implements it slightly differently, very similar to regular form operation:
1- awFrm.Load() and/or DataEnvironment USE tables and views, probably NODATA
Form.Load() is executed once for all users, when the form instance is created for the server lifetime.
No difference with regular app operation: as .Load() accepts no parameter, coding user-based variations is very unlikely.
2- With Form.Init(parms) you can requery the views based on some parameters.
This only thing to take care of is to replace
parm1=value1
parm2=value2
Requery(myView)
by
thisForm.wViewParmSet(myView, 'parm1', value1)
thisForm.wViewParmSet(myView, 'parm2', value2, .T.)
This way FAS knows the view's parameters names and values, and is able to restore the view in the same state when user comes back for a new request.
Form.Init() is executed each time a user first needs a form, exactly like in regular LAN operation;
- parameters are passed as in normal LAN operation;
- .Refresh() is executed as in normal LAN operation.
The only difference is that the .Show() is not executed in Web mode. But awFrm.wFormShow() is executed, you can move your code there, and call this.wFormShow() from .Show().
3- awFrm.wUserSet(userID) allows you to adapt the form environment (including data) to user's profile - e.g. you may reUSE different tables or views based on userID, like in your scenario.
Care must just be taken with grids:
Grid.RecordSource = ''
USE IN commonAlias
USE currentUserTable/View ALIAS commonAlias
Grid.RecordSource = 'commonAlias'
In this scenario is when you have a Grid with dynamically populated columns (not in the Class/Form designer) - As columns are destroyed when clearing Grid.RecordSource, you need to restore everything like .Header.Caption, .CurrentControl, etc.
[by the way, I think we could create a standard method for reUSEing an alias with a different table/view and take care of Grid(s).RecordSource and .Columns definitions]
awFrm.wUserSet(userID) is called at the very beginning of each request, before form state is restored, thus before any user event is executed.
awFrm.wUserGet() is called at the very end of each request
[All this can be seen in awAJAX.FormRequest() source code.]
You would probably move to awFrm.wUserSet(userID) the code you usually run in Form.Init() based on user ID.
This is a straight application of the 'stateless principle' we recalled at the beginning of this post: everything user-dependent must be restored on each request.
HTH,
there needs to be some way of emulating what Load does. for multi data sets, you want to initialize grid data sources before the grid initializes. if you have a private data session in the form, I see no way to do this. You can now create a data source in Load and update it in init, but that does not help this issue. I see no place to ever create a grid data source after the initial Load without a whole bunch of manual coding in the Init.
Multi data sets rely typically on the fact that there are X copies of the complete data set, each located in a unique location, but with the exact same data names and structures. Like deciding to drive a car down Highyway 1 or a parallel highway called Highway 1. Once on the highway, the car functions exactly the same. The 2 highways are parallel and never meet. Once on one of them you are committed to staying on that road.
Since forms are instatiated only once, it is like only having one highway. Therefore in the Init we have to build a new highway as we go by manually creating the grid. Yuck,