Agents: Not just for Bond anymore

Learn what agents are and how to create them using IBM's Aglet Workbench

1 2 3 Page 2
Page 2 of 3
User passivity/data timeliness
Applications that demand immediate reaction to incoming streams of real-time data, regardless of whether the users are at their desk or not, fit well into an agent-based architecture. This is perhaps the classic application of agents, whereby the agent acts as a digital proxy for a human user, interacting with incoming data streams on the user's behalf. A good example of such an application is outlined below in the section on distributed searching.
Multi-staged/multi-processed calculations
Cumbersome calculations often can be broken into discrete units for distribution among a pool of servers or processors. Each of these discrete units can be assigned to an agent, which is then dispatched to an "agent farm," where the work is actually performed. Upon completion, each agent can return home and the results can be aggregated and summarized. An example of such an application appears below in the virtual supercomputer section.
Untrusted collaborators
Mobile agents can collaborate with other agents by meeting in pre-specified "neutral turf." These agents could be from different product groups within the same organization or even from different, possibly competing, companies. Like distributed objects, agents communicate through well-defined interfaces and are usually protected from intrusion or inspection by other agents by the agent host. Unlike distributed objects, however, a compromised agent rarely poses a security threat to the owner's network, since the agent does not have access to internal network resources until it returns home. Even then, it can be barred access to networked resources by the agent host.
Low-reliability/partially-disconnected networks
In systems with low-reliability or frequently disconnected networks, agents can save network retries by moving the executable content to the data source rather than repeatedly attempting network connections to the data source. An example of such an environment is one in which a majority of users rely on notebook computers networked via dial-up connections. Prior to disconnecting from the network, agents can be sent to a server to perform offline calculations. Upon reconnecting, the agents can be recalled to the notebook machine for local execution and a manipulation.

Agent services and tools

A variety of product and services companies offer agent-based solutions. Most of these advertise the ability to sift through newsfeeds and Web sites for information, retrieving interesting content offline for rapid perusal. PointCast and BackWeb exemplify this model in product offerings of the same names. My Yahoo! offers similar functionality as a service. The FireFly network takes this model a step further by attempting to introduce people with similar interests in music and video through online chat and discussion groups.

On the tools side, no discussion of agents is complete without mention of General Magic and its Telescript technology. Now in its fifth year of business, this progeny of Apple, Sony, Motorola, and AT&T has impressively regrouped after the disappointing lack of market acceptance of its super-cool, albeit proprietary, Magic Cap operating system. Tabriz, General Magic's latest technology offering, provides Internet wrappers around the company's Telescript agent scripting language and API. This time around, General Magic is opening up -- offering free Tabriz SDKs to any developer with a pulse and a business card. General Magic's newfound openness may be an example of "too little, too late," however, as Java's widespread acceptance threatens to unseat Telescript as the agent-creator toolbox.

Why Java makes the perfect agent language

Java's network-centricity, sandbox security model, and platform independence make the language a perfect environment in which to development agent-based tools. One such tool, IBM's Aglet Workbench, currently in alpha release, provides a laboratory for creating Java-based mobile agent applications. The Aglet Workbench defines its own Java agent API (which has been submitted to standards committees) and provides a set of tools and samples for getting started.

The term aglets is a play on words between agents and applets. There are threads of similarity (no pun intended) between Java's applet model and the IBM aglet environment. These similarities are thoroughly explored by the venerable Bill Venners, in his companion Under the Hood column in this issue of JavaWorld.

Aglets Workbench tutorials

To further our exploration of mobile agents, the final sections of this article provide a series of tutorial applications written using IBM's Aglets Workbench. To use the tutorials, you should download and install the Aglets Workbench. The documentation and provided examples (which are quite good for an alpha release) should be sufficient for readers with enough background with aglets to get started with these tutorials. It is recommended that you test drive the Tahiti aglet server with a few of the bundled samples prior to digging into the tutorials.

Links to the Aglets Workbench and other information pertaining to this product are provided in the Resources section of this article.

Distributed searching

