PowerBuilder Authors: Chris Pollach, Yeshim Deniz, Jayaram Krishnaswamy, Kevin Benedict, Avi Rosenthal

Related Topics: PowerBuilder

PowerBuilder: Blog Feed Post

Migrating PowerBuilder SOAP clients to WCF

Powerbuilder 12 Has Been Released, And Comes In Two Flavors!

PowerBuilder 12 has been released, and if you’ve been paying attention, you know that it now comes in two flavors!  There’s PB12 “Classic” for traditional Win32, WinForm, WebForm, .NET Assembly, and J2E component targets, and PB12 .NET for WPF (Windows Presentation Foundation) and WCF (Windows Communication Foundation) proxy targets.


One of the overriding goals of this release was to give PB developers an easy migration path that would allow them to bring their tried-and-true Win32 PowerBuilder applications into the new and exciting world of WPF.  While it’s unrealistic to assume that all PB apps, big and small, will migrate cleanly into PB12.NET with zero refactoring, there is one specific class of applications that will absolutely require some coding work to make the transition.  These would be any applications that invoke SOAP-based web services, using the SoapConnection and SoapException extension classes. These have been deprecated in PB12.NET (don’t worry – they still exist in PB12 Classic!).  They have been replaced with the new WCF proxies.  However, the migration process does not automatically convert the existing web service proxy objects/projects into WCF proxy projects.  But don’t worry, I’m here to help…


This post is going to walk through the process of migrating the existing Web Services sample app, which was featured in a previous blog post, into a WPF/WCF application. You’ll see that it’s relatively easy, and results in much cleaner and more streamlined coding.


Step 1:  Migrate the existing target into PB12.NET


This step is very simple.  Open PB12.NET, and create a new Solution (what we used to call a Workspace).  This creates an empty .PBWX file in a folder of your choosing.  Then click Add Target…  This prompts you for the location of the an existing .PBTX (WPF) or .PBT (Classic) target file.  If you installed the Sample Applications during the PB12 install, the target you want should be found in the folder C:\Documents and Settings\All Users\Documents\Sybase\PowerBuilder 12.0\Code Examples\Web Services.


Select the WS.PBT file.  This target has NOT been migrated to PB12.NET, so the Migration Wizard will kick in.


PB12.Net Migration Wizard


Note that this is a non-destructive migration, unlike previous versions of PB.  You’re asked for two locations – and the terminology used can be a little confusing.  The first location, labelled “Target”, is actually the location of the existing Source – i.e., the code you’re migrating FROM.  The second, labelled “New location and target file” is both the folder location into which PB will place the migrated code AND the new target name.  The PBLs referenced in the “target” are not changed at all – the migrated code is placed into the “new” directory – PBL for PBL.


Walk through the remaining panels of the wizard, accepting the defaults, and you’ll get to the main PB12.NET IDE.


Step 2: Generate the WCF Proxies for the services


The old SOAP proxies are useless in PB12.NET.  In fact, once we finish replacing the existing proxies with WCF proxies, you can even remove the Proxies.PBL from the target library list.  None of the proxy or structure classes in that PBL will be referenced.

  • Select File >> New >> PB Library to create a new PBL that will store the new WCF Proxy classes.  I’m calling mine WCFProxies.PBL.
  • Select File >> New >> WCF Client Proxy to start the Proxy wizard.  You’ll have to do this for each of the old SOAP web service proxies, but let’s start with the Movie Times service.
    • I’ll name this project p_movietimes_wcfclient, and place it in the WCFProxies PBL.
    • The service URL is:
    • Leave the NameSpace entry blank.  Name the proxy assembly movietimes.dll, and place the proxy class into WCFProxies.PBL.
    • The next panel shows the list of services (there’s only one), and the data structures (there are several).  Click Next, then Finish.  This opens the Project Painter and loads p_movietimes_wcfclient
    • Now click the Generate Proxy button to create the proxy object class.
  • Do this for each of the web services that currently have proxies.  I’ve gone ahead and completed this process and stored the zipped solution files here.  Note:  some of the web services are no longer active, so the code in the cb_invoke button of their corresponding visual user objects has been commented out.

What comes out:  you’ll get WCF proxy objects in the WCFProxies.PBL.  These are real PowerScript objects, with methods and events that you can open and inspect.  You’ll also (optionally) get new additions into the References folder, for any structure classes that are called out in the WSDL.  So, in your PowerScript, you’ll declare the proxy with the class type that appears in the PBL, and any structure references that appear will come from the References folder.


Step 3: Remove the deprecated SOAP client classes


The SoapConnection, SoapException, and SoapPBCookie classes are obsolete in PB12.NET.  All of the processing that these classes used to perform has been incorporated directly into the WCF proxy class (which we generated in Step 2).  All we need to do is delete these from the WS PBL, and then remove any references to them from the PowerScript code.

uo_ancestor (tabpages.pbl)

  • Remove the instance variable declaration for the SoapConnection class.
  • Remove all the code from the Constructor and Destructor events.
  • Remove both of the InstantiateService() methods. Select the method, then choose Edit >> Delete Function…

Step 4: Call the new WCF proxy classes


The uo_ancestor class used to manage all the SOAP client and proxy instantiation.  Since none of that is necessary anymore, all we need to do is open every descendent of uo_ancestor, and fix the code in their cb_invoke::clicked event to instantiate and invoke the new WCF proxies.  Again, let’s start with uo_movietimes.

uo_movietimes (tabpages.pbl)


  • Replace the local declarations and remove the call to InstantiateService()
    • s03_movieinformation on line 1 becomes movietimes_MovieInformationSoapClient (Intellisense really helps here).
    • s03_theatre on line 2 becomes movietimes.Theatre
    • Comment out the entire IF statement that calls InstantiateService() on line 13.  Replace it with:
      px_Service = CREATE movietimes_MovieInformationSoapClient
    • Comment out the final END IF on the last line.
  • Fix a type casting exception that will be thrown at runtime (the C# compiler is much more strict than the PowerScript compiler!)
    • The local ANY variable response needs to be changed to an array declaration, since the proxy’s GetTheatresAndMovies() method returns an array of movietimes.Theatre structures.  PowerScript allows an Any to hold literally any reference, but C# has strict rules about array to non-array assignments.

That’s really all the code that needs to change!   I did go ahead and comment out the code that invokes the dead web services, since I couldn’t generate new proxies for them.  And I changed the MovieTimes user object layout so that the Canvas element was nested inside a Grid with two RowDefinition.  This makes the Resize logic completely unnecessary, as WPF handles resizing anything inside a Grid cell.   But that’s the topic of the next blog post – no reading ahead.

The final step would be to perform a full Build, and a Deploy, then test out the Movie Times web service call.


Download the sample PB12.NET solution by clicking here.




Read the original blog entry...

More Stories By Paul Horan

Paul Horan is a Senior Solution Advisor and Mobility Architect at SAP, and works with the SAP Mobile Platform and SAP Mobile Secure product lines. Paul joined SAP as part of their acquisition of Sybase in June, 2010. Prior to that, Paul worked for Sybase as a technical pre-sales architect supporting PowerBuilder, PowerDesigner, and SQL Anywhere. Paul works out of SAP's Reston VA office. A 1984 graduate of Indiana University, Paul currently resides in Arlington VA.