ROWL: Rule Language in OWL and Translation Engine for JESS

 
Authors:  Fabien L. Gandon, Mithun Sheshagiri, Norman M. Sadeh (sadeh@cs.cmu.edu)
Copyright: See the bottom of this page
Date: Feb 15, 2004
Configuration used:
Sun JDK 1.4, XSLT 1.0,JESS 6

 This page contains source code and instructions to frame rules in OWL, transform them into Jess (Java Expert System Shell) rules. In addition, the page also contains a small tutorial that will help you frame rules in RDF/XML using our rule ontology.

Required technologies and software.

These files are being made available as part of the DAML initiative in an effort to promote broader, more rapid adoption of the Semantic Web. No warranty is being made, whatsoever, on the reliability or correctness of this implementation.  The code provided herein has been successfully used in the myCampus project, a Semantic Web environment for pervasive computing where agents reason about context and privacy concerns of the user.

The remainder of the document is as follow:
System Overview: A brief overview of our system that explains the overall architecture and the modules involved.
Rules and ROWL: A basic description of rules, the ROWL ontology for framing rules in RDF and use of variables in our system.
Rules using ROWL: A tutorial that illustrates the use of rules using an example.
Using ROWL with other Expert Systems: Some tips regarding the use of rules in Expert Systems other than JESS.
Tips for using the stylesheets: This section discusses controlling type information using type parameter in the stylesheet and other tips.

 System Overview

  The system enables users to frame rules in RDF/XML syntax using an ontology in OWL. Using XSLT stylesheets, the rules in RDF/XML are transformed into forward-chaining defrules in JESS. We make use of two more stylesheets to transform ontology and instance files into Jess undordered facts of the form (triple (predicate p) (subject s) (object  o)). The defrules generated by our system adhere to this format.

Note the stylesheets for transforming ontologies and annotations were part of an OWL Engine release. Related information can be found here.

 As shown in Fig. 1, our system uses stylesheets to transform OWL ontologies, instances and rules into the CLIPS format using XSLT stylesheets. The file with facts and rules in CLIPS are then fed to JESS which enables inferencing and rule invocation.

Principle behind the engine

Figure 1. Shaded area illustrates the use of ROWL.

 Rules and ROWL

  Rules in our system are of the form body => head. The body and head are also referred to as antecedent and consequent respectively. Both, the body and the head are conjunctions of Predicate-Subject-Object (PSO) triples. The triples can have variables in them. A rule of the form body=>head is interepreted as: if conditions specified in the body (antecedent) hold then the conditions specified in the head (consequent) should also hold. In other words, if there are facts in the system which match the pattern of triples in the body then the system should also contain facts that correspond to the pattern of triples in the head. Variables can be part of both the head and the body. Also, every variable in the head should be present in the body as well. Since Jess is essentially a forward-chaining expert system (although there are ways to do backward-chaining), rules are executed as follows. Given a rule, the system tries to find facts that match the triple pattern in the body, whenever a pattern is found, the triple patterns in the head are asserted with corresponding variable bindings.

The ROWL ontology is a simple ontology consisting of a class Rule which is used to embody rules. It also has two properties - head and tail. The head and tail contain assertions that correpond to triple patterns. ROWL also defines a class Variable used for instantiating variables in the RDF file containing the rules.
 
Variable instances can be declared in the file which contains the rule and local references can be made to these instances of Variables. In the RDF fragment below, person is an instance of class Person and and an instance of type Variable. Now the instance person can used like any other resource but will be treated as a variable while building defrules from the RDF/XML file.
<rowl:Variable rdf:ID="person"/>
<foo:Person rdf:about="#person"/>


Rules using ROWL

