I planned on writing a blog post on this for a while. A recent support request reminded me that i had not done this yet.

For someone coming from desktop application development there are a number of concepts with web applications that are new or different.

Some of these issues are well hidden and can lead to hours of fun debugging your application.

Most of these things have to do with the fact that we have a client server system with the client completely disconnected from the server except for short calls between the two

lets look at a simple example. A view with a button that shows a messagebox

Our code in the view looks something like this

//
Object oTestBtn is a cWebButton
    Procedure OnClick
        Send ShowInfoBox "Hello World"
    End_Procedure
End_Object

All good. We click the button, it executes the OnClick procedure which in turn pops up an InfoBox.

But thats exactly the same as in a desktop application isn’t it?

Well the code might look the same but technically there is a lot going on behind the scenes to make this work.

For starters when the view is shown the server has to send the view to the client in order to be able to show the view. This view that is created using client side Javascript classes and data sent to the client.

When the user clicks the button the click happens on the client side calling a javascript event. The client side Javascript class then fires the event and calls back to the server.

The callback to the server arrives at the web server which will then communicate with the DataFlex WebApp Server component. The webapp server component in turn finds an available process in the process pool for this application and calls into the application.

after synchronizing the process with the clients data the buttons OnClick procedure is actually executed where it encounters the line to call ShowInfoBox.

ShowInfoBox is a DataFlex procedure. The server of course cannot show a messagebox on the client so the ShowInfoBox method actually calls a javascript method on the client passing the required data.

The JavaScript method actually shows the InfoBox to the client.

That doesnt seem to be too bad but lets take a look at an example that does a little more than showing a message box.

Lets take our GEO Location control for example. It has a method called RequestGetLocation that is called to get the users current GEO location. The control has properties called psLongitude as well as psLatitude.

So lets look at a little button example

//
Object oShowLocationBtn is a cWebButton
    Procedure OnClick
        // Call GEOLocation helper to get location
        Send RequestGetLocation to oGEOLocationHelper

        // Now show location
        String sLatitude sLongitude
        WebGet psLatitude  of oGEOLocationHelper to sLatitude
        WebGet psLongitude of oGEOLocationHelper to sLongitude

        Send ShowInfoBox ("Lon: "+trim(sLongitude)+" Lat: "+trim(sLatitude))
    End_Procedure

End_Object

code looks good. We call the RequestGetLocation method which gets the GEO location and then we get the web properties containing the location and show them in the messagebox

Well not quite. If you dont have our GEOLocation control you will have to trust me when I tell you the above code will fail miserably and not return a location or return the incorrect location.

Why is that. Well actually there are two things in play here that we can learn from this example.

As mentioned previously functionality that has to be executed on the client needs to be sent to the client.

In this procedure we are calling two methods on the client. The first one RequestGetLocation and the second one ShowInfoBox. In between the two we are getting the values of the properties and we are using WebGet because we know these are web properties that are updated from the client.

There is an additional important thing to know. These two calls to the client do not happen when you would think they happen which is where the code lines are.  Rather these two calls are queued and executed when the server execution finishes for the current call.

This would be at the end of the OnClick procedure. So whats actually going to happen with the code above is as follows

  1. Queue up a call to get the GEO Location
  2. get the current value of the web properties of psLatitude and psLongitude
  3. Queue up a call to show an infobox

Now the execution returns to the client and the client code will now execute all queued up calls. The last one will show the messagebox but it will show the text with values that were in place before the call to get the GEO location was even executed.

The example with our GEO location control shows another issue. The actual call on the client to get the GEO location is asynchronous. This means that you call the function but it will return immediately without returning any values.

Your code will keep executing but the data you expect will not be available until a callback happens. This means that in order for this specific call to work you have to work with the proper callbacks as well

The code to make this work would look like this

//
Object oGEOLocationHelper is a cszGEOLocation
    ....
    
    // OnLocationChanged event is called when a location is available
    Procedure OnLocationChanged Integer iStatus String sLongitude String sLatitude
        Send ShowInfoBox ("Lon: "+trim(sLongitude)+" Lat: "+trim(sLatitude))
    End_Procedure   
End_Object

Object oShowLocationBtn is a cWebButton
    Procedure OnClick
        // Call GEOLocation helper to get location
        // this will call the event when a location is available
        Send RequestGetLocation to oGEOLocationHelper
    End_Procedure
End_Object

in this example now the button calls the RequestGetLocation method which in turn will call the javascript method to get the location

The javascript codes callback event will be called when the browser has a proper location which will then cause the DataFlex client to call back into the server to call the OnLocationChanged event

The OnLocationChanged event will execute and then show the info box with the proper location values

Michael Salzlechner is the CEO of StarZen Technologies, Inc.

He was part of the Windows Team at Data Access Worldwide that created the DataFlex for Windows Product before joining StarZen Technologies. StarZen Technologies provides consulting services as well as custom Application development and third party products specifically for DataFlex developers