Imagine a mobile agent that crawls the Web, searching for interesting tidbits of information. Jumping from Web site to Web site, a distributed searching agent can execute a predefined set of behaviors upon finding content of note after scanning it with a predetermined heuristic.

Contrast this to today's popular search engines, like Yahoo!, Alta Vista, or InfoSeek. These services collate and index Web-based material in a centralized data repository for searching via Web-based interfaces. After visiting one of these sites and ingesting your daily dose of Webvertising, you are given access to a search facility. Finding content in this manner requires an active presence on the part of the user. When JavaSoft releases a new API specification at its Web site (www.javasoft.com), it eventually will be found and indexed by the search engine Web crawlers, and queries to the search engine will start returning pointers to the new document.

But what if I need immediate notification of new API specifications from JavaSoft? I can't realistically expect to visit JavaSoft or execute a search engine query with the magic keywords more than once or twice a day. What is needed is an agent that will monitor Web sites for me and notify me when new APIs are released. There are several Web utilities and services that promise this capability, a few of which are noted in the preceding section, Agent services and tools.

Is distributed searching a good application of mobile agents? Using the parameters defined above, passivity, timeliness, and untrusted collaborators are all features of a system that provides distributed Web searching services. The agents must run without human intervention, notify their owners immediately upon finding items of interest, and execute in a domain of distrust -- the Internet. So, yes, this does appear to be a system that fits well within the mobile agent model. Let's prototype such a system using IBM's Aglet Workbench.

How to design an agent application

The first step in designing an agent application is to identify and model the entities inherent in the system. For our distributed searching system, we will model two classes of agents, Publishers and Searchers. Upon creation, a Searcher agent makes a note of the document it is searching for and registers interest in messages emanating from Publishers about new document publications. Using the aglet API, the Searcher's onCreation() event would look as follows:

s

    public void onCreation(Object init) {
        // Create a new document for which this agent will search.
        if (init == null) {
            desiredDocument = new Document();
        } else {
            desiredDocument = new Document((String)init);
        }
        // Subscribe to Publisher NewDocumentAlert messages.
        try {
            subscribeMessage("NewDocumentAlert");
        } catch (Exception e) { e.printStackTrace(); }
        report("Created (keyword: " +
               desiredDocument.getKeyword() +
               ").");
    }

The single behavior of a Searcher, testDocument(), is triggered when a new document is published by a Publisher. As we will see in a moment, Publishers tell the world about new documents by broadcasting NewDocumentAlert messages, to which our Searchers have subscribed in the above onCreation() handler. The message handler and testDocument() behavior for a Searcher are defined by the following code fragments:

    public boolean handleMessage(Message msg) {
        // Handle newly published documents.
        if (msg.kind.equals("NewDocumentAlert")) {
            testDocument((Document)msg.getArg("Document"));
            return true;
        }
        return false;
    }
    public void testDocument(Document newDocument) {
        // Compare the newly published document with the
        // document for which the agent is searching.
        if (newDocument.matches(desiredDocument)) {
            // If they match, report so and go away.
            // In a real system, the creator of the Searcher agent
            // might be notified via e-mail or other means.
            report("Found desired document (keyword: " +
                   newDocument.getKeyword() +
                   ").");
            try {
                dispose();
            } catch (InvalidAgletException e) { e.printStackTrace(); }
        }
    }

As the comments in testDocument() indicate, a real Searcher agent probably would want to do more than vaporize itself upon finding its desired documents. For the purposes of this prototype, however, the Searcher will do just that and no more. A full-fledged Searcher also might migrate to other Web sites after unsuccessfully searching for a given period of time. These enhancements are left as an exercise for the reader. For now, the entire source of the prototype Searcher can be found in Searcher.java.

Now that we've defined Searcher, let's code its counterpart, Publisher. Publisher's onCreation() event simply registers interest in Timer events, which are described below:

    public void onCreation(Object init) {
        // Subscribe to Timer events, which will notify the simulated
        // Publisher to create new documents at regular intervals.
        try {
            subscribeMessage("Timer");
        } catch (InvalidAgletException e) { e.printStackTrace(); }
    }

