From the book: Integration-Ready Architecture and Design, by Cambridge University
Press, ISBN 0521525837, Jeff Zhuk, 2004. Subtitle: Software Engineering with XML, Java, .NET, Wireless, Speech, and Knowledge Technologies; http://www.amazon.com/exec/obidos/tg/detail/-/0521525837 http://javaschool.com/about/publications.html

 

Can people think? – Maybe... At least not in the way we do…

– Computer-to-computer chat

Chapter 13

Integration with Knowledge

This chapter reveals the dependencies between a natural user interface (NUI) and knowledge technologies; discusses architecture, design, and code samples that integrate knowledge technologies into enterprise applications; and gives the keys to a new breed of software – “Softology,” a mix of software and ontological engineering.

We talked about NUIs in the previous chapter and agreed that they are not a trivial pursuit. We discussed at length a small part of an NUI – current speech technologies – and ended up with the conclusion that they can do a decent job when using machine-directed dialogs with multiple choices but are not quite ready to understand natural language spoken by a person.

We face similar difficulties with machine translation from foreign languages. I worked with multiple language translation programs that produced nonsense text filled with the right words.

Why Are Computers Stupid? What Is Missing?

Can tasks such as machine vision, speech recognition, and foreign language translation, which all seem very different, have a common solution?

The first common denominator is easy to find: all these tasks belong to the field of data interpretation. The next move is to find common steps for all three activities. What do people do when they are engaged in image or speech recognition, when they translate text from Hebrew to English? Why can’t we build a program to perform similar steps?

The very first step is to recognize a business (social) domain area in which the data belong. For example, it is impossible to translate an article written in a foreign language (assuming you know the language) before you know if it is about medical science or cooking. It is easier to recognize the voice of a speaker with an identified name and a related speaker’s voice profile. Direct topic pointers or metadata may be very helpful in solving recognition programs.

The second step is to find a set of conceptual models related to this topic. Then, take one piece of data at a time and dive into these models with the data, trying to select the best one.

Every model has its own set of patterns. The third step is to retrieve these patterns (expected choices) and try to find a match between the data and the patterns.

Was that a joke? Can these three steps really solve all three puzzles? The funny thing is, it was not a joke.

Where are the pitfalls that delay building intelligent machines?

Note that the most valuable asset here is this set of models and their internal patterns. Where do they come from?

We human beings slowly develop skills to create conceptual models. We obtain multiple models in different subject areas during our lifetime. We sometimes call this process “becoming a professional” in a related area. We never start from ground zero; from the very beginning, we have an extremely powerful background ready for this work. Information we collect and process lives on top of this rich background and is associated and connected with pre-existing data.

This is the major difference between our modeling programs and us. The data collected in relational databases have no relationships with each other and make sense only to the specific applications they belong to. Our programs are filled with great algorithms that can talk to these disparate data without allowing us to integrate the knowledge and grow smarter.

Knowledge Integration Participants, Processes, and Products

There are no tricks that can overcome this limitation of the current software technology. Hopefully, the move to data and service integration will produce a set of knowledge containers able to consume incoming data and service rules in a learning fashion.

These distributed knowledge systems will be initiated with data and rules that provide loose connections between new and pre-existing data, and allow for the creation of a knowledge background with basic roots and branches that can grow and become fruitful. An inference engine able to execute “commonsense” logic while adding or rejecting new facts and relationships would serve as the heart of such a system.

A high-level inference framework, a constraint solver, case-based reasoning, and other similar techniques provide the base for learning capabilities. These capabilities are crucial in preventing the chaos that naturally follows increasing quantity without increasing complexity, when the number of subject choices (and consequently entropy) gets larger and larger.    

Inference frameworks and learning capabilities turn the quantity of related models and patterns into a quality of better understanding instead. Then, it is a matter of time until these collaborative systems reach the “smart” point of being visibly more helpful.

A knowledge engine keeps track of successful inference paths to reach solutions, and periodically does its homework to improve its ability to do similar things more quickly for subsequent requests.

Fig. 13.1 shows the basic elements of the system. There are three essential groups displayed in the diagram: participants, processes, and products. Developers and partners, knowledge workers, and consumers are all active participants with different roles and activities. They participate in different processes and work with different products.

[Fig.13-1]

Developers and partners are involved in the system development process and participate in active knowledge capture and exchange. Knowledge workers contribute and consume data and services; they work with the active knowledge capture and exchange process as well as the knowledge and service consumption process. The third group, consumers, plays the major role in the knowledge and service consumption process.

These activities result in three products:

·      Developers produce tools that make systems work.

·      Consumers create a virtual currency that can be used to reward contributors of knowledge.

·      The main product produced is growing knowledge.

Distributed yet connected, specific yet based on generic roots, different in themes yet nonconflicting: these are the qualities required for information to be inherently useful. Creating this quality data is extremely difficult but has proven to be possible.

Fortunately, We Do Not Need to Start from Scratch

After decades of struggle with the challenges of artificial intelligence, several companies delivered solutions that are finally available to the public. One of them is an open source project by Cycorp that I described in Chapter 5. 

Thousands of concepts and relationships, which we take for granted and assume everyone knows, are moving into bits and bytes. Logical rules that we use every day are translated into inference engine algorithms.

We are lucky. We have knowledge bases and knowledge engines ready to serve as a starting point, as a rich background that can retain new and specific information and relate it to old and generic data. An inference engine checks incoming data for conflicts with existing knowledge and rejects conflicting information. Computers cannot tolerate conflicting data so far. (This is another difference between machines and us.)

The Growing Basket of Knowledge: Layered Information

The growing basket of knowledge presented in Fig. 13.2 includes several layers of rules and data. The diagram reflects the structure of ontology from its roots to its branches. The core ontology includes very few and very generic data and assertions (rules). The generic knowledge layer is filled with systematic data and rules that provide basic concepts and relationships. This is the background to which knowledge workers can apply specific rules and data that come to the top of the knowledge basket and stick in specific domain areas.

 [Fig.13-2]

Knowledge technologies are undervalued today, but the situation is going to change after their use expands beyond scientific tasks. Scientific and research centers use knowledge-based facilities as “smart search engines” for their specific data collections.

Can the software industry directly employ knowledge technologies?

Connect Software and Knowledge Technologies

Imagine that a set of rules that define a recognition process – for example, in a grammar file – is enhanced with the ability to access a knowledge engine. This would promise more intelligent recognition, based not only on the multiple choices prepared in the file, but also on existing facts and rules of the available world of knowledge, associations between related topics, and so forth.

Why are we so excited about knowledge engine integration? What qualities will we buy with this extension? What difficulties do we face here?

To answer these questions, I need to clarify the roles in this development process. Who are “we”?

First, there is a rich set of current development roles. I will only mention three of them: business experts, system programmers, and application developers. System programmers work on operating system or database internals, or on hardware-related tasks (e.g., device drivers), often using low-level programming languages. Application programmers work on projects suggested by business domain experts. They translate business ideas into models and high-level programming languages. Business experts provide initial requirements and participate in model discussions.

There are several filters between the initial requirements and the final implementation. Knowledge technologies can minimize the gap that exists today between business requirements and the resulting applications by providing new means to describe business rules directly with an “almost natural” language. CycL (described in Chapter 5) can serve (with some stretches) as an example of this language.

A new role of “knowledge worker” is needed in the development process to use this language and (even more importantly) understand the logistics of the knowledge and inference engine. A software or ontology engineer, a mathematician or philosopher, or perhaps a business domain expert with a good logical background can play this role.