Consider the following ontology for capturing information about people you know.
<rdf:RDF xmlns:rdf="http://www.w3.org/1999/02/22-rdf-syntax-ns#"
xmlns:rdfs="http://www.w3.org/2000/01/rdf-schema#"
xmlns:owl="http://www.w3.org/2002/07/owl#"
xml:base="http://mycampus.cs.cmu.edu/ontology/foo"
xmlns="http://mycampus.cs.cmu.edu/ontology/foo#">
<owl:Class rdf:ID="Person"/>
<owl:DatatypeProperty rdf:ID="name">
<rdfs:domain rdf:resource="#Person"/>
<rdfs:range rdf:resource="http://www.w3.org/2000/01/rdf-schema#Literal"/>
</owl:DatatypeProperty>
<owl:DatatypeProperty rdf:ID="email">
<rdfs:domain rdf:resource="#Person"/>
<rdfs:range rdf:resource="http://www.w3.org/2000/01/rdf-schema#Literal"/>
</owl:DatatypeProperty>
<owl:ObjectProperty rdf:ID="webpage">
<rdfs:domain rdf:resource="#Person"/>
<rdfs:range rdf:resource="http://www.w3.org/2000/01/rdf-schema#Resource"/>
</owl:ObjectProperty>
<owl:ObjectProperty rdf:ID="relation">
<rdfs:domain rdf:resource="#Person"/>
<rdfs:range rdf:resource="#Person"/>
</owl:ObjectProperty>
<owl:DatatypeProperty rdf:ID="location">
<rdfs:domain rdf:resource="#Person"/>
<rdfs:range rdf:resource="http://www.w3.org/2000/01/rdf-schema#Literal"/>
</owl:DatatypeProperty>
<owl:Class rdf:ID="Group"/>
<owl:Class rdf:ID="FriendCircle">
<rdfs:subClassOf rdf:resource="#Group"/>
</owl:Class>
<owl:Class rdf:ID="OfficeMates">
<rdfs:subClassOf rdf:resource="#Group"/>
</owl:Class>
<owl:ObjectProperty rdf:ID="member">
<rdfs:domain rdf:resource="#Group"/>
<rdfs:range rdf:resource="#Person"/>
</owl:ObjectProperty>
<owl:ObjectProperty rdf:ID="friend">
<rdfs:subPropertyOf rdf:resource="#relation"/>
</owl:ObjectProperty>
<owl:ObjectProperty rdf:ID="colleague">
<rdfs:subPropertyOf rdf:resource="#relation"/>
</owl:ObjectProperty>
</rdf:RDF>
Person is a class with the following properties: name, email, location, webpage and relation. The range of all properties of Person except relation is rdfs:Literal. Range of relation is a the class Person. friend and colleague are subproperties of relation. Group is a class with a single property member. FriendCircle and OfficeCircle are subclasses of Group.

We use the above ontology to make the following assertions (fooInstance.rdf):
<?xml version="1.0" encoding="ISO-8859-1"?>
<!DOCTYPE uridef[
  <!ENTITY rdf "http://www.w3.org/1999/02/22-rdf-syntax-ns">
<!ENTITY rdfs "http://www.w3.org/2000/01/rdf-schema">
<!ENTITY owl "http://www.w3.org/2002/07/owl">
<!ENTITY xsd "http://www.w3.org/2000/10/XMLSchema">
<!ENTITY foo "http://mycampus.cs.cmu.edu/ontology/foo">
<!ENTITY DEFAULT "http://mycampus.cs.cmu.edu/ontology/fooIns">
<!ENTITY THIS     "http://mycampus.cs.cmu.edu/ontology/fooIns">
<!ENTITY nbsp "&#160;">
]>
<rdf:RDF xmlns:rdf="&rdf;#" xmlns:rdfs="&rdfs;#" xmlns:owl="&owl;#"
         xmlns:xsd="&xsd;#" xmlns:foo="&foo;#" xmlns="&DEFAULT;#"
         xml:base="http://mycampus.cs.cmu.edu/ontology/fooIns">
  <foo:Person rdf:ID="me">
    <foo:name>Magnus Morrison</foo:name>
    <foo:webpage rdf:resource="http://www.magnusplanet.com"/>
    <foo:location>Belize</foo:location>
    <foo:email>magnusm@magnusplanet.com</foo:email>
  </foo:Person>
  <foo:Person rdf:ID="p1">
    <foo:name>John Smith</foo:name>
    <foo:webpage rdf:resource="http://foo.bar/smith"/>
    <foo:location>Baltimore</foo:location>
    <foo:email>john.smith@foo.com</foo:email>
    <foo:friend rdf:resource="#me"/>
  </foo:Person>
  <foo:Person rdf:ID="p3">
    <foo:name>Mary Jane</foo:name>
    <foo:webpage rdf:resource="http://foobaz.org/jane"/>
    <foo:location>San Diego</foo:location>
    <foo:email>john.smith@foo.com</foo:email>
    <foo:friend rdf:resource="#me"/>
  </foo:Person>
  <foo:Person rdf:ID="p2">
    <foo:name>Isabell Peters</foo:name>
    <foo:webpage rdf:resource="http://bar.foo/peters"/>
    <foo:location>Pittsburgh</foo:location>
    <foo:email>isabell.peters@foo.com</foo:email>
    <foo:colleague rdf:resource="#me"/>
  </foo:Person>
  <foo:FriendCircle rdf:ID="my_mates"/>
  <foo:OfficeMates rdf:ID="o_mates"/>
