Updated: March 14,1996 |
Introduction
Benefits of Client-Host Applications
Application Programming Interfaces (APIs)
HLLAPI and Visual Basic
Calling HLLAPI Functions
Basic HLLAPI Functions
Example Application 1
OLE
Example Application 2
Conclusion
MIS managers today are faced with the task of reconciling two seemingly opposite trends in corporate computing. One is the need to provide secure, reliable, high-quality information to the enterprise. The other is to leverage the power of desktop computing tools. The either-or computing models of the late eighties and early nineties have given way to a new paradigm called Client Host Computing. In this model, the best capabilities of the host and PC are leveraged to provide end users with access to enterprise data via powerful desktop tools. The mainframe excels in making available very large amounts of data to thousands of users. Personal computers allow users to manipulate and present data with ease. This paper suggests that technologies such as Microsoft's OLE and SNA Server connectivity for IBM® enterprise networks can be the glue that connects these two platforms.
The information systems of most large companies are based on mainframe or midrange systems that have slowly evolved over the last couple decades. In the last few years, however, the advances in the microcomputer environment have accelerated at a much faster pace than in host systems, to the point where smaller systems are approaching, and in some cases eclipsing, the sophistication of larger systems. For example, with the acceptance and popularity of the Microsoft® Windows® operating system, the user interface design on the PC is at least five years ahead of the user interfaces on host systems. And, because of the power and sophistication of development tools available on the PC, it is unlikely that host system software will be able to catch up, let alone surpass, the user interface innovations of PC software.
However, there are aspects of host system software that are difficult to duplicate in the PC environment. In most large companies, a stable mainframe-based network is already in place, with access available for all end users. Networks are still relatively new in the PC environment, and are not yet as stable as mainframe networks. Mainframe and midrange computers have sophisticated security systems built in, and access can be strictly regulated. Large systems allow for massive data storage and multitasking computing power far beyond what is currently available in the PC environment. An often overlooked benefit of host-based computing is the centralized business rules. MIS departments have spent decades translating business processes into COBOL procedure divisions. Having these rules stored in one place ensures that all transactions are handled the same way. Recreating these rules correctly, distributing them, and keeping all copies of them synchronized has proved difficult. While a lot of work is being done by companies such as IBM, distributed computing is not yet a reality for the majority of applications and users.
Inertia might be the most significant factor in the favor of host systems. For most large companies, the host system software runs their business. It is not practical to just unplug these systems and replace them with something new, even if the replacement is better.
One solution is to take the best pieces of each environment - the data storage, security, and stability of the host system and the flexibility, development tools, and user interface of the PC - and combine them into a single application. This strategy uses the tools and innovation of client-server technology and applies them to the host environment through the use of terminal emulation software. Terminal emulation software resides on the PC and allows PC users to access the host system as if they were using a stand-alone terminal. Client-host applications take advantage of the API sets included with terminal emulation software to automate interaction with the host system. In traditional terminal emulation, the user sees little difference between interacting with the host system through a PC and interacting through a terminal. In client-host applications, users do not even have to know that the host system exists: They interact with the client-host application, which interacts with the terminal emulator.
An advantage of client-host applications is that the host system applications do not have to change. A program running on a PC using a terminal emulation program can interact with the host without the host knowing it is a program and not a physical end user. There does not have to be any interruption in the processing of the host application, and no development needs to be done on the host. A client-host application can interact with the host software exactly as it is today.
One factor that is moving companies toward development of client-host applications is the trend of end users developing their own applications. Traditionally in large companies, development of applications is done on the host by the company's MIS department. However, lack of sophisticated development tools and high demand for applications has caused a significant backlog in the MIS departments of many large companies. Rather than waiting months or years for the applications they need, many department power users have begun developing the applications on their own, using development tools available on the PC. With this trend, companies are increasingly looking for ways to take advantage of the PC platform in improving and updating their host system applications.
Microsoft's introduction of Visual Basic has put the power of sophisticated Windows application development in the hands of power users. Development of Windows applications is no longer limited to C programmers using the Windows SDK. Not only are applications easier to develop, but development time has been reduced dramatically. It is now possible for a wider range of people to quickly develop client-host applications to fit their own needs. Because of its extensibility features, including custom controls and use of dynamic-link libraries (DLLs), Visual Basic is an ideal tool for client-host development.
There are many different types of client-host applications, ranging from automation of simple tasks, to completely replacing the host system application. The most common types of client-host applications are discussed below, in order of sophistication.
An automation application is a program that automatically performs a task on the host system. These tasks are usually repetitive procedures that are performed frequently by end users-for example, logging on to the host system. An automation application can navigate end users through the host system and leave them at a place where they can begin work. An automation application can also run unattended, automatically performing a task, checking for error conditions, and generating log files. Automation applications can monitor end-user activity in the host application, and take action when a particular event takes place. For the most part, automation applications simply enhance the host system application, making it a little easier for users to navigate. With automation applications, the user is still interacting directly with the host system application. There usually is little or no PC interface; the application just automates a series of processes on the host.
Mainframes can be used as large data storage devices, storing files and documents that are generated and processed by PC applications. Or, there may be files on the host that can be ported into PC applications for editing or report generation. Sometimes, the mainframe is used as a distribution center for PC files, since everyone in the company is able to access the host system. A company's electronic mail system might be based on the host system and some method is needed to transfer files from the host system environment to the PC environment.
Most terminal emulators provide some method of file transfer between the host and the PC. Many companies want a PC application to perform the file transfer automatically to make it easier and more seamless for users to pass data between the host and the PC. File transfer applications can prompt the user for the files to transfer, or do the transfer automatically. They could either require the user to be already logged on to the host system, or could do the whole process for the user. File transfer applications particularly lend themselves to unattended processing. If large files need to be transferred between the PC and the host, or if there is a common set of files that is transferred on a periodic basis, an application can be written to automatically transfer the files without any user intervention. This application could be run unattended at night, so it does not affect the normal response time of the host during the day. Log files can be generated either on the PC or the host, listing which file transfers were completed and whether there were any errors.
In most cases, file transfer applications do not eliminate the need for a user to interact directly with the host system. Typically, there will be applications on the host system that still need to be accessed by users, since not all the necessary information can be conveniently stored in files to be downloaded to the PC.
In companies that have a large PC population, users have become used to working with the Windows graphical user interface and have expectations of the features and behavior of computer software. When host system software does not match these expectations, users become frustrated and avoid working with host system applications. Although the PC programs may be better suited to the tasks they need to perform, there is critical data stored on the host that users must access.
Data integration applications take data from the host system and integrate it with applications on the PC. This is typically done through a macro programming language that is built into the PC software application. The data can be captured from the host and loaded into the PC application where the user can process it. The users work with the data locally, distributing processing from the host to the PC. After the user has manipulated the data, the changes can be sent back to the host. A data integration program can be written so that the user is unaware that the data came from a host system. The users do not need to know how to access the data directly or where it came from; they simply run a macro in their PC application and the data is accessed for them.
A PC front end is a PC-based application that replaces the interface of a host system application. The user interacts only with the PC application, which in turn interacts with the host system application. This is the most sophisticated and time-consuming type of client-host application, since a carefully designed user interface must be developed.
Front-end applications are most beneficial for host system applications that are used daily by end users. These host-system-based applications often have cumbersome user interfaces, and may have been written 10 or more years ago. Some of the data displayed by the host application may no longer be valid, and some panels may no longer be needed. Additionally, users may have to switch between two or more host system applications to get all the data they need.
Developing a PC-based front end gives the opportunity to redesign the way the application works. A new, more appropriate user interface can be implemented. Repetitious or redundant tasks can be automated by the PC application. Information can be gathered automatically from many different sources and presented to the user. A user's productivity can be dramatically enhanced by a properly designed front-end application.
With the introduction of Microsoft Windows, we have become much more aware of the impact of the user interface. Applications for the MSDOS® operating system that were acceptable before now seem cumbersome in comparison. Just the ability to run multiple applications and copy and paste data between them is a major enhancement that has significantly improved user productivity. The common user interface of Windows reduces end-user training and support, since many procedures are the same throughout different applications.
Host system applications, especially in the 3270 and 5250 environments, are far less advanced than PC applications. The user interfaces of most host system applications are five to 10 years behind PC interfaces. When accessing host applications through the use of terminal emulation programs under Windows, the interface differences become strikingly obvious. Everything on the Windows desktop has the same user interface, except for the host system applications. However, these are the applications that many users spend the majority of their time using.
Client-host applications can take advantage of the Windows user interface, while still allowing end users to access host system data. The PC interface can be designed with mouse support, menus, list boxes, drag and drop, and other standard Windows interface features. Not only does this make the application easier for end users, but it gives the host system application the same interface as all the other applications on the Windows desktop.
While host systems typically have security systems already built in, a client-host application can add yet another layer of security. Since the PC program has complete control over the host system application, it can limit user access to only certain areas of the application. It can display only the data that the user needs, and hide security-sensitive information from non-authorized users. Other features, such as prompting for password re-entry after a period of non-activity, can be easily implemented.
Error checking and data verification can be done locally on the PC before any data is sent to the host system. Using Windows controls, users can be limited to entering only valid data. List boxes can be used to force the user to choose data only from a defined list of valid possibilities. Redundant data does not have to be re-entered by the user; it can be sent to the host automatically by the client-host application. The application can present default data to the user to reduce the number of required keystrokes. These error checking techniques can provide data validation far beyond what is currently available on the host system.
Because the user interface of a client-host application follows the same standard design of all Windows-based applications, new users can be trained much faster, since there is only one interface to be learned. A client-host application can be designed so that it is much more intuitive and easier to use than the host system application, decreasing learning time for new users.
Once all users are trained on the new client-host application, support calls should decrease, since the new application is easier to use. Since users no longer interact with the host system directly, they are no longer able to accidentally stumble into an area of the host system with which they are unfamiliar.
Client-host applications can also take advantage of the Help features of Windows to make applications easier to support. Context-sensitive Help can be programmed directly into the application. Also, the Windows Help engine can be used to create powerful and useful Windows help files.
A client-host application can take advantage of the power of the PC by off loading processing that used to be done on the host system. Data can be captured from the host system and processed on the PC to reduce the work that is done on the host. A client-host application can log on, get the data it needs, and then log off, substantially reducing connect time. Some data can be stored locally in the PC environment so that the interaction with the host system can be minimized. Calculations, graphics, and reports that used to be generated on the host can be sent to PC applications for processing.
Application programming interfaces are sets of functions, provided by vendors, that give developers direct access to software applications. An API can allow the developer's program to interact directly with a commercial piece of software, requesting data and executing commands by calling functions in the API. Many Windows-based applications support a specialized API set known as dynamic data exchange (DDE). Windows itself has an API, documented in the Microsoft Windows Software Development Kit (SDK). Some Windows-based applications allow access to API functions through a special Windows file called a dynamic-link library (DLL). Accessing an API function through a DLL is usually more direct than using DDE and gives you more power and flexibility. Visual Basic has both DDE support and DLL support.
In the 3270 environment, there is a standard API, defined by IBM, called the high-level language application programming interface (HLLAPI). This function set was defined when IBM released early versions of its MSDOS-based 3270 emulation program, which allowed users to emulate multiple terminal sessions on their PCs while concurrently running an MSDOS session. Users toggled between terminal and MSDOS sessions with a keystroke combination. IBM also released an entry-level version of its emulation program that only allowed one host session, and an MSDOS session that could not run concurrently with the host session. When the user toggled to the host session, the processing in the MSDOS session stopped. This version came with an API that contained a subset of the HLLAPI functions, not including the functions that required either multiple sessions or a concurrent MSDOS session. This set of functions is known as EHLLAPI.
Other 3270 terminal emulation vendors, such as Attachmate and DCA, adopted one or both of the HLLAPI sets defined by IBM. Since almost every vendor supported at least the EHLLAPI functions, that became the standard API set for 3270. Products that provide the full HLLAPI set give developers more programming power, but calling the functions not included in EHLLAPI may restrict their programs to running only with certain 3270 emulators.
In the Windows environment, the MSDOS-based EHLLAPI function set has been carried over as the standard API for Windows-based 3270 emulators. However, this function set is somewhat limiting in the Windows environment, so some 3270 vendors have provided their own proprietary HLLAPI sets. These Windows-based HLLAPI functions are much more powerful than EHLLAPI and take advantage of the power of the Windows operating system. However, these APIs are not standard among vendors.
Microsoft, along with the leading vendors of Windows-based 3270 emulation products, has proposed a standard HLLAPI for Windows, known as WinHLLAPI. This set of functions is based on EHLLAPI, with some additional functionality added for the Windows environment. Although it is still not as powerful as proprietary Windows HLLAPI sets, it is a standard among different vendors.
Each of the HLLAPI sets gives functions to send keystrokes, capture data from the host screen, initiate file transfers, check the status of the host sessions, as well as many others. Virtually anything that can be done by a user working on a terminal can be duplicated through a program using HLLAPI functions. A limitation of the HLLAPI functions is that a HLLAPI program, just like a user sitting at a terminal, can only capture data that can be displayed on the screen or can be transferred to the PC in a file.
Logical Unit Type 6.2 (LU 6.2) is an IBM-defined SNA protocol for peer-to-peer communications between SNA devices. In contrast, 3270 terminals are based on the LU 2 protocol, which defines a master-slave relationship between the host and the terminal. LU 6.2 allows a terminal to interact with the host on an equal level.
IBM defined an API set for LU 6.2 called advanced program-to-program communications (APPC). This is a set of functions and a communication protocol that allows supported applications to communicate directly with one another. With 3270 HLLAPI, the host has no knowledge the PC program. LU 6.2 APPC requires programs both on the host and on the PC that have knowledge of each other. Each can request information directly from the other. Unlike an HLLAPI program, LU 6.2 applications are not limited only to data that can displayed on a screen. An LU 6.2 program can request any piece of data, as long as the program on the host knows how to respond.
Unfortunately, there is not a standard set of APPC functions (known as verbs) across all SNA devices. APPC on a mainframe system is different from APPC on a midrange system. For this reason, IBM has introduced the common program interface for communications (CPI-C). This is a set of APPC-like verbs that is standard across all SNA devices.
At this point, neither APPC nor CPI-C has gained wide acceptance. There are only a limited number of host applications that provide LU 6.2 support. The host system applications that most companies are interested in writing client-host applications for are usually internal database or order-entry applications. In order for these applications to support LU 6.2, they would need to be completely rewritten. This can be a major development effort, and may not be feasible for many companies.
Microsoft allows Visual Basic to be extended through the support of custom controls. Controls are objects that appear on a window or dialog box, such as buttons, text fields, and list boxes. Visual Basic comes with many standard controls, but vendors and developers can write their own custom controls. To make development of client-host applications quicker and easier, some terminal-emulation vendors provide custom controls that are specific to the 3270 environment. For example, there are custom controls to send keystrokes, transfer files, and capture data. These controls can be easily added to a Visual Basic project to create quick prototypes and simple client-host applications.
There is a limit to the types of applications you can develop using only custom controls. Custom controls do not give you complete control of the data and interactions with the host. Custom controls typically only provide support for the most common types of PC-host interaction. Your application does not have control over the logic of host interaction and error recovery.
For those applications that require more power than custom controls can provide, terminal-emulation vendors provide APIs in dynamic-link libraries. Most emulation vendors support some form of HLLAPI as a DLL. Visual Basic has the capability to link to these DLLs and call the functions in them. This gives the Visual Basic programmer direct access to the functionality of the terminal emulator. Any series of tasks that can be performed by a user can be executed by a Visual Basic program.
Before a function in a DLL can be called by Visual Basic, it must be declared. The Visual Basic Declare statement specifies the name of the function, the name of the DLL it can be found in, and what types of parameters are required by the function. The Declare statement is put in the declarations section of any .BAS module. The syntax for declaring the EHLLAPI functions in Visual Basic is:
Declare HLLAPI Lib "ACS3EHAP.DLL" (Func%, ByVal DataString, Length%, RetCode%)
In this case, ACS3EHAP.DLL is the name of the DLL that contains the EHLLAPI functions. It may have a different name, depending on your terminal emulation program.
Different types of HLLAPI may take different parameters. Windows-based proprietary HLLAPI sets might take parameters that are window handles or long pointers to strings. The variable type of the parameters should be listed in the HLLAPI documentation for your terminal emulation program. The parameters in EHLLAPI are standard across all PC platforms - MS-, Windows, and OS/2®. All EHLLAPI functions require four parameters: the function number, a data string, a length parameter, and a position parameter. Some functions may not use all four of the parameters, but some value must still be passed to the function.
Since there is a variety of different HLLAPI sets, and most vendors support at least EHLLAPI, for simplicity the following information will be restricted to EHLLAPI only.
Each EHLLAPI function has a number associated with it. The function numbers run from 1 to 99, although there is not a function for each number. There are about 35 EHLLAPI functions altogether, depending on which set is being used. The number of a function has little to do with the function's purpose, although similar functions are grouped together. The numbers for some of the most commonly used EHLLAPI functions are listed below:
1 - Connect 7 - GetCursor 2 - Disconnect 8 - GetString 3 - SendKey 40 - SetCursor 4 - Wait 90 - SendFile 6 - Search 91 - ReceiveFile
This parameter is a string that can contain a number of things, depending on the function. In the Connect function, for example, the Data String parameter contains a letter representing the session short name of the host session. This is a letter, A-Z, that identifies each session. In the case of the GetString function, when the function returns, the Data String contains the text that was captured from host.
The third parameter is an integer that usually represents the length of the Data String parameter. Some functions use it for other purposes.
The Position parameter can specify many things, but most often it is used to represent a position on the host screen. Since host screens are character based, screen positions are based on character positions. The character in the upper-left corner is at position 1, the next is at position 2, and so on. If a host screen has 80 columns, the character in the first column of the second row is at position 81.
The Position parameter is also used to store a return code when the function completes. If the function was successful, the value of this parameter will be zero. The parameter will be set to a non zero value if there is an error or the function was not successful.
To capture a string of data from the host screen, the HLLAPI function GetString is used. This is function number 8, and the parameters it requires are a string variable, the number of characters to capture, and the position to start at. To capture 10 characters starting at row 5 column 3, the commands would be:
DataString$ = String(10," ") Position% = (5-1)*80 + 3 EHLLAPI 8, DataString$, Len(DataString$), Position% If Position% <> 0 then MsgBox "Error while capturing data" End if
Calling the Connect function (function 1) is required before calling many of the HLLAPI functions. Connect logically links the HLLAPI application with a specific host session, so that HLLAPI knows which session to interact with. A HLLAPI application can be connected to only one session at a time; however, the Disconnect function (function 2) can be used to disconnect from a session, allowing the HLLAPI application to switch between sessions. The Reset function (function 21) is typically called just before a program exits, and will disconnect any connected sessions.
Example:
Session$ = "A" ' Session short name = A RetCode% = 0 ' Initialize return code EHLLAPI 1, Session$, 0, RetCode% ' Connect to session ' Program Logic EHLLAPI 2, Session$, 0, RetCode% ' Disconnect from session HLLAPI 21, "", 0, RetCode% ' Reset HLLAPI
SendKey (function 3) will send a host keystroke to the terminal session as if a user had typed it. SendKey can also send characters as if they were being typed. To differentiate between characters and keystrokes, there is a set of mnemonics to represent keystrokes as strings. The mnemonics are letters and numbers preceded by the '@' character. For example, a PF1 key is represented by the string "@1". An Enter key is represented by the string "@E". The DataString parameter is set to the string of keystrokes to be sent, and the Length parameter is set to the length of the data string.
Example:
EHLLAPI 1, "A", 0, RetCode% ' Connect to session A EHLLAPI 3, "logoff@E", 8, RetCode% ' Send "logoff" and then an ' Enter key
The Search function (function 6) will search the host screen for a specified string. The string to search for is passed in the DataString parameter, and the position to start searching from is passed in the Position parameter. If zero is passed as the position, the function will search the entire host screen.
Example:
EHLLAPI 1, "A", 0, RetCode% 'Connect to session A RetCode% = 0 EHLLAPI 6, "Ready", 5, RetCode% ' Search the entire ' screen for "Ready"
The CopyString function (function 8) will copy a string of data from the host screen to a string variable in the HLLAPI program. This function requires as parameters a string buffer, the number of characters to copy, and the position to start copying from.
Example:
EHLLAPI 1, "A", 0, RetCode% 'Connect to session A ' Capture 240 characters starting at row 5, column 0 HostString$ = String$(240," ") ' initialize 240 ' character string Position% = 320 ' Start @ 5,0 HLLAPI 8, HostString$, 240, Position% ' CopyString
The Send function (function 90) will transfer a file from the PC to the host. The Receive function (function 91) will transfer a file from the host to the PC. These functions require the DataString parameter to be a string containing the name of the file on the PC, the name of the file on the host, and a list of any file transfer options desired. The example below shows the code to transfer the file QR056.SALES.TEXT from the host to a PC file named SALES.TXT, and store it as an ASCII file.
Example:
Session = "A" HostFile$ = "QR056.SALES.TEXT" PCFile$ = "SALES.TXT" Options$ = "ASCII CRLF" Transfer$ = PCFile$ + " " + Session$ + ":" + HostFile$ Transfer$ = Transfer$ + " " + Options$ HLLAPI 91, Transfer$, Len(Transfer$), RetCode%
The following Visual Basic application uses EHLLAPI.DLL calls to retrieve customer information from a host application.
The EHLLAPI.BAS module of this application contains the declaration for EHLLAPI. This links the Visual Basic application with the EHLLAPI DLL so that the functions can be called. Also, some constants are declared for the function numbers we will be using.
' EHLLAPI Functions Are Called By Passing in a Function Number
Declare Sub EHLLAPI Lib "ACS3EHAP.DLL" Alias "HLLAPI" (Func%, ByVal DataString$, Length%, RetCode%) ' Define constants for each function number Global Const Connect = 1 Global Const Disconnect = 2 Global Const SendKey = 3 Global Const Wait = 4 Global Const CopyScreen = 5 Global Const Search = 6 Global Const GetCursor = 7 Global Const GetString = 8 Global Const QuerySessions = 10 Global Const LockKeyboard = 11 Global Const UnlockKeyboard = 12 Global Const QueryAttribute = 14 Global Const SendString = 15 Global Const WSCTRL = 16 Global Const Pause = 18 Global Const QuerySystem = 20 Global Const ResetSystem = 21 Global Const QueryStatus = 22 Global Const SendFile = 90 Global Const ReceiveFile = 91 Global Const Convert = 99
There is also a function defined, called WaitForString. This function will continue searching the host screen until a specified string appears. This will be useful in determining when the host screen has updated.
Function WaitForString (WaitString$) As Integer EHLLAPI Wait, temp$, 0, Ret% ' wait for host For counter% = 1 To 10 ' search up to 10 times DoEvents ' allow other apps to run Ret% = 1 ' Search at position 1 Length% = Len(WaitString$) ' set string length 'Call search function EHLLAPI Search, WaitString$, Length%, Ret% If Ret% = 0 Then Exit For ' found the string If Ret% <> 24 Then ' didn't find the string MsgBox "Parameter error in WaitForString" End 'fatal error, exit End If DoEvents ' allow other apps to run EHLLAPI Pause, temp$, 2, x% ' wait one second Next counter% If Ret% = 24 Then ' couldn't find string WaitForString = 0 ' function failed Else WaitForString = Length% ' return position where ' string was found EHLLAPI Wait, temp$, 0, Ret% ' wait for host End If End Function
Shown below is the first form of the application as it appears at run time. This form prompts the user for a user ID and password, which are used to log onto the mainframe.
The user types a user ID and password, then clicks the Logon button. The code for the Click event of the Logon button looks like this:
Sub cbLogon_Click () Screen.MousePointer = HourGlass RetCode% = LogonToHost(tbUserID.Text, tbPassword.Text) Customer.Show Screen.MousePointer = Arrow End Sub Function LogonToHost (ByVal UserID$, ByVal Password$) ' Connect to Session A EHLLAPI Connect, "A", 0, RetCode% ' Send A and the Enter Key EHLLAPI SendKey, "A" + "@E", 3, RetCode% ' Wait Until the Logon Screen Appears RetCode% = WaitForString("VMSPREL6") ' Send UserID, Password and the Enter Key Send$ = UserID$ + Password$ + "@E" EHLLAPI SendKey, Send$, Len(Send$), RetCode% ' Wait for the Ready; Prompt RetCode% = WaitForString("Ready;") LogonToHost = True End Function
The Customer form looks like this:
The code that navigates to the customer data screen, looks up the customer information, and copies it to the Visual Basic form is as follows:
Sub cbFind_Click () RetCode% = CustomerFind(tbAcct.Text) End Sub Function CustomerFind (ByVal Acct$) ' Find Customer Information ' Start Host Customer Information Application EHLLAPI SendKey, "CUST" + "@E", 6, RetCode% RetCode% = WaitForString("CS100") ' Enter Customer Account Number EHLLAPI SendKey, "002125" + "@E", 8, RetCode% RetCode% = WaitForString("CS101") ' Get Company Name Field from Host Session TempLen% = 25 Temp$ = Space$(TempLen%) PSPRetCode% = 171 EHLLAPI GetString, Temp$, TempLen%, PSPRetCode% Customer.tbComp.Text = Temp$ ' Get Agent Name Field from Host Session TempLen% = 12 Temp$ = Space$(TempLen%) PSPRetCode% = 205 EHLLAPI GetString, Temp$, TempLen%, PSPRetCode% Customer.tbAgnt.Text = Temp$ ' Get Address1 Field from Host Session TempLen% = 25 Temp$ = Space$(TempLen%) PSPRetCode% = 331 EHLLAPI GetString, Temp$, TempLen%, PSPRetCode% Customer.tbAddr1.Text = Temp$ ' Get Address2 Field from Host Session TempLen% = 25 Temp$ = Space$(TempLen%) PSPRetCode% = 365 EHLLAPI GetString, Temp$, TempLen%, PSPRetCode% Customer.tbAddr2.Text = Temp$ ' Get City Field from Host Session TempLen% = 12 Temp$ = Space$(TempLen%) PSPRetCode% = 491 EHLLAPI GetString, Temp$, TempLen%, PSPRetCode% Customer.tbCity.Text = Temp$ ' Get State Field from Host Session TempLen% = 2 Temp$ = Space$(TempLen%) PSPRetCode% = 508 EHLLAPI GetString, Temp$, TempLen%, PSPRetCode% Customer.tbState.Text = Temp$ ' Get Zip Field from Host Session TempLen% = 5 Temp$ = Space$(TempLen%) PSPRetCode% = 517 EHLLAPI GetString, Temp$, TempLen%, PSPRetCode% Customer.tbZip.Text = Temp$
OLE means integration. Software complexity is growing. It is no longer practical to write everything from scratch each time we develop an application. By using OLE, we can leverage pre-built components, providing more functionality in our application without additional development time.
The following definitions were taken from Microsoft's Object Technology Glossary of terms.
Automation Controller: An Automation Controller is a development tool or application that can drive OLE applications through Automation. Today Microsoft Visual Basic, Visual Basic for Applications, and the Visual C++ development system are all Automation Controllers. Numerous third-party development tools available today are Automation Controllers.
Automation Object: An Automation Object is component software that supports OLE Automation. For instance, Microsoft Excel spreadsheet charts are Automation objects because they can be created and manipulated (that is, automated) by other applications through OLE Automation.
Method: A method is a logical operation provided by an object. Operations performed on objects are defined as "methods of an object."
Property: Properties are the attributes associated with a component object. For example, a chart has the properties of color and type among others.
OLE Automation: OLE Automation allows applications to expose data and services as components for use by other OLE Automation-enabled applications.
Visual Basic and Visual Basic for Applications support OLE Automation. The language elements specific to OLE Automation are discussed below.
Dim: initializes a variable of type Object.
Dim MyCustomer as Object
Create Object: Creates an OLE object of a specified type. In this case we are creating a new object of type AttachmateCustomer and assigning it to the variable MyCustomer.
Dim MyCustomer as Object Set MyCustomer = CreateObject("AttachmateCustomer")
GetObject: Similar to CreateObject, except that instead of creating a new object it gets an existing one.
Set MyCustomer = GetObject("AttachmateCustomer")
To access object methods you would use the . (dot) syntax. For example, to run the Init method of the object MyCustomer, passing in an account number of 002125, you would use the following syntax:
MyCustomer.Init "002125"
To access object properties also use the . (dot) syntax. For example, to copy the Company property from the object MyCustomer to a Visual Basic text box, you would use the following syntax:
Text1.Text = MyCustomer.Company
These language elements are used in the OLE version of the customer sales application.
Microsoft has documented all of the OLE components available within Microsoft Office family of products in the Office Developer's Kit (ODK). There are hundreds of components including: Microsoft Word word processor documents, sections, selections, macros, Microsoft Excel worksheets, charts, and Visual Basic for Applications modules. Other software vendors including Attachmate have begun exposing their product functionality through OLE object models. Instead of offering limited capability via dynamic-link libraries or macro languages, entire products are being opened up for use in customer solutions. For example, Attachmate's EXTRA! for Windows object model will include host session objects, macro objects, connection and configuration objects, all of which will be available to developers for use in their applications. Then instead of worrying about host connectivity, developers can focus on the business problem they are trying to solve.
When designing an application, it's important to have the right division of labor. Programmers who are competent in both communications programming and elegant user interface design are rare. If you've got one, keep him or her happy. Recently Microsoft has been talking about a two-tier development model of component builders and solution builders.
Component builders develop reusable objects, which are then put in a toolbox for use by solution builders. Components can include a customer object, a spreadsheet model, a communications object, etc. Component builders typically focus on lower-level issues including data access, communications, data validation and formatting.
The solutions developer, on the other hand, is focused on delivering business solutions. He or she is tuned into business goals and processes and is less concerned with low-level technology issues. As a user of pre-built components, a customer object for example, the solution builder is not interested in the source of the customer data or its implementation. The solution developer wants to select a few pre-built components and quickly produce a compelling business solution.
LOBjects are OLE components modeled after real-world business entities such as customers, insurance policies, stock trades, and airline seats. LOBjects have properties such as customer.name, policy.premium, stock.tickersymbol and seat.number. LOBject methods are business processes such as customer.notify, policy.renew, stock.buy, seat.assign. Just as a chart object shields developers from having to know how to code 3-D pie chart graphics, LOBjects shield solution developers from having to know where the data is stored or what the underlying access method is. In addition, business logic can be built into the object, ensuring it is implemented the same way each time.
OLE is a key technology in Attachmate's client-host development model. In the customer sales application, we saw user interface, business rules, data access, and communications spread throughout the application. While this application meets the immediate business need, future flexibility is somewhat limited. For example, rightsizing the customer sales application to the SQL Server client-server database management system would mean rewriting most of it because the communications and data access code is tied so closely to the user interface. By leveraging OLE, we can build components that encapsulate the business rules, data access, and communications, separating them from the user interface. As you will see in version 2 of the application, by encapsulating the data source inside of an OLE component, our user interface does not change when we rightsize. The EHLLAPI calls inside the object will be removed and SQL calls will be put in their place. The application and the solution builder see no change in the object's interface or behavior.
Currently OLE components can only be developed in Microsoft Visual C++. Several ISVs are working on development tools that allow creation of OLE components.
Below is a high-level overview of the steps needed to create an OLE component in Visual C++. Please see the Visual C++ documentation for further information.
The following code fragment from the Attachmate Customer Init method illustrates using EHLLAPI calls to navigate to a host screen and copying host fields to AttachmateCustomer properties.
BOOL atmcust::Init(const VARIANT FAR& AccountNumber) { if (AccountNumber.vt != VT_EMPTY) { // Connect to session A int HLLFunc = CONNECTPS; CString HLLDataStr = "A"; int HLLDataLgth, nRet; HLLAPI(&HLLFunc, HLLDataStr.GetBuffer(1), &HLLDataLgth, &nRet); #ifdef _DEBUG wsprintf (szDebug, "AttachmateCustomer::Init - EHLLAPI ConnectPS ret: %d\n", nRet); OutputDebugString (szDebug); #endif ProcessReturnCode(HLLFunc, nRet); m_bConnected = TRUE; // Make sure that we are at the ready prompt CString strWait("Ready;"); if (!WaitForString(strWait)) return FALSE; // Start the customer sales application HLLFunc = SENDKEY; HLLDataStr = "CUST@E"; HLLDataLgth = HLLDataStr.GetLength(); HLLAPI(&HLLFunc, HLLDataStr.GetBuffer(HLLDataStr.GetLength()), &HLLDataLgth, &nRet); #ifdef _DEBUG wsprintf (szDebug, "AttachmateCustomer::Init - EHLLAPI SendKey ret: %d\n", nRet); OutputDebugString (szDebug); #endif ProcessReturnCode(HLLFunc, nRet); // Make sure we reached the customer sales application strWait = "CS100"; if (!WaitForString(strWait)) return FALSE; m_bInSalesApp = TRUE; // Send the objects account number HLLFunc = SENDKEY; HLLDataStr = m_accountNumber + "@E"; HLLDataLgth = HLLDataStr.GetLength(); HLLAPI(&HLLFunc, HLLDataStr.GetBuffer(HLLDataLgth), &HLLDataLgth, &nRet); #ifdef _DEBUG wsprintf (szDebug, "AttachmateCustomer::Init - EHLLAPI SendKey ret: %d\n", nRet); OutputDebugString (szDebug); #endif ProcessReturnCode(HLLFunc, nRet); // Wait for the customer record to appear strWait = "CS101"; if (!WaitForString(strWait)) return FALSE; // Fill in the object data with customer data HLLFunc = COPYPSTOSTRING; HLLDataLgth = 25; int HLLPSPos = 171; HLLAPI(&HLLFunc, HLLDataStr.GetBuffer(HLLDataLgth), &HLLDataLgth, &HLLPSPos); #ifdef _DEBUG wsprintf (szDebug, "AttachmateCustomer::Init - EHLLAPI CopyPSToString ret: %d\n", nRet); OutputDebugString (szDebug); #endif ProcessReturnCode(HLLFunc, HLLPSPos); m_company = HLLDataStr; HLLDataLgth = 12; HLLPSPos = 205; HLLAPI(&HLLFunc, HLLDataStr.GetBuffer(HLLDataLgth), &HLLDataLgth, &HLLPSPos); ProcessReturnCode(HLLFunc, HLLPSPos); #ifdef _DEBUG wsprintf (szDebug, "AttachmateCustomer::Init - EHLLAPI CopyPSToString ret: %d\n", nRet); OutputDebugString (szDebug); #endif m_agent = HLLDataStr; HLLDataLgth = 25; HLLPSPos = 331; HLLAPI(&HLLFunc, HLLDataStr.GetBuffer(HLLDataLgth), &HLLDataLgth, &HLLPSPos); #ifdef _DEBUG wsprintf (szDebug, "AttachmateCustomer::Init - EHLLAPI CopyPSToString ret: %d\n", nRet); OutputDebugString (szDebug); #endif ProcessReturnCode(HLLFunc, HLLPSPos); m_address1 = HLLDataStr; HLLDataLgth = 25; HLLPSPos = 365; HLLAPI(&HLLFunc, HLLDataStr.GetBuffer(HLLDataLgth), &HLLDataLgth, &HLLPSPos); #ifdef _DEBUG wsprintf (szDebug, "AttachmateCustomer::Init - EHLLAPI CopyPSToString ret: %d\n", nRet); OutputDebugString (szDebug); #endif ProcessReturnCode(HLLFunc, HLLPSPos); m_address2 = HLLDataStr; HLLDataLgth = 12; HLLPSPos = 491; HLLAPI(&HLLFunc, HLLDataStr.GetBuffer(HLLDataLgth), &HLLDataLgth, &HLLPSPos); #ifdef _DEBUG wsprintf (szDebug, "AttachmateCustomer::Init - EHLLAPI CopyPSToString ret: %d\n", nRet); OutputDebugString (szDebug); #endif ProcessReturnCode(HLLFunc, HLLPSPos); m_city = HLLDataStr; HLLDataLgth = 2; HLLPSPos = 508; HLLAPI(&HLLFunc, HLLDataStr.GetBuffer(HLLDataLgth), &HLLDataLgth, &HLLPSPos); #ifdef _DEBUG wsprintf (szDebug, "AttachmateCustomer::Init - EHLLAPI CopyPSToString ret: %d\n", nRet); OutputDebugString (szDebug); #endif ProcessReturnCode(HLLFunc, HLLPSPos); m_state = HLLDataStr; HLLDataLgth = 5; HLLPSPos = 517; HLLAPI(&HLLFunc, HLLDataStr.GetBuffer(HLLDataLgth), &HLLDataLgth, &HLLPSPos); #ifdef _DEBUG wsprintf (szDebug, "AttachmateCustomer::Init - EHLLAPI CopyPSToString ret: %d\n", nRet); OutputDebugString (szDebug); #endif ProcessReturnCode(HLLFunc, HLLPSPos); m_zip = HLLDataStr; } return TRUE; }
The following Visual Basic application uses OLE Automation to retrieve customer information from a host application. EHLLAPI calls have been encapsulated inside the customer object. The Logon functions in both sample applications are the same. However, the CustomerFind functions are different.
Function CustomerFind (ByVal Acct$) ' Find Customer Information ' Create Customer Object Set MyCustomer = CreateObject("AttachmateCustomer") ' Run the Init method passing in the customer account number. ' The Init method navigates to the customer screen in the ' host application and enters the customer account number. ' It then copies data fields from the host screen and stores ' them as properties of the object. MyCustomer.Init tbAcct.Text ' Assign the object's Company Name property to a VB text box Customer.tbComp.Text = MyCustomer.Company ' Assign the Agent Name property to a VB text box Customer.tbAgnt.Text = MyCustomer.Agent ' Assign the Address1 property to a VB text box Customer.tbAddr1.Text = MyCustomer.Address1 ' Assign the Address2 property to a VB text box Customer.tbAddr2.Text = MyCustomer.Address2 ' Assign the City property to a VB text box Customer.tbCity.Text = MyCustomer.City ' Assign the State property to a VB text box Customer.tbState.Text = MyCustomer.State ' Assign the Zip property to a VB text box Customer.tbZip.Text = MyCustomer.Zip End Function
Notice that all of the EHLLAPI code has moved from the Visual Basic application (the solution) into the customer object (the component), vastly simplifying the interface code.
The rightsizing trend is being driven by two forces. First, users need access to more information than ever. Second, they need more powerful and flexible tools to manipulate and present this data. By fully leveraging PC technology including host connectivity software, graphical development environments, and OLE, corporate developers can provide solutions that meet these business needs.
© 1995 Microsoft Corporation.
THESE MATERIALS ARE PROVIDED "AS-IS," FOR INFORMATIONAL
PURPOSES ONLY.
NEITHER MICROSOFT NOR ITS SUPPLIERS MAKES ANY WARRANTY, EXPRESS
OR IMPLIED WITH RESPECT TO THE CONTENT OF THESE MATERIALS OR THE
ACCURACY OF ANY INFORMATION CONTAINED HEREIN, INCLUDING, WITHOUT
LIMITATION, THE IMPLIED WARRANTIES OF MERCHANTABILITY OR FITNESS
FOR A PARTICULAR PURPOSE. BECAUSE SOME STATES/JURISDICTIONS DO
NOT ALLOW EXCLUSIONS OF IMPLIED WARRANTIES, THE ABOVE LIMITATION
MAY NOT APPLY TO YOU.
NEITHER MICROSOFT NOR ITS SUPPLIERS SHALL HAVE ANY LIABILITY FOR
ANY DAMAGES WHATSOEVER INCLUDING CONSEQUENTIAL INCIDENTAL, DIRECT,
INDIRECT, SPECIAL, AND LOSS PROFITS. BECAUSE SOME STATES/JURISDICTIONS
DO NOT ALLOW THE EXCLUSION OF CONSEQUENTIAL OR INCIDENTAL DAMAGES
THE ABOVE LIMITATION MAY NOT APPLY TO YOU. IN ANY EVENT, MICROSOFT'S
AND ITS SUPPLIERS' ENTIRE LIABILITY IN ANY MANNER ARISING OUT
OF THESE MATERIALS, WHETHER BY TORT, CONTRACT, OR OTHERWISE SHALL
NOT EXCEED THE SUGGESTED RETAIL PRICE OF THESE MATERIALS.
![]() |
Click Here to Search TechNet Web Contents | TechNet CD Overview | Microsoft TechNet Credit Card Order Form At this time we can only support electronic orders in the US and Canada. International ordering information. |
©1996 Microsoft Corporation |