Editor’s Note: For many AS/400 shops, the cost of learning an entirely new language is too high, even when the benefit is the brass ring of e-business. It’s difficult to justify retraining your entire staff without a concrete payback. It would make better business sense to gradually move to Java, without entirely disrupting your day-to-day business. In this article, Joe Pluta explains the concept of encapsulation, which hides the complexity of a new language behind an easy-to-learn interface. His JDB/400 package (which is free on the Web) allows RPG programmers to use familiar RPG op codes, such as SETLL, READE, and UPDAT, to access AS/400 data from Java programs and to develop e-business applications that use the logic of existing legacy programs.
I’ve been listening lately as the discussion about Java, pro and con, has waged throughout boardrooms, lunchrooms, and chat rooms. The debates are held at the highest levels of technical expertise and are often fraught with esoteric terminology, but the general consensus is shaping up to be that—and pardon my technical jargon—Java is “a nice place to visit, but (most programmers) wouldn’t want to live there.”
I admit that I’m in the minority here. I think Java is going to play a major role in software design in the new millennium. But somehow, having that opinion makes me a fanatic (OK, that and the fact that I spend a lot of my spare time writing and giving away free Java software). To the majority of programmers, we Javaphiles fall into one of two camps: Either we declare Java to be the vanguard in the holy crusade against Mighty Bill and his minions, striding alongside Sir Linux to slay the Microsoft dragon, or we consider Java to be the One and Only True Language, brought down from on high to sweep aside the Babel of high-level languages that has kept us from our true calling.
The truth is that neither of these is the truth. Java is an extremely robust and powerful language designed from the ground up to provide platform-independent object- oriented programming today. It has no magical powers and won’t grow hair or remove unsightly blemishes. But what Java will do is bring the power of platform-independent object-oriented programming into the hands of any programmer who wants it.
What sort of power? Object-oriented techniques bring certain benefits to software design. Among these are code reuse and encapsulation. The advantages of code reuse are well documented: reduced development time, reduced debugging time, and fewer bugs.
However, even more important to software design, in my opinion, is the concept of encapsulation. In this article, I focus on a simple example of encapsulation and the power it can have.
Keeping It Simple
For many years, RPG evolved very slowly, with incremental additions to the language designed to disrupt legacy code as little as possible. Therefore, legions of RPG programmers have happily transitioned from one version to the next, learning some new skills but doing so with a sense of comfort about their old abilities. This gentle forward movement had been crucial to the long-term success of RPG as a language.
RPG IV changed all that. With its new look and new features, RPG IV is a radical departure from the RPG of old. And we’ve seen how difficult it’s been for some programmers to make the move from RPG III to RPG IV. I’m no exception; I still write much of my RPG code using the RPG III style and syntax, and while I can rationalize that it’s because most of my clients still use RPG III almost exclusively, there’s also a bit of discomfort with the new RPG syntax. I like my columns nice and tidy.
Add to that the new complexities of the OS/400 APIs (and the associated data structure specifications), and RPG IV becomes a perfect example of a putting a little something for everyone in one bag. To IBM’s credit, this approach has always been their philosophy. Rather than provide half an interface, they tend to go to the other extreme and provide a solution that supports every conceivable situation. We programmers then have to live with that complexity, and some of us just don’t have the time to master everything.
This is where encapsulation becomes so important. One person in an organization can be appointed to learn a given API and determine how it needs to be used. That person can then write a “wrapper” program that accepts a few simple parameters and then does all the work of formatting the API data structures, calling the program, and deciphering and returning the results. This is encapsulation.
IBM’s Java Toolkit for the AS/400
IBM’s Java Toolkit for the AS/400 is another shining ex-ample of an incredibly robust set of APIs that can be utterly incomprehensible to the casual user. Don’t get me wrong; it is my opinion that “the toolkit,” as it’s often called, is one of the best pieces of free software available today. Used properly, the toolkit provides access to nearly every AS/400 service imaginable, from user profiles to data queues to record-level access functions. The problem lies in the fact that because it allows so many options, it is difficult to determine which options to use. Encapsulation is the key, and in this article, I encapsulate the record-level access functions.
Take a look at a simple piece of RPG code that will read the file QRPGSRC until end of file (Figure 1). As you can see, it’s a simple routine. The toolkit allows you to write Java code that does exactly the same thing. The only problem is that it requires several more lines of code (Figure 2). As you can see, the code is quite a bit more complex and far less understandable. To give the toolkit some credit, however, this same code will run without change on either the AS/400 or a workstation connected to the AS/400 via TCP/IP.
But the cost for such connectivity seems a little high. For example, among the things the Java code must do are establish a connection with the AS/400 database, convert the AS/400 file name to an AS/400 Integrated File System (AS/400 IFS) path name, and determine the record format to use. The RPG compiler automatically does that sort of work for you. In effect, the RPG compiler encapsulates much of the work in creating database applications.
Well, since Java is an object-oriented language, a programmer who understands the details of the record-level access classes should be able to create classes that encapsulate all those details and should, in theory, be able to create classes that mimic the simpler RPG syntax.
Enter JDB/400
I’ve written several Java packages, which you can download from my free software site at www.zappie.net. You can go directly to the download page at www.zappie.net/java/techniques/pbd.htm to get the latest version of pbd.jar (Version 1.2P at this writing), and you can also join the mailing list here. One of the packages in pbd.jar is JDB/400, a Java package designed to hide the details of record-level access behind classes that support basic AS/400 and RPG syntaxes. For example, operations such as READ, WRITE, CHAIN, and UPDAT are implemented along with support for key lists and partial keys. By simply declaring a file (using standard AS/400 library/file syntax) and then executing the READ() method repeatedly, one can read through a file using the same logic as in the original RPG program. Figure 3 shows the Java code required using the JDB/400 routines. The code fragment actually requires fewer lines of code than the original RPG!
The idea is simple. The common logic used to access AS/400 files via the record- level access classes is already coded within the JDB/400 classes. The Jdb400File class, which is the superclass of all the JDB/400 file classes, provides basic support, such as connecting to the AS/400 and determining the correct AS/400 IFS path name. Note that JDB/400 currently supports only files with a single record format, which covers most database applications. If you need to support multiple formats, feel free to extend or modify the class yourself—source is provided for all classes. (Extensibility is another key feature of object-oriented design; unfortunately, I don’t have the time to dive into those waters in this article.) Other classes inherit the base behaviors of connection and file naming and add specific behavior for that class. For example, the Jdb400SequentialFile class supports a CHAIN() method to retrieve a record with a specific record number. Meanwhile, the Jdb400KeyedFile class also supports a CHAIN() function, but it requires a key field or a key list. The Jdb400KeyedUpdateFile and Jdb400SequentialUpdateFile classes support the DELET(), UPDAT(), and WRITE() methods.
Using these classes, you can quickly develop applications that mimic the business logic of your existing legacy applications. But there’s a subtle difference: Once the encapsulating classes are written and debugged, application programmers need never worry about them. No code is “cloned”; instead, the JDB/400 classes are automatically incorporated into the application, much in the same way that the RPG compiler incorporates its initialization and file handling code.
What this means is that only one programmer need be assigned the task of learning the internal functions of the toolkit; that person’s knowledge is then disseminated through the encapsulating classes. And in the case of JDB/400, it’s already written and freely available, so you don’t need to assign any additional resources, unless you want to be able to extend the classes yourself someday.
Encapsulation: Not Just for Database Access
After I had the JDB/400 classes written, it became obvious that if I wanted to create a real “RPG-like” development environment, I’d have to write more classes to support other functions. For example, I’d need to develop classes to mimic the behavior of display files. This effort eventually became the Java Blockmode User Interface (JBUI) package (also available at www.zappie. net). JBUI supports concepts such as output and entry fields, screens, buttons, com-mand keys, and errors. The amount of code required to write a graphical interface that mimics a simple 24-by-80 character-based screen is surprisingly large. (Well, it takes a large amount of code to do it with some aesthetic appeal, anyway.) Rather than a simple fixed-font re-creation of typical AS/400 screens, JBUI uses the features of Java, and especially Swing, as often as possible. Subfiles are represented as tables, not simply rows of fields. This sort of design, although difficult, began to pay off when I realized that the package would have to support building screens dynamically.
Because I was using the standard Java classes, it was fairly easy to add scrolling to panels that were too large.
The JBUI package is several times the size of the JDB/400 package, but once again, because it is already written and available for download, you don’t have to reinvent the wheel. And if you need to change some of the basic behavior of the package, you need to have only one good, solid programmer study the internal workings of the package. If done correctly, any changes made by that person will automatically enhance the programs written by your application programmers.
After I had the JBUI package working, I realized that I should write some real database applications combining JBUI with JDB/400. However, a funny thing happened as I was writing. I began to notice that many of the calls to these encapsulating classes could indeed be encapsulated themselves. This was the first step toward the development of the JAO/400 package (again, at www.zappie.net). JAO (for Java Application Objects) is designed to provide a standard way to develop applications. JAO/400 is an example of a “frameworks” package. Frameworks are the ultimate expression of encapsulation. The designer distills that portion of a given application that is common across implementations and provides base classes with minimal functionality in support of that application. In the case of JAO/400, I wanted to design classes that would support basic business applications. The implementer could then add site-specific extensions to the base classes.
One of the primary requirements of business systems is the ability to inquire into and modify master files. To that end, I developed some classes to support single-file lists and single-record display panels. Jao400List is a data list panel similar to a subfile, and Jao400Display is a detail panel. I began to experiment with linking the JDB/400 information to the JBUI screens and came up with a way to automatically retrieve the characteristics of an AS/400 file and translate it directly into JBUI screen fields without actually having to define each individual field. Implementing a JAO/400 class became simply defining the AS/400 file name and the field names I needed to work with. You may notice a trend here: You can tell that your object-oriented programming is going correctly when your interfaces become simpler rather than more complex.
Because of encapsulation, common functions tend to be combined and interfaces between those functions are hidden. The best example of this to date is the Jao400Split class. Jao400Split is the culmination of a year of research and development. It’s still a fairly simple class, but it’s also very powerful. It takes advantage of all the strengths of Java but still works pretty closely with the old 24-by-80 paradigm. A Jao400Split is a split panel, with the left pane being a record list and the right pane being the details for the selected record. The primary acquiescence to the GUI paradigm is that record selection is a double-click rather than a selection code and a command key. Figure 4 shows a Jao400Split panel that has been extended to display the Shop Order file from System Software Associates’ (SSA’s) BPCS. The class is called FSOSplit and requires a grand total of 16 lines of code, 4 of which are blank and 3 of which consist only of a closing brace.
The code for the FSOSplit class is shown in Figure 5 in its entirety.
Division of Labor: Divide and Conquer
I hope this article gives you a glimpse of how encapsulation can dramatically improve your productivity. By designing your classes so that different areas of expertise are encompassed in different levels of the hierarchy, you can actually begin to divide your workload in a rational manner and allow your programmers to become subject-matter experts. In the examples in this article, one package requires in-depth knowledge of the record-level access classes but little else; one package requires strong understanding of graphical and nongraphical user interfaces; and one package requires an understanding of business applications. Even though I wrote all three, there is no reason each package couldn’t have been developed independently and linked together. And the result is a set of
classes that even a novice Java programmer can use to create sophisticated, robust client/server applications. This is the power of encapsulation.
FQRPGSRC IF E DISK
C READ QRPGSRC 90
C *IN90 DOWEQ*OFF
C EXSR PROCES
C READ QRPGSRC 90
C ENDDO
Figure 1: This simple piece of RPG code reads QRPGSRC until end of file.
AS400 system = new AS400();
String filePath = (new QSYSObjectPathName(“%LIBL%”, “QRPGSRC”,
“FILE”)).getPath();
SequentialFile file = new SequentialFile(system, filePath);
try {
system.connectService(AS400.RECORDACCESS);
RecordFormat format =
(new AS400FileRecordDescription(system,
filePath)).retrieveRecordFormat()[0];
file.setRecordFormat(format);
file.open(AS400File.READ_ONLY, 100,
AS400File.COMMIT_LOCK_LEVEL_NONE);
Record record;
while((record = file.readNext()) != null)
process(record);
}
catch (Exception e) {
System.out.println(e);
}
Figure 2: The Java code required to read the same QRPGSRC file as Figure 1 is more complex.
Jdb400File file = new Jdb400SequentialFile(“QRPGSRC”);
while (file.READ()) {
process(file.getRecord());
}
Figure 3: The Java code using JDB/400 routines requires fewer lines of code than the original RPG.
LATEST COMMENTS
MC Press Online