Preparing Your Development Environment
Before you start building a COM wrapper for a web service, you need a solid foundation. The environment for Great Plains developers usually consists of the Microsoft Dynamics GP installation, a compatible .NET IDE, and a local or network copy of the web service you want to expose. The version of Dynamics GP you are targeting will determine the exact SDK files and libraries you’ll need to reference. For the example below, we’ll assume GP 7.5 or 8.0, which ships with the Dynamics GP SDK and the Dexterity Development Suite.
First, install Visual Studio 2003 or newer. The COM build process relies on the .NET Framework 2.0 or later. If you’re using a newer version of Visual Studio, you can still target the older framework by changing the project’s target framework in the project properties. This ensures the generated assembly remains compatible with GP’s COM registration utilities.
Next, download or copy the web service you plan to call. In this example we’ll refer to a simple SOAP service called WildCardWebService. The service should expose a method named LoadActivate that accepts a string URL and several parameter strings, returning a single string result. Deploy the service to a known endpoint, such as http://localhost/wildcardwebservice/wildcardwebservice.asmx, and confirm it responds by visiting the URL in a browser. If the service responds with a WSDL page, the endpoint is reachable.
On the GP side, open the Dynamics GP installation CD and navigate to the SDK folder. Copy the COM and Dexterity subfolders to a working directory. These contain the reference assemblies you’ll need when compiling your COM wrapper.
Now create a new Class Library project in Visual Studio. Add references to Finally, make sure you have the The wrapper’s job is to expose a COM-friendly interface while internally delegating calls to the .NET web service client. In VB.NET, this means defining a public class, decorating it with COM attributes, and providing a default constructor that Visual Studio will expose as a creatable COM object. The following code snippet shows a minimal yet functional wrapper that can be compiled into a Class Library:Microsoft.Win32, System.Runtime.InteropServices, and any other assemblies required by your web service client. If you’re using the generated SOAP proxy classes, they will typically reference System.Web.Services and System.Xml
regasm.exe tool available. It comes with the .NET Framework and resides in the %windir%\Microsoft.NET\Framework\ folder. You’ll need it later to register the assembly so GP can instantiate the COM class. With all these components in place, you’re ready to write the actual wrapper.Building a COM Wrapper for a Web Service
Public Class AST_ComWildCard
#Region "COM GUIDs"
Public Const ClassId As String = "E14B960C-780C-45B4-92BD-4E8EB228AFC3"
Public Const InterfaceId As String = "7C2C2917-43D0-4BE1-B16B-1473E8A40BDC"
Public Const EventsId As String = "8BE33DF4-D64D-4A54-BEA7-EFD645D205D6"
#End Region
Public Sub New()
MyBase.New()
End Sub
Public Function LoadActivate(ByVal localurl As String, ByVal baseurl As String, _
ByVal userid As String, ByVal pwd As String, _
ByVal sourceid As String, ByVal cardnum As String, _
ByVal subprogid As String, ByVal LoadAmount As String, _
ByRef response As String, ByRef Description As String) As String
Dim result As String
Try
Dim ws As New WildCardWebService(localurl)
result = ws.LoadActivate(baseurl, userid, pwd, sourceid, cardnum, _
subprogid, LoadAmount)
If result = "URL doesn't respond!" Then
response = "2"
Description = result
Return result
End If
If result.IndexOf("Response=") > 0 Then
response = result.Substring(result.IndexOf("Response=") + 9 + 1, 1)
End If
If result.IndexOf("ErrorDescription=") > 0 Then
Description = result.Substring(result.IndexOf("ErrorDescription=") + 17 + 1, _
result.IndexOf(" ErrorDisplay") - 1 - (result.IndexOf("ErrorDescription=") + 17 + 1))
End If
Return result
Catch ex As Exception
response = "3"
Description = "COM Object Error!"
result = ex.Message.ToString()
End Try
End Function
End Class
Notice a few important patterns. The class declares three GUID constants: one for the class itself, one for the primary interface, and one for events. These GUIDs must remain stable; changing them breaks existing COM clients. The public constructor with no parameters is mandatory; COM will invoke this when a client calls CreateObject. The LoadActivate method accepts the web service parameters and returns the result string, while output parameters response and Description give callers detailed status information. The method wraps the web service call in a Try…Catch block so that any .NET exception surfaces as a controlled COM error.
Because Dexterity expects COM objects to expose a single interface, you may need to add an Interface declaration and mark the class with ComVisible(True) attributes. In this example, the default Public members are automatically visible, but explicit attributes make the intent clear and prevent accidental exposure of internal helpers.
Compile the project into a DLL. If you’re using Visual Studio 2003, choose “Release” configuration to avoid debugging symbols. The resulting assembly should have a strong name if you plan to register it in the Global Assembly Cache (GAC); otherwise a simple registration will work for local deployment.
At this point, the wrapper is a fully functional COM object that can be instantiated from any COM-aware environment, including Dexterity. The next step is to register it so GP’s COM runtime can locate it.
Registering the COM Component
Registration turns the compiled assembly into a COM server that Windows can load on demand. The easiest tool for this is regasm.exe. Open a command prompt with administrative rights and navigate to the folder containing your DLL. Run the following command:
regasm /codebase /tlb AST_ComWildCard.dll
The /codebase flag tells Windows to register the assembly’s physical path; this is useful for local testing. The /tlb flag generates a type library (.tlb) that Dexterity uses to discover the COM interface. If the command succeeds, you’ll see a confirmation message listing the CLSID and interface GUIDs.
Verify the registration by opening the Windows Registry Editor ( Because GP may load the COM server in a different process, you’ll need to make sure the assembly is accessible from that process. For a simple local test, placing the DLL in the same folder as the GP executable or in the system Once the COM server is registered, GP can create an instance using With the COM object registered, the real integration work begins inside a Dexterity form or window. In Dexterity, navigate to the Open or create the window you want to host the call. Create a new local invisible field, naming it Add a push button to the form and write the following Sanscript in its regedit.exe) and navigating to HKEY_CLASSES_ROOT\CLSID\{E14B960C-780C-45B4-92BD-4E8EB228AFC3}. The InprocServer32 key should point to the path of your DLL, and the ProgID key should be set to WildCardClassLibrary.AST_ComWildCard. If anything looks wrong, double‑check the GUIDs and re‑run regasm
PATH is sufficient. In a production deployment, you might copy the DLL to C:\Program Files\Microsoft Dynamics GP\Custom\AST_ComWildCard.dll and register it there.CreateObject("WildCardClassLibrary.AST_ComWildCard") from within Dexterity scripts. The next section shows how to wire that call into a Dexterity form.Integrating COM Calls in Dexterity
Resource Explorer, right‑click the target database, and select New → Library (COM). Point the wizard to the DLL you just registered, and finish the wizard. The library appears in the Explorer’s list of COM objects.(L) WildCard. Set its reference type to COM Object, then choose the interface generated by the .tlb file – typically WildCardClassLibrary.AST_ComWildCard. This field will hold the COM instance while the window is active.Click event:' Create the COM instance
(L) WildCard of window AST_WildCard = COM_CreateObject("WildCardClassLibrary.AST_ComWildCard");
If '(L) WildCard' of window AST_WildCard = null Then
error "Could not create WildCardClassLibrary object.";
abort script;
End If;
' Call the web service method
Dim resp As String
Dim desc As String
(L) Result' of window AST_WildCard = '(L) WildCard' of window AST_WildCard.LoadActivate(
"http://localhost/wildcardwebservice/wildcardwebservice.asmx",
"https://yourasppage.asp",
"PARAMETER1",
"PARAMETER2",
"PARAMETER3",
"PARAMETER4",
"PARAMETER5",
"PARAMETER6",
resp,
desc);
' Clean up
(L) WildCard' of window AST_WildCard = null;
Replace the placeholder URLs and parameters with the values your business logic requires. The call populates resp and desc with status and error text. The (L) Result field will contain the raw string returned by the web service. From here you can parse the result, display messages, or store data in GP tables.
Because the COM object is created and destroyed on each button click, memory usage stays minimal. If you need a persistent connection, move the COM_CreateObject call to the window’s Create event and release it in the Destroy event. That keeps the COM instance alive for the window’s lifetime.
When deploying the custom form to production, copy the DLL to the GP Custom folder, re‑register it, and rebuild the Dexterity window. Users will then experience a seamless web‑service integration without leaving the GP interface.
Testing and Troubleshooting
Testing is critical when mixing COM, .NET, and GP. Begin by launching the window in the GP sandbox. Click the button and watch the result field. If the service endpoint is unreachable, the wrapper returns URL doesn't respond! and sets response to . Any .NET exception triggers the Catch block, setting response to and providing the exception message. These codes give you a quick way to log or display error states.
To debug the wrapper, attach a debugger to the GP process (gp.exe). Visual Studio can load the source because the assembly is compiled with debugging information. Place breakpoints in LoadActivate and step through the SOAP call. Verify that the service URL is correct and that the proxy’s binding matches the service’s WSDL. Inspect the returned XML to confirm the expected fields exist.
If the COM object cannot be created, double‑check the GUIDs, the CLSID registry entry, and the assembly’s strong name. The most common mistake is forgetting to expose the default constructor; without it, Windows will reject the COM registration.
When performance matters, consider caching the web service client inside the COM object rather than recreating it on each call. Add a private field to the class that holds the WildCardWebService instance and initialize it lazily. Dispose of it in a finalizer or a Dispose method called from Dexterity’s Destroy event.
Finally, remember that network latency and service downtime are outside your control. Add retry logic in the wrapper if your business processes can tolerate temporary failures. A simple loop that retries a fixed number of times with exponential back‑off keeps the user experience smooth while still surfacing permanent errors.





No comments yet. Be the first to comment!