We can envision a time when current programming languages like C# and Java will be used mostly by system programmers, whereas applications will be driven by knowledge base rules and application scenarios similar to those discussed later in this text. This chapter considers the new application environment that consists of:

·      Regular services provided with programming languages like C# and Java

·      Knowledge base services filled with rules by knowledge workers

·      Simple application scenarios written with the direct influence of business experts to drive both worlds

This chapter offers an example of such integration, in which software applications can talk to the Cyc knowledge engine [1] and the knowledge engine’s responses can influence the flow of services.

The Knowledge Connector

Interaction between the enterprise and knowledge services is described with XML-based scenarios. Interoperability is provided with the Knowledge Connector package that interprets XML scenarios, as well as the user’s input, using extended grammar application program interfaces (APIs). The package delivers an application that serves as an alternative to the Cyc browser. It is designed to work as a node in a distributed JXTA community. The Knowledge Connector helps to teach the Java API to Cyc and provides interoperability in the application environment, which consists of three major components:

1.                  Regular (Java-based) application services, which are expected to be built with a service-oriented architecture

2.                  The knowledge engine, in which business rules and services are defined with the CycL language

3.                  XML-based application scenarios

The connector is a set of Java classes collected into the org.opencyc.connector package in the OpenCyc [2] project.

What Are the Main Goals of the Knowledge Connector Package?

The package aids the interaction between a user (person) and the OpenCyc knowledge engine, and also provides well-defined communication APIs between a user program and the knowledge base. In both cases, the connector uses XML-based scenarios.