</rdf:RDF>


The files that contains triples represented as Jess facts are available here: foo.jess (ontology) and fooInstance.jess (annotations). Now the user of this system wants to aggregate all his/her friends into an instance of FriendCircle. Friends are identified using the foo:friend property; all instances of the class Person whose friend property points to the instance me belong to the friend circle. In generic rule language the rule is framed as
friend(?person, me) => member(?person, my_mates) where me is particular instance of class Person, ?person represent any instance of class Person, my_mates is an instance of the class FriendCircle.
 
The rule in ROWL would look like the following:

<rdf:RDF xmlns:rdf="&rdf;#" xmlns:rdfs="&rdfs;#" xmlns:owl="&owl;#"
         xmlns:rowl="&rowl;#" xmlns:var="&var;#" xmlns:foo="&foo;#"
         xmlns:xsd="&xsd;#" xmlns:app="&app;#">
  <rowl:Variable rdf:ID="person"/>
  <rowl:Rule rdf:ID="rule1">
    <rdfs:label>Freinds belong to the FriendCircle Group</rdfs:label>
    <rowl:head rdf:parseType="Collection">
      <foo:FriendCircle rdf:about="&app;#my_mates">
        <foo:member>
          <foo:Person rdf:about="#person"/>
        </foo:member>
      </foo:FriendCircle>
    </rowl:head>
    <rowl:body rdf:parseType="Collection">
      <foo:Person rdf:about="#person">
        <foo:friend rdf:resource="&app;#me"/>
      </foo:Person>
    </rowl:body>
  </rowl:Rule>
</rdf:RDF>


The complete file with all the namespace declaration can be found here: rule1.rdf