In order to simulate the passage of time (deadlines perhaps), a static Timer agent needs to be defined. This is a simple agent that endlessly sleeps for a few moments and then broadcasts "clock tick" events to those interested in consuming them. The source for Timer can be found in Timer.java.

In Publisher, the consumption of timer events triggers the publishNewDocument() behavior. The source fragments for Publisher's message handler and publishNewDocument() behavior read as follows:

    public boolean handleMessage(Message msg) {
        // Upon each Timer tick, publish a new document.
        if (msg.kind.equals("Timer")) {
            publishNewDocument();
            return true;
        }
        return false;
    }
    public void publishNewDocument() {
        // Create a new document.
        Document document = new Document();
        report("Publishing new document (keyword: " +
               document.getKeyword() +
               ").");
        // Broadcast a message that a new document has been
        // published.
        Message alertMsg = new Message("NewDocumentAlert");
        alertMsg.setArg("Document", document);
        try {
            getAgletContext().multicastMessage(alertMsg);
        } catch (InvalidAgletException e) { e.printStackTrace(); }
    }

As the comments above indicate, publishing a new document entails creating the document and then advertising to the world that it exists by broadcasting a NewDocumentAlert message to all interested parties. In our model, these messages are consumed by Searcher's message handler, the code for which we've already seen. The complete source code for Publisher can be found in Publisher.java.

To launch simulations inside of the Tahiti aglet server, it usually is helpful to create a utility agent that automatically spawns a small set of agents. A typical spawner for our distributed searching system has been provided in DistributedSearchingDemo.java.

Distributed searching agents that simply notify their owners of success fall short of exercising the full capabilities of mobile agent technology. In addition to just shouting "Eureka!," mobile agents can go one step further and act on new information in real time. For example, this Distributed Searching example could be extended to simulate a stock market or commodity exchange.

In a way, stock and commodities markets are one massive search engine: Prospective buyers of a particular asset scour the marketplace for sellers willing to part with their goods for a given price. But the buyers and sellers don't just shake hands after negotiating a price; they conduct the business of transferring funds and certificates of ownership. These buyers and sellers could be digital, and most often are in contemporary exchanges.

The entire source for this example is listed below. In addition to the classes defined previously, I've included Document.java, which is used to define a data structure representing documents.

A virtual supercomputer

In the January 1997 edition of JavaWorld, Laurence Vanhelsuwe explored the possibilities of using Java applets as a means of distributing computations across a pool of machines in his article "Create your own supercomputer with Java". By delegating discrete sub-tasks to a cluster of browsers, large computations can be partitioned, executed, and reassembled into the Answer, whatever that might be. Vanhelsuwe's DAMPP (distributed applet-based massively parallel processing) applets are in fact mobile agents of sorts. They have behaviors (defined by the methods of the applets), state (the piece of the Answer that they are working upon), and location (they can be thought of as migrating from a Web server to a Web browser). As Vanhelsuwe demonstrates, mobile agents provide a good foundation for implementing parallel processing systems.

Let's build a simple parallel processing system that factors integers by distributing the work across a cluster of IBM Tahiti aglet servers. To do this, we will build upon the master/slave pattern included in the Aglets Workbench. As you might suspect, this pattern involves a master aglet spawning one or more slave aglets to perform specific tasks. In this example, this task is to factor a single number. By spawning multiple number-factoring slaves, a single master can distribute processing load to a number of aglet servers.

First, we will define the slave aglet, which we will call Laborer. This aglet's sole responsibility is to factor a single number and then return home to its master. To use the aglet master/slave pattern, slave aglets must descend from ibm.aglets.patterns.Slave. Upon creation, our Laborer aglet must initialize itself; this is done in initializeJob():

public class Laborer extends Slave {
    long numberToFactor;
    Vector factors;
    // Store number to factor and initialize factors Vector
    public void initializeJob() {
        numberToFactor = ((Long)ARGUMENT).longValue();
        factors = new Vector();
    }

Again, the bailiwick of Laborer is to factor numbers. The events and behaviors required to do this task are defined below:

1 2 3 Page 2
Page 2 of 3