The connector package is lightweight middleware that can translate XML scenarios into calls to Java-based services, including knowledge services. (A later version of the connector will add interaction with C#-based products and allow for a multiplatform environment.) 

The package is a prototype that integrates the main application layers: a user interface, services (regular [e.g., email], location based, and not-so-traditional knowledge base services), natural language interpretation logics, and program output transformations, all under the single roof of XML-based application scenarios. The package also includes a Cyc training application that acts as a knowledge peer in a distributed network.

The Knowledge Connector offers a programming interface to application services integrated with a Cyc knowledge base. The package creates a wrapper around the OpenCyc Java API. This wrapper represents the interface to the knowledge engine as a set of XML elements.

The Knowledge Connector allows programmers to write XML-based scenarios that combine a user interface, grammar rules of input interpretation, and service invocations.

The package interprets knowledge base responses and forms XML-based information flow that can be passed to other programs and services, including Web services. The API makes it possible to directly call any existing services using knowledge base instructions and also helps to convert knowledge engine algorithms into callable services.

There are several scenarios, or examples, built into the connector. They help use the package as a training facility to learn this new development paradigm, build more scenarios, and add domain-specific knowledge to the core knowledge base.

We will take a close look at architecture, design, and code samples. But first, a few words about the driving force of XML-based APIs.

Each XML scenario consists of several acts (XML elements). Every act can be a prompt to a user, a conditional statement with following interpretation logics, a user interface perform command, or an action of a service invocation.

In most cases, scenario elements include action (method name) and service (class name) parameters. If the method expects arguments, all necessary arguments are provided with name-value pairs in the same XML element.

The KnowledgeService class is the default action service that communicates to the knowledge engine. The UserAVI class is the default service class for perform elements. The UserAVI class is responsible for user audio and video interface as well as interpretation logics. These classes will be used by default in scenario acts if the service (class) name is not specified.

Object Model Diagram

Several core classes of the package are presented in Fig. 13.3. The center of the diagram is taken by the UserAVI class that drives a user audio-video interface as well as the whole application. The UserAVI class is an extension of the ScenarioPlayer class, which implements the Scenario interface. Some methods of the UserAVI class and almost all methods of the ScenarioPlayer are interpretation methods for XML scenarios and user interaction.

 [Fig.13-3]

The UserAVI class collaborates with several helpers: the Communicator, ServiceConnector, AVIFactory, and Performer objects. Each helper is responsible for one of the application layers. For example, an AVIFactory object is responsible for formatting presentations; a Performer object is responsible for performing the presentations; a Communicator object supports networking behavior in a peer-to-peer or Web-based distributed knowledge architecture; and a ServiceConnector object (as you can guess from the class name) provides access to services.

 

………  I skip here several pages of design and code details from the book ………..

 

………………………………………………………………………………

 

How Do These Classes Work Together?

The collaboration diagram in Fig. 13.11 answers this question. The diagram simplifies the activity of the application into eight major steps.

[Fig.13-11]

1.      The UserAVI object receives an XML instruction from the current scenario or a user’s input related to the current scenario.

2.      The UserAVI object uses the methods of its base class, the ScenarioPlayer, to interpret this instruction or user input and translate it into a service request (the most common action).

3.                  The ServiceConnector object uses its act() method to connect to or obtain (load at run-time) a necessary object and perform a requested operation.

4.                  The service object invokes the proper method with the necessary parameters and delivers the results back to the caller.

5.                  The ScenarioPlayer gets the results of the service and passes them further to the AVIFactory object.

6.                  The AVIFactory implementation (the CycHTMLFactory in our case) translates the results into a presentation format and produces XML scenarios related to the expected user interaction.

7.                  The UserAVI class methods and the methods of the ScenarioPlayer, its base class, interpret the results for the Performer object if the operation was a success. If the operation failed (e.g., the knowledge base query returned a “not found” string), the actionPerformed() method of the UserAVI (the focal point of event handling) can use the Communicator peer (if present) to outsource this operation to the network of knowledge peers.

8.                  The Performer object presents results on a screen and/or in voice format. The alternative to this step is to communicate to other peers (if the local peer failed) and, finally, to present successful results (or a “Sorry” message) to the Performer.

The eight steps of the cycle have now been completed and the new results shown on a screen or pronounced via voice. The invisible part of the result interpretation is the XML scenario instructions related to expected user interactions. At this point, the instructions are stored in the expectedChoices table. The program is again ready to start from the first point of the collaboration diagram to react to a user’s input or play the next act of a scenario.

…………………..  More design and Java code details ………………………………..

 

…………………………………………………………………………………….

 

Application Scenario Language

Application Scenario Language (ASL) is an XML-based language that describes application business flow in small scenarios. Think about ASL as a simplified BPEL extended with CycL expressions. Scenarios consist of XML elements: scenario steps or acts. Scenario steps are numbered sequentially and executed in the numbered order. It is not necessary to number steps manually. The numbering can be done automatically. The numbers are important to keep the proper order while converting an XML scenario to the hash table format. Every act of a scenario is a prompt, a condition, or an execution step.

Prompt the User for an Answer

The prompt() method of the UserAVI class delivers a prompt message to the user. The method sets the promptState flag to true. This shifts the program into an interpretation state. The user’s response will be interpreted to fill the variable provided with the prompt parameters. The prompt might have additional arguments, specific hints for input interpretation, and conditional actions.

Here is an extract from the newTopic.xml scenario that allows someone to introduce a new object to the knowledge base.

   <prompt variable="NEW-OBJECT"

       service="org.opencyc.connector.UserAVI"

       action="prompt"

       noinput=”reprompt(Your input is needed)”

       translate=”concatenate”

       msg="Please provide a name for your new topic." />

<if condition=”!exists” perform=”doNextStep(acceptNewObject )” />

<!—There is an object with this name in knowledgebase. à

<!—Query and display this object and let user know it is not new à

<act action=”query” constant=”NEW-OBJECT”

 lastMsg=”NEW-OBJECT is not new.” />

<!—The lastMsg element above makes this act to close the scenario à

 

<act name=”acceptNewObject” service=”com.its.connector.KnowledgeService

  action=”createNewPermanent” constant=”NEW-OBJECT” />

 

<!—more prompts and acts to relate new object to existing knowledge à

 

The prompt element of the XML scenario specifies the service class name (UserAVI) and the action method name (prompt), and sets the prompt variable (NEW-OBJECT) to store the user’s input and the prompt message.

The noinput and translate elements are optional interpretation parameters. The noinput element directs the program to reprompt the user if he or she just pressed the ENTER key.

The translate element instructs the program to concatenate multiple word input into a single word in the manner of Cyc knowledge base naming conventions. For example, the input “Volga River” is translated into the VolgaRiver name.

An important part of the prompt element is its internal variable element. In this example the variable has the “NEW-OBJECT” name. The resulting interpretation of the response will be assigned to a variable created on the fly with the “NEW-OBJECT” name. The ScenarioPlayer then will parse the current scenario to replace all occurrences of the “NEW-OBJECT” with its value.

 

The second step of the scenario is a condition. If the object name does not exist (!exists) in knowledgebase, the system will perform the doNextStep(acceptNewObject) operation and will skip the third step.

 

The third step of the scenario is performed only if a name suggested by the user is known to knowledge base. The third step queries the knowledge base on this known subject and presents existing information with the last prompt (the end of the scenario), which lets the user know that this object name is absolutely not new to the knowledge base.

Aliases

The current extract does not include the aliases element in the prompt, but when we talk about scenario APIs, it would be a crime to omit this important element. The aliases element can be a part of any prompt instruction providing hints on the response interpretation. The aliases element can list possible answers that can come in different forms but still represent the same concept.

 

The aliases element, for example, can instructs the program to interpret user input, for example, “y”, or “sure”, as “yes”. In other words, if the user’s input matches one of the aliases, the original input will be replaced with the related key value and all the following conditions (if any) will apply to the resulting key.

The following example shows the aliases element in the user’s prompt.

 

<prompt variable=”YES-OR-NO-ANSWER”

  action=”prompt”

  service=“com.its.connector.ScenarioPlayer

  msg=”Are you a new user? (y/n)”

  aliases=”yes|y|new|sure^no|n|old

     />

 

Note, that there are two sets of aliases in the example above. These two sets are separated by the “^” character, while aliases within the case are separated with the “|” character. There could be multiple sets in the aliases element.

Translate

The translate element instructs the program to perform string manipulations on a user’s input. The translate element includes method names and arguments (if necessary). In most cases, the methods are of the Stringer class, although the class name may also be present. Here is an example using the translate element:

<prompt variable=”PERSON-NAME” action=”prompt”

  service=“org.opencyc.connector.UserAVI

  msg=”Please provide your name (First Last)”

  translate=

concatenate(REPLACE-WITH-INPUT)^startWithUpperCase(REPLACE-WITH-INPUT)”

     />

The program concatenates the user’s input and makes sure each word begins with the upper case. For example, if the input is jeff zhuk, the first instruction produces jeffZhuk, and the second instruction makes it JeffZhuk, in the best Cyc tradition. The resulting string is saved in the lastInterpretation variable, a member of the ScenarioPlayer class.

The Condition Element

The condition element is a rich combination of conditional and execution expressions. Here is an extract that follows the prompt for a login name in the login scenario:

<if condition="exists"

 pattern="LOGIN-NAME-INPUT"  

 perform="doNextStep(checkPassword)" />   

<!-- Login name is not found -->

<prompt variable="NEW-USER-ANSWER"

   action="prompt"

   service="REPLACE-WITH-USER-SERVICE"

   msg="Are you a new user? (y/n)" aliases="yes|y|new" />

<if condition="equals"

 source=” NEW-USER-ANSWER"

 pattern="yes"

 perform="playScenario(newuser)" />

<!-- The user is not a new user. Incorrect login. -->

<act lastMsg="Please re-login" />

<!-- Login name is found -->

As you can see, a conditional statement in the first step of the extract above checks for the pattern’s existence. The condition in this statement is exists, and the pattern is a value of the LOGIN-NAME-INPUT variable.

The program queries the knowledge base to verify the login name’s existence. If this pattern is known to the knowledge base (exists), the scenario performs the playScenario(newuser) operation that can sign-up a new user.

 

The most common way to change the order of a scenario is to use the doNextStep() operation with the label name as an argument as it is shown in the example below:

doNextStep(labelName)

<!—several scenario steps à

<act name=”labelName” perform=”someService” />

 

It is also possible to use the playScenario(scenarioName) operation to jump to a new scenario. We can even start in the middle of the scenario if we provide additional arguments like in the example below.

 

playScenario(scenarioName, labelName, internalScenarioArguments);

 

The list of conditions includes several keywords.

exists [pattern] – returns true if a pattern exists in the knowledge base

!exists [pattern] – opposite of exists; returns true if a pattern does not exist in the knowledge base

equals [source] [pattern] – compares a source to a pattern and returns true if the source equals a pattern

!equals [source] [pattern] – compares a source to a pattern and returns true if the source is not the same as the pattern

includes [source] [pattern] – returns true if the source includes a pattern

!includes [source] [pattern] – returns true if the source does not include a pattern

inAliases [source] [pattern] – looks for a pattern in a table of aliases (from the configuration file or knowledge base) in which a source defines the name of the table of aliases; returns true if a pattern is found as one of the aliases

!inAliases [source] [pattern] – looks for a pattern in a table of aliases (from the configuration file or knowledge base) in which a source defines the name of the table of aliases; returns true if a pattern is not found in the table

The noinput option that can be used in the prompt statement performs an instruction when the user does not answer the prompt but just presses the ENTER key. A condition statement is followed by an action to perform, an executable instruction. If a condition is not met (returns false), the action is not performed and the next scenario step is played instead.

Both perform- and action-executable instructions use a service object and an action method name for this service method invocation. The only difference between the two is the default service name used when a service name is omitted in the statement. The perform instruction uses the UserAVI class in this case, whereas the action instruction targets the KnowledgeService.

Executable instructions accept parameters in the form of a method signature or key-value elements. Here is an example of a signature approach:

perform=”playScenario(newuser)”

This statement performs the playScenario() method of the UserAVI or its base class. This method must expect a single string argument. The newuser string is passed to the method. The alternative way is to specify all parameters as key-value pairs:

action="createNewObject"

msg="REPLACE-WITH-MAIN-GROUP"

or

action="createMicrotheory"

Mt="REPLACE-WITH-MAINMT"

msg="REPLACE-WITH-MAIN-GROUP knowledge area"

genlMts="KnowledgeExchangeMt,ComputerNetworkMt"

This way is convenient for methods that expect a table (Hashtable) of key values, as in the code extract below (see the KnowledgeService class):

    public String createMicrotheory(Hashtable parameters)

      throws Exception {

        String comment = (String)parameters.get("msg");

        String mtName = (String)parameters.get("Mt");

        mtName = Stringer.startWithUpperCase(mtName);

        String isaMtName = (String)parameters.get("isa");

        String genlMtsString = (String)parameters.get("genlMts");

      // etc. etc…………………..

The Query Element Talks to the Knowledge Base

The query element is a direct combination of knowledge base query results and the following conditions and executions. It consists of a Cyc query and usually includes the queryResult option that assigns a variable to store query results.

Query instructions require us to define a microtheory name in which the search will be performed. The program assigns the main microtheory name (set by the configuration file) as the default if this parameter is omitted in the query statement. As an example, let us consider an extract from the newTopic.xml scenario below. The extract includes a prompt for the user’s input, a condition element, and a query statement followed by an analysis of query results.

<!—Ask a user to relate a new subject to some existing Collection à

<prompt variable="EXISTING-COLLECTION"

  service="org.opencyc.connector.UserAVI" 

  action="prompt"

  msg="Please relate your new topic to some existing object that must represent some Collection. Enter an existing topic name that can serve as a parent to your new topic.”

  noinput=”setDefault(REPLACE-WITH-MAIN-TOPIC)” />

<!—Check if this is an existing name à

<if   condition=”!exists

pattern=”EXISTING-COLLECTION”

perform=”reprompt(EXISTING-COLLECTION is not found in the KB.) “ />

<!—Check if this is a Collection à

<act query="(#$isa #$EXISTING-COLLECTION ?X)” queryResult=”COLLECTION-QUERY-RESULT” />

<if condition=”!includes

 pattern=”Collection”

perform=”reprompt(EXISTING-COLLECTION is not a Collection)" />

The example above prompts the user to provide an existing collection name that relates a new subject to existing data. The following statements check to determine if the user’s input is worth trusting. Does this name really exist in the knowledge base, or just in the user’s imagination? Does this name meet the requirement to be a collection? If the requirements are not met, the system re-prompts the user for a better answer. Only a good qualified answer can pass this test.

This example includes two of the most commonly used conditional actions: reprompt() and setDefault(). The reprompt() action can take an optional argument-message and add this message to the last user’s prompt. The setDefault() action instructs the program to replace the user’s input with the value that follows this action. The example above uses the setDefault() method in the “noinput” case to set a collection name as the main topic name. (The main topic name must be set in the configuration file.)

Learn by Example: How to Add Knowledge to Knowledgebase?

I hope that several more extracts from the newTopic.xml scenario provide enough exposure into the world of application scenario writers. The scenario extract below sets a scope or a microtheory for the new topic.

<prompt variable="YOUR-MICROTHEORY"

   service="REPLACE-WITH-USER-SERVICE"

   action="prompt"

   noinput=”setDefault(REPLACE-WITH-MAINMT)”

   msg="Provide one of your existing microtheories (scope) for this object. (REPLACE-WITH-MAINMT is the default scope.)" />

<act query=”(#$isa #$YOUR-MICROTHEORY ?X)”  

  actionResult=”CHECK-MICROTHEORY-RESULT” />

<if condition=”!includes

  source=”CHECK-MICROTHEORY-RESULT”

  pattern=”Microtheory

  perform=”reprompt(This is not a microtheory name)" />

In this example, the user’s prompt suggests defining a scope for a new topic as an existing microtheory. The user has the option of pressing the ENTER key without any input. In the noinput case, the program performs the setDefault() method to set the scope to the main microtheory defined by the configuration file. The following query uses the knowledge engine to determine if the user’s input really represents a microtheory. If the query result does not include the word Microtheory, the program reprompts the user.

You might notice the REPLACE-WITH-MAINMT and REPLACE-WITH-USER-SERVICE variables in this extract. The program replaces these variables and some other variables with the same REPLACE-WITH syntax with the replacement values from the configuration file:

<replacements>

   ……

  <replacement name="REPLACE-WITH-MAINMT" value="JavaSchoolMt" />

 

  <replacement name="REPLACE-WITH-USER-SERVICE"  value="org.opencyc.connector.UserAVI" />

  …..

</replacements>

Can a New Topic Serve as a Parent-Umbrella for More Objects?

The last extract from the newTopic.xml scenario helps to define whether a new topic can serve as a parent-umbrella for more objects:

<prompt variable="COLLECTION-OR-INDIVIDUAL"

   service="org.opencyc.connector.UserAVI"

   action="prompt"

   aliases="Collection|1^2|Individual"

   nomatch=”reprompt(/incorrect answer. Only 1 or 2 is accepted.) “    

   msg="Is a new topic a Collection - class of objects (1) or an instance - individual object (2) ? Enter 1 or 2" />

<!—If a new topic is a collection - its RELASHIONSHPIS to a parent is as a class to a subclass, “genlsà

<if condition="equals”

  source=” COLLECTION-OR-INDIVIDUAL”

  pattern=”Collection”

  perform=” modifyScenario(RELATIONSHIPS,genls) />"

<!—If a new topic is an individual - its RELASHIONSHIPS to a parent is an instance “isaà

<if condition="equals”

  source=” COLLECTION-OR-INDIVIDUAL”

  pattern=”Individual”

  perform=” modifyScenario(RELATIONSHIPS,isa) />"

<!—Set a rule-relationships between the new object and its parent à

<act action=”assert”

  msg=”(#$RELATIONSHIPS #$NEW-TOPIC-NAME #$EXISTING-COLLECTION)” />    

 

The program substitutes the user input “1” or “2” with the word Collection or Individual according to the aliases attribute.

The nomatch attribute instructs the program to reprompt the user if the user’s input does not match the condition (is neither 1 nor 2). The program performs the modifyScenario() method of the UserAVI class to replace the RELATIONSHIPS variable (in the last step of the scenario) with “isa” or “genls” relationships. Both are CycL predicates.

The last step of the scenario establishes relationships between the new object and its parent. Collections have transitive inheritance established by genls (generic inheritance), whereas individual inheritance established by isa is not transitive. The message that we use with the assertGAF action is an example of a sentence rule written in CycL.

Think of the isa predicate as an analogy to creating an instance of a class, whereas genls is about the similar relationship between a base and a subclass. The meaning of the sentence is either: The new topic is a subclass of the EXISTING-COLLECTION and is a new Collection or a class of new objects; or the new topic is an individual instance of the EXISTING-COLLECTION.

The most important achievement of the new topic scenario is the connection of a new object to existing roots in the knowledge base (Fig. 13.12). New data must be related to roots with several rules/assertions.

1.       A new object is a collection (a class of objects) or an individual instance.

2.      A new object has a parent-umbrella in the existing knowledge space.

3.      A new object has a scope or micro-theory.

<?xml version = "1.0" encoding = "UTF-8"?>

<dialogScenario name="newobject">

 <scenario>

   <prompt variable="NEW-OBJECT" unique="true"

       service="UserAVI" action="prompt"

            msg="Please provide a unique name for your topic." />

 

   <prompt variable="YOUR-MICROTHEORY"

     default="REPLACE-WITH-MAINMT" service="UserAVI" action="prompt"

     msg="Provide one of your existing microtheories (scope) for this object.

        (REPLACE-WITH-MAINMT is the default scope.)" />

  

  <act query="(#$isa #$YOUR-MICROTHEORY ?X)"  

    queryResult="CHECK-MICROTHEORY-RESULT" />

 

  <if condition="!includes" source="CHECK-MICROTHEORY-RESULT"

    pattern="Microtheory" perform="reprompt(This is not a microtheory name)" />

 

  <prompt variable="COLLECTION-OR-INDIVIDUAL"

       service="UserAVI" action="prompt"

       aliases="Collection,1;Individual,2"

       ifInputEquals="Collection,replaceAll,RELATIONSHIPS,genls;Individual,replaceAll,RELATIONSHIPS,isa"

            msg="Is it a Collection - class of objects (1) or an instance - individual object (2) ? Type 1 or 2." />

 

   <prompt variable="EXISTING-COLLECTION" unique="false"

       query="(#$isa #$REPLACE-WITH-INPUT ?X)" checkFor="Collection"

       service="UserAVI" action="prompt"

       msg="Please relate your new topic to some existing object.

            Enter an existing topic name that can serve as a parent to your new topic.

            You actually name a Collection-Type for your new object.

        For example: Event, Person, PartiallyTangible, etc. can be valid types.

            You can always come back and edit this assertion as well as

            add more types and assertions to this topic.

        At this point it might be advantages to use Cyc browser trying to answer this question :-)" />

 

   <act action="createNewObject" msg="NEW-OBJECT" />

 

   <act action="assert" Mt="YOUR-MICROTHEORY"

     msg="(#$RELATIONSHIPS #$NEW-OBJECT #$COLLECTION-OR-INDIVIDUAL)" />

 

   <act action="assert" Mt="YOUR-MICROTHEORY"

     msg="(#$isa #$NEW-OBJECT #$EXISTING-COLLECTION)" />

 

   <act action="query" Mt="YOUR-MICROTHEORY" msg="(?X #$NEW-OBJECT ?Y)"

    variable="X,Y" constant="NEW-OBJECT" />

 

  </scenario>

 

</dialogScenario>

 

[Fig.13-12]

<?xml version="1.0" encoding="UTF-8" ?>

 <dialogScenario name="newobject">

   <scenario>

 

  <prompt variable="NEW-OBJECT" unique="true" service="UserAVI" action="prompt" msg="Please provide a unique name for your topic." />

 

  <prompt variable="YOUR-MICROTHEORY" default="REPLACE-WITH-MAINMT" service="UserAVI" action="prompt"

 msg="Provide one of your existing microtheories (scope) for this object. (REPLACE-WITH-MAINMT is the default scope.)" />

 

  <act query="(#$isa #$YOUR-MICROTHEORY ?X)"

 queryResult="CHECK-MICROTHEORY-RESULT" />

 

  <if condition="!includes" source="CHECK-MICROTHEORY-RESULT" pattern="Microtheory" perform="reprompt(This is not a microtheory name)" />

 

  <prompt variable="COLLECTION-OR-INDIVIDUAL" service="UserAVI" action="prompt" aliases="Collection,1;Individual,2"

msg="Is it a Collection - class of objects (1) or an instance - individual object (2) ? Type 1 or 2." />

 

<act condition=”equals" source=”Collection”

  pattern=” COLLECTION-OR-INDIVIDUAL” perform=”replaceAll(RELATIONSHIPS,genls)” />

 

<act condition=”equals" source=”Individual”

  pattern=” COLLECTION-OR-INDIVIDUAL” perform=”replaceAll(RELATIONSHIPS,isa)” />

 

  <prompt variable="EXISTING-COLLECTION" unique="false"

query="(#$isa #$REPLACE-WITH-INPUT ?X)" checkFor="Collection" perform="prompt"

msg="Please relate your new topic to some existing object. Enter an existing topic name that can serve as a parent to your new topic. You actually name a Collection-Type for your new object. For example: Event, Person, PartiallyTangible, etc. can be valid types. You can always come back and edit this assertion as well as add more types and assertions to this topic. At this point it might be advantages to use Cyc browser trying to answer this question :-)" />

 

  <act action="createNewObject" msg="NEW-OBJECT" />

 

  <act action="assert" Mt="YOUR-MICROTHEORY"

msg="(#$RELATIONSHIPS #$NEW-OBJECT #$COLLECTION-OR-INDIVIDUAL)" />

 

  <act action="assert" Mt="YOUR-MICROTHEORY"

msg="(#$isa #$NEW-OBJECT #$EXISTING-COLLECTION)" />

 

  <act action="query" Mt="YOUR-MICROTHEORY"

msg="(?X #$NEW-OBJECT ?Y)" variable="X,Y" constant="NEW-OBJECT" />

 

</scenario>

  </dialogScenario>

 

You can see that XML-based APIs of application scenarios serve to interpret words and sentences coming from a user or from text documents, and to invoke existing software services, including knowledge engine services. Collected into XML scenarios, they can completely describe application behavior and, if necessary, include presentation layer definitions in XML and/or HTML, WML, and other formats.

Can We Change the Execution Order of a Scenario?

The playScenario, as well as the doNextStep, action can be very handy in conditional statements. The playScenario is an executable instruction to play a specific scenario starting with a specific step number (or by default, from Step 1) and other optional arguments.

Here is an example from the countryData scenario, which may be handy if you want to add some information that you surveyed about a foreign country.

 

 <prompt variable=”COUNTRY-INPUT”

msg=” What country?”

service="REPLACE-WITH-USER-SERVICE" action="prompt" />

<if condition=”!exists” pattern=”COUNTRY-INPUT” perform=”playScenario(newCountry,2,COUNTRY-INPUT) “  />

 

This scenario prompts the user to enter a country name. If the user names a country that is not currently known to the knowledge base (is new), the program invokes the playScenario() method with the following arguments:

The scenario name is newCountry.

The starting step of the scenario is 2. 

The COUNTRY-INPUT will be passed to the newCountry scenario as an expected argument – the name of a new country to be entered in the knowledge base.

A very simple example of changing the order of steps in a scenario is the conditional invocation of the doNextStep action. The argument to the doNextStep() method instructs the program to jump to a proper element in the scenario flow.

There are many actions and methods that are accessible with the action and perform attributes of XML scenarios. The easiest way to look into these possibilities is to view the JavaDoc APIs (method definitions) of the UserAVI, KnowledgeService, and other classes inside and outside the Knowledge Connector package.

Executable Acts of a Scenario

Almost every method may be considered a potential action or executable act in XML scenarios. Executable acts have only the parameters necessary for the execution: the service name, action name, and method arguments (if needed). For example:

 

<act action="createNewObject"

service=”org.opencyc.connector.KnowledgeService

msg="NEW-OBJECT-NAME" />

 

The action element may include a class name and all necessary parameters. A class name can be omitted. In this case, the default class name is used instead. If a class name does not include a package name, the org.opencyc.connector package name is added by default. It is recommended that you provide a qualified class name that includes a package name (see the example above). Otherwise, the Java Reflection package has to look in all the jar files available in your Java classpath. This lookup may be an expensive exercise, especially in J2ME resource-restricted devices.

As we mentioned earlier, the connector package not only works with its own services but can also invoke any service available in any other package. For example, the XML scenario provided below uses the email service from the com.its.mail (Internet Technology School, Inc. [4]) package.

 

<?xml version = "1.0" encoding = "UTF-8"?>

<scenario>

 <!—Example of email service invocation à

 <prompt msg=”Provide TO: address”

  variable=”TO-EMAIL-ADDRESS”

  service=”org.opencyc.connector.UserAVI” action=”prompt” />

 <prompt msg=”Provide your message”

  variable=”EMAIL-MESSAGE” 

  service=”org.opencyc.connector.UserAVI” action=”prompt” />

 <act service=”com.its.mail.EmailClient” action=”send”

  to=”TO-EMAIL-ADDRESS” msg=”EMAIL-MESSAGE” />

</scenario> 

 

An alternative way is to provide a qualified method signature in the action or perform statements. The example below shows an act of a scenario that sends email with predefined arguments:

<act action=

com.its.mail.EmailClient.sendMail(Jeff.Zhuk@JavaSchool.com, test, Hello!)” />

Explore the Cyc API

The low-level Java API for the Cyc knowledge engine is very rich and nontrivial. The training tool based on the connector package allows us to enter the inlineAPI keyword followed by a Java Cyc API expression in the command line. This technique helps us discover Java Cyc API method details and to quickly survey some data with no browser at hand.

It is possible to copy and paste a method definition from the org.opencyc.api.CycAccess APIs. For example, the command line can initially consist of:

inlineapi getAllDependentSpecs(CycFort cycFort)”

This method gets the list of all of the dependent specs for a CycFort collection.

Substitute an argument string with the real collection name – for example, Person. The command line will look like this:

inlineapi getAllDependentSpecs(CycFort Person)”

Press the ENTER key, and view all the rules (assertions) associated with the Person collection.

The program interpretation is based on the inlineAPI() method of the ScenarioPlayer. The inlineAPI() method tries to interpret and execute any API and includes special support for Cyc objects. For example, it will convert the Person string argument to a CycFort object, as the getAllDependentSpecs() method requires.

Here is another example of the Java Cyc API executed with the inlineAPI() method:

inlineapi getAllInstances(CycFort cycFort, CycFort mt)”

This call gets a list of all the direct and indirect instances (individuals) for a CycFort collection in the given microtheory.

Substitute a collection name with Person and a microtheory name with JavaSchoolMt and press the ENTER key. The resulting command line is:

inlineapi getAllInstances(CycFort Person, CycFort JavaSchoolMt)”

This query produces a list of people associated with the Person collection in the JavaSchoolMt microtheory.

Note that providing the type of variable, such as CycFort, is optional. By using this option, the user gives the program an indication that the default class name is CycAccess. More precise method calls include a class name. Here is an example:

inlineapi org.opencyc.api.CycObjectFactory.makeUniqueCycVariable(CycVariable modelCycVariable)”

This call constructs and returns a new CycVariable object by suffixing the given variable name.

If the inlineAPI() method works with a single command line typed by a user, the similar performAction() method of the ScenarioPlayer class interprets and executes elements of XML scenarios provided at run-time by the application. The performAction() method of the ScenarioPlayer class tries its best to resolve a class name, method name, and related parameters within an XML element. This is not always possible, but if the interpretation is successful, the performAction() method uses the same act() method of the ServiceConnector class powered by the Java Reflection package to invoke the proper service method on the proper service object. The resulting data usually feed the next XML elements of the same scenario or may be formatted by a presentation factory and displayed (or pronounced) by a performer implementation. For example:

<act action=”CycAccess.getAllSpecs(CycFort \”Person\”)” />

or

<act action=”org.opencyc.api.CycAccess.getAllSpecs(CycFort Person)” />

or

<act action=”CycAccess.getAllSpecs(CycFort Person, CycFortJavaSchoolMt”)” />

In all cases, the execution produces a list of Cyc knowledge base specifications related to the “Person”.

The performAction() method is not limited to OpenCyc class methods, but can resolve and execute method calls to object services located on the same network. Here is another example of a service invocation:

 

<act action="sendMail" service="com.its.mail.EmailClient"

       to="EMAIL-ADDRESS"

       from="REPLACE-WITH-MAIN-AGENT"

       subject="Welcome"

       message="Welcome to Cyc-JavaSchool training." />

 

In this example, the com.its.mail.EmailClient service object invokes the sendMail method with the above parameters.

The connector package is powered not only by a set of Java classes. The config.xml file (Fig. 13.13) also plays a role in the package configuration and behavior definition. The configuration file includes alias elements and presentation patterns. The program reads the config.xml file at the very beginning and sets configuration tables in the ScenarioPlayer and CycHTMLFactory (presentation patterns).

 

<?xml version = "1.0" encoding = "UTF-8"?>

<config>

 <predicates>

  <predicate name="clients" value="users,customers" />

  <predicate name="relatives" value="sister,brother,aunt,cousin,sisters,brothers,cousins,aunts,friend,friends" />

  <predicate name="friends" value="friend,comrad" />

 </predicates>

 <presentationPatterns>

  <presentationPattern name="presentationType" value="org.opencyc.connector.HTMLFormatter" />

  <presentationPattern name="listPresentationType" value="CycList" />

  <presentationPattern name="userServiceName" value="UserAVI" />

 

   <presentationPattern name="scenarioHeader"

    value="[table][td][img src=file:///REPLACE-WITH-URLimages/its.gif][/td][/table]" />

 </presentationPatterns>

 

 <defaults>

    <default name="tryNewScenarioMsg" value="Try new scenario. It might actually work :-)" />

    <default name="defaultScenarios" value="newtopic,find,newscenario,setWorldSystem,showWorld" />

    <default name="existingScenarioMsg" value="The name is taken by one of core scenarios." />

 

    <default name="unresolvedMsg" value="ERROR: The system has saved unresolved situation for future learning process. " />

    <default name="emptyMsg" value="Cannot take RETURN key as an answer. Please enter a meaningful value" />

    <default name="upgradeFromURL" value="http://JavaSchool.com/school/public/knowledge/upgrade" />

 </defaults>

<!-- More configuration data -->

</config>

 

[Fig.13-13]

 

………………………. Java Code Details …………………………………..

 

How to Set Your World

There are several steps that the Knowledge Connector application performs automatically for every user.

At its first startup, the application uses the setWorld scenario to check that basic security and resource provisioning are in place. The scenario queries the knowledge base for several basic areas or names provided in the configuration file. If one or more areas are not established yet, the scenario creates the necessary microtheories and constants in the knowledge base.

How is privilege-based access provided to knowledge base?

4.      The setWorld scenario creates a special microtheory with the name provided in a configuration file. The default name is ResourceAvailabilityMt. This microtheory serves as a custom bookkeeper for a specific group of users to associate created data (resources) with a security domain [4].

5.      This is a part of the setWorld scenario that takes care of this issue.

6.      <action="createMicrotheory"
Mt="REPLACE-WITH-RESOURCEMT"
msg="REPLACE-WITH-RESOURCEMT relate objects to privileged access domains"
genlMts="KnowledgeExchangeMt"
isa="Microtheory" />

7.      While creating a new object name or a new microtheory, the program makes two additional assertions (rules):

4.1. Mark a new object (constant) as "SomethingExisting
<act action="assert" Mt="REPLACE-WITH-RESOURCEMT"
msg="(#$isa #$REPLACE-WITH-NEW-CONSTANT #$SomethingExisting)" />

4.2. Mark a new constant as "resourceAvailable" for a default or a specific "DOMAIN-NAME"
<act action="assert" Mt="REPLACE-WITH-RESOURCEMT"
msg="(#$"(#$resourceAvailable #$REPLACE-WITH-DOMAIN-NAME #$REPLACE-WITH-NEW-CONSTANT)" />

 

The DOMAIN-NAME can be a group of users, a security level, or anything of this kind. The only requirement: a DOMAIN-NAME must be marked as a #$Agent in the knowledge base.

Fig. 13.16 shows the setWorld scenario. The first steps of the scenario are to script check and establish (if necessary) the resource and main microtheories that define a world of knowledge for the group of users to which a current login user belongs. Then, the scenario makes a provision for a session security area, and the last act of the setWorld scenario passes control to the login scenario.

<?xml version = "1.0" encoding = "UTF-8"?>

<dialogScenario name="setWorld">

 <scenario>

   <if condition="exists" pattern="REPLACE-WITH-RESOURCEMT" perform="doNextStep(checkGroupExistence)" />

 

   <act name="2" action="createMicrotheory"

     Mt="REPLACE-WITH-RESOURCEMT"

     msg="REPLACE-WITH-RESOURCEMT relate objects to privileged access domains"

     genlMts="KnowledgeExchangeMt"

     isa="Microtheory" />

 

   <!-- Check and if necessary create main group agent -->

   <if name="checkGroupExistence" condition="exists"

     pattern="REPLACE-WITH-MAIN-GROUP" perform="doNextStep(checkMtExistence)" />

 

   <act action="createNewObject" msg="REPLACE-WITH-MAIN-GROUP" />

 

   <act action="assert" Mt="REPLACE-WITH-RESOURCEMT"

     msg="(#$isa #$REPLACE-WITH-MAIN-GROUP #$TemporalThing)" />

 

   <!-- Provision for object registration -->

   <act action="assert" Mt="REPLACE-WITH-RESOURCEMT"

     msg="(#$isa #$REPLACE-WITH-MAIN-GROUP #$Agent)" />

 

   <!-- Check and if necessary create the main microtheory -->

   <if name="checkMtExistence" condition="exists"

     pattern="REPLACE-WITH-MAINMT" perform="doNextStep(checkSessionExistence)" />

 

   <act action="createMicrotheory"

            Mt="REPLACE-WITH-MAINMT" msg="REPLACE-WITH-MAIN-GROUP knowledge area"

        genlMts="KnowledgeExchangeMt,ComputerNetworkMt" isa="Microtheory" />

 

   <act action="assertGAF" Mt="REPLACE-WITH-MAINMT"

   msg="(#$isa #$REPLACE-WITH-MAIN-GROUP #$Agent)" />

 

   <!-- Register the main microtheory -->

   <act action="assert" Mt="REPLACE-WITH-RESOURCEMT"

   msg="(#$resourceAvailable #$REPLACE-WITH-MAIN-GROUP #$REPLACE-WITH-MAINMT)" />

 

   <!-- Check and if necessary create the session microtheory -->

   <if name="checkSessionExistence" condition="exists"

     pattern="REPLACE-WITH-SESSIONMT" perform="doNextStep(end)" />

 

   <act action="createMicrotheory"

          Mt="REPLACE-WITH-SESSIONMT"

          msg="REPLACE-WITH-SESSIONMT keeps session data for current users: last login, action, etc."

          genlMts="KnowledgeExchangeMt,ComputerNetworkMt"

          isa="Microtheory" />

 

   <act name="end" perform="playScenario(login)" />

 

 </scenario>

</dialogScenario>

 

[Fig.13-16]

The names of initial microtheories and user groups, such as REPLACE-WITH-MAIN-GROUP and REPLACE-WITH-MAINMT, are defined in the Replacements section of the configuration file. Each group of users, or even an individual user, can redefine the names and establish a unique world or area of knowledge within the knowledge base. Here is the extract from the Replacements section of the configuration file:

<replacements>

<!—A Security Domain or a Group Name à

  <replacement name="REPLACE-WITH-MAIN-GROUP" value="JavaSchool" />

<!—The Main microtheory à

  <replacement name="REPLACE-WITH-MAINMT" value="JavaSchoolMt" />

<!—Resource Microtheory Name à

  <replacement name="REPLACE-WITH-RESOURCEMT" value="ResourceAvailabilityMt" />

<!—Session Microtheory Name à

  <replacement name="REPLACE-WITH-SESSIONMT" value="SessionDataMt" />

<!—More configuration Names à

</replacements>

The main microtheory (JavaSchoolMt in this example) serves as an overall umbrella for all data and rules created by the group, whereas the resource microtheory (ResourceAvailabilityMt in this example) only stores resourceAvailable rules that specify privilege-based access to this data. It is especially handy to have these umbrellas when you want to distribute your data – for example, when you work within a network of Cyc-Peers. In this case, it is relatively easy to query for available resources (resourceAvailable ?X ?Y) in the resource microtheory to get all object names, then collect all the rules related to these objects under the main microtheory.

User Authentication with the Login Scenario

The Knowledge Connector application keeps track of a user’s session data, provides authentication mechanisms, and distinguishes the user’s objects from objects in other worlds.

Fig. 13.17 provides an example of the login scenario.

<?xml version = "1.0" encoding = "UTF-8"?>

<dialogScenario name="login">

 <scenario>

 

   <prompt variable="LOGIN-NAME-INPUT"

    service="REPLACE-WITH-USER-SERVICE" action="prompt"

            msg="Please type your login name. Press ENTER if you are a new user."

    translate="loginToName(REPLACE-WITH-INPUT)"

    actionResult="USER-NAME" noinput="playScenario(newuser)" />

   

    <if condition="exists" pattern="LOGIN-NAME-INPUT"

      perform="doNextStep(checkPassword)" />

   

    <!-- Login name is not found -->

    <prompt variable="NEW-USER-ANSWER"

      action="prompt" service="REPLACE-WITH-USER-SERVICE"

      msg="Are you a new user? (y/n)" aliases="yes|y" />

     

    <if condition="equals" pattern="yes" perform="playScenario(newuser)" />

   

    <!-- The user is not a new user. Login name was entered incorrectly -->

    <act lastMsg="Please re-login" />

   

   <!-- Login name exists. Check for password --> 

   

   <prompt name="checkPassword" variable="PASSWORD-INPUT"

      service="REPLACE-WITH-USER-SERVICE" action="prompt"

      msg="Please enter your password" echo="*"

      noinput="setDefault(NO-PASSWORD)" />

 

    <!-- Check password match. Query knowledgebase first. -->

  <act queryResult="PASSWORD-FOUND" query="(#$nameString #$USER-NAME ?X)" />

 

  <if source="PASSWORD-FOUND" condition="includes"

    pattern="psw=PASSWORD-INPUT" perform="doNextStep(success)" />

 

  <!-- Check NO Match case -->

   <if source="PASSWORD-FOUND" condition="!equals" pattern="notFound"

    perform="lastMsg(No match. Sorry. Try again)" />

 

   <!-- Set default password if not found. -->

   <act translate="nameToLogin(USER-NAME)" actionResult="DEFAULT-PASSWORD" />

 

   <act action="assert" msg="(#$nameString #$USER-NAME \"psw=DEFAULT-PASSWORD\")" />

  

   <!-- Let user know that a default password has been set -->

   <act action="prompt" service="REPLACE-WITH-USER-SERVICE"

    msg="Your record set to DEFAULT-PASSWORD now. Change it later. Press ENTER." />

 

  <!-- Full success. Set necessary session data -->

  <!-- set Cyclist name to Cyc -->

  <act name="success" peform="org.opencyc.api.CycAccess.setCyclist(USER-NAME)" />

 

  <!-- get and show last session data -->

  <act query="(#$nameString #$USER-NAME ?X)"

      Mt="REPLACE-WITH-SESSIONMT" queryResult="LAST-SESSION-DATA" />

  <!-- if no previous session found -->

  <if condition="equals" pattern="notFound"

    endingTalk="doNextStep(loginSuccess)" />

 

<!-- Remove old session record and replace it with the new session data -->

  <act action="unassert" Mt="REPLACE-WITH-SESSIONMT"

      msg="(#$nameString #$USER-NAME \"LAST-SESSION-DATA\")" />

 

  <act perform="REPLACE-WITH-PERFORMER-TYPE.setDisplay(LAST-SESSION-DATA)" />

 

  <!-- Login success: set session data -->

  <act name="loginSuccess" perform="loginSuccess(USER-NAME)" />

 

  </scenario>

 

</dialogScenario

 

 [Fig.13-17]

The first step of the scenario prompts a user for a login name and immediately translates the user’s input into an internal system user name according to naming conventions for this application and knowledge base. If the user enters nothing and just presses the ENTER key (giving up at the very beginning), the system picks up the noinput case and plays the newuser scenario. Hopefully, our user is brave enough and the first step is a success.

The second step verifies the existence of the user’s name. If the user name is found, the control is passed to the “checkPassword” act of the scenario. The “checkPassword” act prompts the user for his or her password. If a user’s name is not found in the knowledge base, there are two possibilities: either the user is new or the login name was not entered correctly. Scenario acts that follow the prompt deal with these possibilities.

When the system prompts for a password (in the checkPassword scenario step), the setEcho attribute of the scenario allows us to cover the entered password from watching eyes. The following steps query the knowledge base for an existing password and compare the result of the query with the password entered by the user. We would be acting in a more secure manner if we used the encrypted form of a password, as is shown in the alternate example below:

 

<!-- Optional Encrypted Password à

<prompt variable="PASSWORD-INPUT"

  actionResult="ENCRYPTED-PASSWORD"

 service="REPLACE-WITH-USER-SERVICE" action="prompt"

 msg="Please enter your password" echo="*"

 translate="com.its.util.Cryptor.encrypt(PASSWORD-INPUT)"

 noinput=”setDefault(NO-PASSWORD)" />

<act actionResult="PASSWORD-FOUND"

 query="(#$nameString #$USER-NAME ?X)” />

<if condition=”include”

 pattern=”psw=ENCRYPTED-PASSWORD”

 perform=”doNextStep(success)" />

 

There are three possible results of password verification:

1.      A complete match. In this case the program passes control to the happy-ending part of the scenario labeled as “success” that performs the necessary system settings and opens all the doors for the user.

2.      No match. The user’s record has a password that is not the same as the user’s input. The scenario takes care of this possibility by issuing the last message “Sorry. Try again.” to the user.

3.      The user’s record has no password. In this case, a default password is set, and the scenario plays the happy ending that begins with the scenario element named as “success”. The default password is created by the nameToPassword() operation that translates user’s login name into the default password that can be changed by the user later on.

The happy ending consists of several acts, or steps. The application sets a Cyclist name to the Cyc knowledge base, retrieves and displays the last session’s data, replaces the old session’s data with the new data, and finally, performs the loginSuccess() method of the UserAVI class.

 

………………………………………………………………………………

 

Summary

The combination of a knowledge engine with traditional application services creates a new development paradigm. A new development role and a new implementation mixture will appear soon thereafter.

The implementation environment that reflects the business model may include:

·      Traditional services (developed using traditional programming technologies, such as Java and .NET)

·      Business rules expressed in the “almost natural” language of the knowledge base

·      Relatively simple application scenarios that bridge both worlds

Figs. 13.21 and Fig. 13.22 compare the process of regular application development to that of an application with an embedded knowledge base.

[Fig13-21]

In the current development process, there is a gap between initial business input provided by business people and the final implementation. The current process requires many transformations to simplify the complex world of reality into low-level program functions and tables expressed with current programming languages. Several filter layers and sometimes multiple teams fill this gap.

[Fig.13-22]

In the new development paradigm, knowledge technologies play an essential role in the development process. Business domain experts will be able to directly participate in the development agenda by writing business rules and application scenarios with more natural language. This will also help to focus developers (currently distracted by technological details) on the business aspects of applications.

Some time ago, we thought of C as the language for application development, whereas Assembly was the language for system development. It is about time to move programming languages like C# and Java from the application to the system level. These languages will be used mostly by system programmers (service providers), whereas applications will be driven by knowledge base rules and scenarios that invoke the services.

Fig. 13.23 represents knowledge-driven architecture [5]. We can review this diagram from the position of the model-view-controller (MVC) design pattern.

 [Fig.13-23]

The major component of the model part is a knowledge engine. Business rules and scenarios are captured in the knowledge base with an almost-natural language (e.g., CycL, CycML). There are also traditional services that capture some business rules and algorithms with current programming languages to support the model. The third model component is a set of application scenarios. Each application scenario is a very lightweight XML description of a part of an application that invokes some services, exercises some business rules, and includes hints for the interpretation of expected user (or program) responses.

There is a traditional view block of the MVC design pattern. The view delivers information in selected video or sound formats. People are the target audience for the traditional view.

The interpreter block on the picture plays the roles of controller and interpreter. The interpreter’s audience is not us (people), but programs that (in most cases) exchange information in XML formats. The interpreter is connected via the service connector block to all parts that represent a business model and actively uses these parts (especially the knowledge base) in the interpretation process.

The interpreter takes the user’s input – or an XML request from the network, or an act of an application scenario (also in XML format) – and transforms it into the proper format (almost always XML) for the proper program. The interpreter is also responsible for the interpretation of service or knowledge base responses. Interpreted responses are often directed (in XML format) to the view block, which performs the final transformational step and delivers data to people in the selected presentation format.

The interpreter may include special engines, such as speech, handwriting, or image recognition, that target a specific type of user input. These extra engines (combined with the Service Evaluator [3] that maintains and re-fines information about services) can provide direct translation of user’s request in the XML-based scenarios and service calls creating applications on-demand (dream comes true!). The interpreter can expect interactions with multiple users and can also handle events generated by different objects (event consumers). Scenarios that describe sequences of events related to multiple users and objects may help automate workflow applications. These scenarios map each expected event to its observer (see Gamma et al. [6]) or a set of observers that have interests in the events and handle these events with proper services.

Of course, there are application areas that just “do not fit.” Keep this in mind while trying to redress an existing development process or an application. A small success is much more fun than a big failure.

We have considered architecture, design, and code examples of the Knowledge Connector package that provides the facilities to integrate Cyc’s knowledge power and regular software applications in a unified XML scenario. Simple yet rich XML scenario APIs benefit from interpretation templates, as well as knowledge base queries, and include some initial elements of a natural user interface.

Consistent separation of presentation layers allows for great flexibility in adapting AVIFactory implementations to speech and/or wireless applications, as well as creating XML-based user interfaces.

While describing the bridge between knowledge and software technologies, this chapter might bring up more questions than answers. How can we use this bridge for natural language interpretation? What else is needed to help subject matter experts verbally describe business requirements? What is the future of the distributed knowledge marketplace? What are the new application types that will employ knowledge technologies?

At some point, subject matter experts will be able to verbally describe business requirements, and integration magic will produce an “application on demand” for all wired and wireless clients.

But this is another story, and may be another book.

Integrating Questions

1.      What are the main goals of software and knowledge technology integration?

2.      How does this integration affect software architecture?

3.      What levels of user requirements can be expressed with business rules and application scenarios? Provide an example from your workplace.

4.      What new development roles and skills are required in integrated software and knowledge engineering?

Case Study

1.      Write a scenario to add a new business area to the knowledge base.

2.      Write a scenario to add a new fact to this business area.

3.      Write a scenario to relate two facts from this business area.

4.      Describe one of the knowledge technologies that may be beneficial to your business. Suggest software architecture for a system that can use this technology.

5.      Research and describe knowledge technology elements in one of the products below or go beyond the list:

·      IBM Web Sphere

·      Cyc or OpenCyc products

·      Your own choice

6.      Provide an example of a knowledge-driven architecture applicable to your workplace.

References

1.  Cycorp Common Sense Knowledge: http://www.cyc.com.

2.  OpenCyc project: http://www.OpenCyc.org.

3. Zhuk, J. Distributed active knowledge and process base, Patent Pending: http://uspto.gov.

4.  Internet Technology School, Inc.: http://JavaSchool.com.

 5. Zhuk, J., Internet Technology School, Inc., Knowledge-driven architecture, Patent Pending, http://uspto.gov

6.  Gamma, E., R. Helm, R. Johnson, and J. Vlissides. 1995. Design Patterns, Elements of Reusable Object-Oriented Software. Boston: Addison-Wesley.