The representation of the above rule in terms of PSO triples is shown below:
Rule:
        body:
                     (triple
                                (predicate    type)
                                (subject       ?person)
                                (object        foo#Person))

                     (triple
                                (predicate    foo#friend)
                                (subject      ?person)
                                (object        fooIns#me))



       
head:
                  (triple
                              (predicate  type)
                              (subject     fooIns#my_mates)
                              (object       foo#FriendCircle"))
  
                   (triple
                             (predicate  foo#member)
                             (subject     fooIns#my_mates)
                             (object      ?person1))
      
                   (triple
                              (predicate  type)
                              (subject    ?person1)
                              (object      foo#Person"))

The first triple isolated all instances of the class Person. The second triples looks for all instances of Person who are linked to the instance me (of class Person) by the property friend. The head of the rule associates all triples that match the body to an instance of FriendCircle using the property member. The type information in the head can be eliminated by setting the type parameter to false. (Note: complete namespaces have not been shown for the sake of brevity).
 
The above rule is looks like the following in Jess:
(defrule  Friends_belong_to_the_FriendCircle_Group
    (triple
                (predicate  "http://www.w3.org/1999/02/22-rdf-syntax-ns#type")
                (subject    ?person1)
                (object     "http://mycampus.cs.cmu.edu/ontology/foo#Person"))

    (triple
                (predicate  "http://mycampus.cs.cmu.edu/ontology/foo#friend")
                (subject    ?person1)
                (object    
"http://mycampus.cs.cmu.edu/ontology/fooIns#me))
 
   
      => 
     
  (assert 
    (triple
                (predicate  "http://www.w3.org/1999/02/22-rdf-syntax-ns#type")
                (subject    "http://mycampus.cs.cmu.edu/ontology/fooIns#my_mates")
                (object     "http://mycampus.cs.cmu.edu/ontology/foo#FriendCircle")))
  (assert 
    (triple
                (predicate  "http://mycampus.cs.cmu.edu/ontology/foo#member")
                (subject    "http://mycampus.cs.cmu.edu/ontology/fooIns#my_mates")
                (object     ?person1)))
  (assert 
    (triple
                (predicate  "http://www.w3.org/1999/02/22-rdf-syntax-ns#type")
                (subject    ?person1)
                (object     "http://mycampus.cs.cmu.edu/ontology/foo#Person"))))


 This tranformation from RDF/XML to Jess defqueries can be done using the following XSLT stylesheet ROWL2Jess.xsl

As you can see in the above rule, the variable ?person should also be an instance of class Person. One could also frame a rule without this constraint i.e., the variable can be an instance of any class. We use the familiar "parent's brother is uncle" example to look illustrate the two cases. The syntax and example is taken from [3].

In generic rule langauge, the rule is as follows:
hasParent(?p1, ?p2)
∧ hasBrother(?p2, ?p3) => hasUncle(?p1, ?p3)

The two variations are as follows:
Case 1. The variables in the rule can be instances of any class.
Case 2. The variables in the above rule are instances of class Person

Rule for the case 1. in RDF and the correspinding defrule (omitting type information in the head)
<?xml version="1.0" encoding="ISO-8859-1"?>
<!DOCTYPE uridef[
  <!ENTITY rdf "http://www.w3.org/1999/02/22-rdf-syntax-ns">
<!ENTITY rdfs "http://www.w3.org/2000/01/rdf-schema">
<!ENTITY owl "http://www.w3.org/2002/07/owl">
<!ENTITY xsd "http://www.w3.org/2000/10/XMLSchema">
<!ENTITY var "http://mycampus.cs.cmu.edu/variable">
<!ENTITY foo "http://mycampus.cs.cmu.edu/ontology/foo">
<!ENTITY rowl "http://mycampus.cs.cmu.edu/ROWL">
<!ENTITY app "http://mycampus.cs.cmu.edu/ontology/fooIns">
<!ENTITY nbsp "&#160;">
]>
<rdf:RDF xmlns:rdf="&rdf;#" xmlns:rdfs="&rdfs;#" xmlns:owl="&owl;#"
         xmlns:rowl="&rowl;#" xmlns:var="&var;#" xmlns:foo="&foo;#"
         xmlns:xsd="&xsd;#" xmlns:app="&app;#">
  <rowl:Variable rdf:ID="p1"/>
  <rowl:Variable rdf:ID="p2"/>
  <rowl:Variable rdf:ID="p3"/>
  <rowl:Variable rdf:ID="p4"/>
  <rowl:Rule rdf:ID="ParentBroUnc">
    <rdfs:label>Uncle Rule</rdfs:label>
    <rowl:head rdf:parseType="Collection">
      <rowl:Variable rdf:about="#p1">
        <app:uncle>
          <rowl:Variable rdf:about="#p3"/>
        </app:uncle>
      </rowl:Variable>
    </rowl:head>
    <rowl:body rdf:parseType="Collection">
      <rowl:Variable rdf:about="#p1">
        <app:parent rdf:resource="#p2"/>
      </rowl:Variable>
      <rowl:Variable rdf:about="#p2">
        <app:brother rdf:resource="#p3"/>
      </rowl:Variable>
    </rowl:body>
  </rowl:Rule>
</rdf:RDF>



(defrule  Uncle_Rule
    (triple
      (predicate  "http://mycampus.cs.cmu.edu/ontology/fooIns#parent")
      (subject    ?p1)
      (object        ?p2)
    )

    (triple
      (predicate  "http://mycampus.cs.cmu.edu/ontology/fooIns#brother")
      (subject    ?p2)
      (object        ?p3)
    )

      =>  
      
  (assert  
    (triple
      (predicate  "http://mycampus.cs.cmu.edu/ontology/fooIns#uncle")
      (subject    ?p1)
      (object  ?p3)
  )
    )
)


Rule for the case 2. in RDF and the correspinding defrule (omitting type information in the head)
<?xml version="1.0" encoding="ISO-8859-1"?>
<!DOCTYPE uridef[
  <!ENTITY rdf "http://www.w3.org/1999/02/22-rdf-syntax-ns">
<!ENTITY rdfs "http://www.w3.org/2000/01/rdf-schema">
<!ENTITY owl "http://www.w3.org/2002/07/owl">
<!ENTITY xsd "http://www.w3.org/2000/10/XMLSchema">
<!ENTITY var "http://mycampus.cs.cmu.edu/variable">
<!ENTITY foo "http://mycampus.cs.cmu.edu/ontology/foo">
<!ENTITY rowl "http://mycampus.cs.cmu.edu/ROWL">
<!ENTITY app "http://mycampus.cs.cmu.edu/ontology/fooIns">
<!ENTITY nbsp "&#160;">
]>
<rdf:RDF xmlns:rdf="&rdf;#" xmlns:rdfs="&rdfs;#" xmlns:owl="&owl;#"
         xmlns:rowl="&rowl;#" xmlns:var="&var;#" xmlns:foo="&foo;#"
         xmlns:xsd="&xsd;#" xmlns:app="&app;#">
  <rowl:Variable rdf:ID="p1"/>
  <rowl:Variable rdf:ID="p2"/>
  <rowl:Variable rdf:ID="p3"/>
  <rowl:Variable rdf:ID="p4"/>
  <rowl:Rule rdf:ID="ParentBroUnc">
    <rdfs:label>Uncle Rule</rdfs:label>
    <rowl:head rdf:parseType="Collection">
      <app:Person rdf:about="#p1">
        <app:uncle>
          <app:Person rdf:about="#p3"/>
        </app:uncle>
      </app:Person>
    </rowl:head>
    <rowl:body rdf:parseType="Collection">
      <app:Person rdf:about="#p1">
        <app:parent rdf:resource="#p2"/>
      </app:Person>
      <app:Person rdf:about="#p2">
        <app:brother>
          <app:Person rdf:about="#p3"/>
        </app:brother>
      </app:Person>
    </rowl:body>
  </rowl:Rule>
</rdf:RDF>



(defrule  Uncle_Rule
    (triple
      (predicate  "http://www.w3.org/1999/02/22-rdf-syntax-ns#type")
      (subject  ?p1)
      (object        "http://mycampus.cs.cmu.edu/ontology/fooIns#Person")
    )


    (triple
      (predicate  "http://mycampus.cs.cmu.edu/ontology/fooIns#parent")
      (subject    ?p1)
      (object        ?p2)
    )

    (triple
      (predicate  "http://www.w3.org/1999/02/22-rdf-syntax-ns#type")
      (subject  ?p2)
      (object        "http://mycampus.cs.cmu.edu/ontology/fooIns#Person")
    )


    (triple
      (predicate  "http://mycampus.cs.cmu.edu/ontology/fooIns#brother")
      (subject    ?p2)
      (object  ?p3)
  )
  
    (triple
      (predicate  "http://www.w3.org/1999/02/22-rdf-syntax-ns#type")
      (subject  ?p3)
      (object        "http://mycampus.cs.cmu.edu/ontology/fooIns#Person")
    )


      =>  
      
  (assert  
    (triple
      (predicate  "http://mycampus.cs.cmu.edu/ontology/fooIns#uncle")
      (subject    ?p1)
      (object  ?p3)
  )
    )
)



Using ROWL with other Expert Systems

Although, our system currently supports Jess, our technique can be ported to any other system by changing the XSLT stylesheet. Modifications will have to take into account the following:
1. How facts are represented in the system
2. The way facts are asserted.
3. The way rules are framed.

You can use the following files to make changes using a text editor with a search and replace option.
1. portOntology
2. portAnnotation
3. portROWL

(triple (predicate p) (subject s) (object o))

The current XSLT stylesheet produces facts in the above format. To change "triple" to some other format say "PropertyValue", replace all occurence of <ph>triple</ph> with PropertyValue in above three files. Similarly, defrule, assert, =>, predicate, subject and object are enclosed within <ruleCons>, <assert>, <imp>, <pred>, <sub> and <obj> tags respectively.

Tips for Using Stylesheets

1. Ensure that the xml:base is specified for using the ontology and annotation stylesheets.
2. The name of the rule is generated from the rdfs:label. Spaces are replaced by '_' while naming the rule.
3. Use "rowl" as the prefix for the ROWL ontology.
4. Range of properties must be specified using a seperate tag and not by using rdf:resource for producing type information in the head.
5. Remember, if you want to control type information in the head, use the type parameter in the ROWL2Jess.xsl file. Setting type='false' will produce rules without type information in the head.

Points 1, 3 and 4 will be addressed in the next release.

References and Related Work


[1] Gandon, F. and Sadeh, N., “Semantic Web Technologies to Reconcile Privacy and Context Awareness”, Web Semantics Journal. Vol. 1, No. 3, 2004.
[2]Gandon, F. and Sadeh, N., “
A Semantic eWallet to Reconcile Privacy and Context Awareness”, Second International Semantic Web Conference, Florida, October 2003.

[3] Ian Horrocks, Peter F. Patel-Schneider, Harold Boley, Said Tabet, Benjamin Grosof and Mike Dean, A Semantic Web Rule Language Combining OWL and RuleML, November, 2003.
[4] Ian Horrocks and Peter F. Patel-Schneider, A Proposal for an OWL Rules Language, October 2003.
[5] Benjamin Grosof, Mahesh Gandhe, and Tim Finin, SweetJess: Translating DamlRuleML to Jess, Proceedings of the International Workshop on Rule Markup Languages for Business Rules on the Semantic Web 14 June 2002, Sardinia (Italy) in conjunction with the First International Semantic Web Conference (ISWC2002). Available at http://userpages.umbc.edu/~mgandh1/

Copyright Notice and Disclaimer

  COPYRIGHT (C) 2001-2004 Mobile Commerce Laboratory -  School of Computer Science - Carnegie Mellon University 5000 Forbes Avenue - Pittsburgh, PA 15213-3890 - ALL RIGHTS RESERVED.

 By downloading the files provided herein you indicate your agreement with this copyright notice and disclaimer. Permission to use, copy and modify this version of the software or any parts of it and its documentation is hereby granted for RESEARCH ONLY purposes and provided that the above copyright notice and this permission notice appear intact in all copies of the software, that you do not sell the software, nor include the software in a commercial package.

 The release of this software into the public domain does not imply any obligation on the part of the authors to release future versions into the public domain. The authors are free to make upgraded or improved versions of the software available for a fee or commercially only. Commercial licensing of the software is available by contacting Dr. Norman M. Sadeh (Norman.Sadeh@cs.cmu.edu) . The software is provided "as is" and without warranty of any kind, express, implied or otherwise, including without limitation, any warranty of merchantability or fitness for a particular purpose. The software is experimental only and has not been designed for, tested or approved for hazardous use. The use of the software is at the user's own risk. Any conclusions you may draw based on the software or its use are your own. We expressly disclaim any responsibility or liability for any and all adverse effects, including personal, bodily, property or business injury, and for damages or loss of any kind whatsoever, resulting directly or indirectly, whether from negligence, intent or otherwise, from the use or disuse of the software, from errors in the software, or from misunderstandings arising from the software itself, its use or its documentation.

 

Acknowledgements

  This material is based on research conducted at Carnegie Mellon University's Mobile Commerce Lab. (School of Computer Science) as part of the DAML initiative. This work has been sponsored by the Air Force Research Laboratory under contract F30602-02-2-0035 and by the Defense Advanced Research Project Agency  under contract F30602-98-2-0135. The US Government is authorized to reproduce and distribute reprints for Governmental purposes notwithstanding any copyright notation thereon. This work was also in part supported by grants from IBM, HP, Symbol, Boeing, Fujitsu and the IST Program (SWAP project). The views and conclusions contained herein are those of the authors and should not be interpreted as necessarily representing the official policies or endorsements, either expressed or implied, of the Air Force Research Laboratory or the U.S. Government.