The Ontopia Omnigator

Users' Guide

Affiliation:Ontopia
Date:$Date: 2001/07/05 09:26:05 $
Version:1.1 ($Revision: 1.25 $)

Abstract

This document is the users' guide to the Ontopia Omnigator, the omnivorous topic map navigator, built using the Ontopia Navigator SDK. It explains how to navigate topic maps using the Omnigator, and also provides some guidance on how to create and load your own topic maps. It assumes some basic knowledge about topic maps. We welcome any suggestions you might have on ways of improving this User Guide. Please send them to dev@ontopia.net.

Table of contents

1. Introduction
1.1. A word about the user interface
1.2. About this user guide
1.3. How the Omnigator works
2. The Guided Tour
2.1. The Welcome Page
2.2. The Topic Map Page
2.3. The Topic Page (of a topic type)
2.4. The Topic Page (of an individual topic)
2.5. Cruising the Knowledge Web
2.6. The Topic Page (of an occurrence type)
2.7. The Topic Page (of an association type)
3. Advanced Omnigator Topics
3.1. The Manage Page
3.2. The Plugin Page
3.3. The Customise Page
3.4. The Plugins
3.4.1. The Statistics plugin
3.4.2. The Filter plugin
3.4.3. The Merge plugin
3.4.4. The Export plugin
3.4.5. The Reload plugin
4. Building Your Own Topic Map
4.1. Step 1: Determining scope and basic ontology
4.2. Step 2: Getting the framework in place
4.3. Step 3: Creating the first topic
4.4. Step 4: Adding a topic type
4.5. Step 5: Adding occurrences
4.6. Step 6: Using Ontopia published subjects
4.7. Step 7: Adding associations
4.8. Step 8: Reification
4.9. Step 9: Over to you
4.10. Jill's First TM

1. Introduction

The Omnigator is an application that lets you load and browse any topic map, including your own, using a standard web browser. The name is a contraction of "omnivorous navigator", and was chosen to underline the application's principle design goal, which is to be able to make sense of any conforming topic map. The Omnigator is intended as a teaching aid, to help you understand topic map concepts, and as an aid in developing your own topic maps. It is built on topic of the Ontopia Topic Map Engine, using the Ontopia Navigator Framework.

1.1. A word about the user interface

Before we go any further we want to impress upon you that the Omnigator's user interface is not (emphatically not!) what we would recommend in an end-user application. End-users shouldn't need to know that the application they are using is driven by a topic map. They don't need to understand concepts like "topic", "topic type", "association", and "facet", and they shouldn't even be exposed to such terms. The user should simply experience a user interface that for once makes it possible to really find the information they are looking for, quickly, easily, and intuitively.

So why have we chosen not to hide the underlying machinery in the user interface of the Omnigator? Precisely because it is intended as a teaching aid targeted at authors, knowledge workers, documentalists, and developers, who want need to understand more about topic maps and perhaps even create their own. So don't be surprised by the "jargon" terms you will come across: They are there for a purpose. Think instead about how the real-world applications you will build can hide the technicalities while at the same time harnessing the power of topic maps to provide an even more exhilarating experience for your end users! The Ontopia Navigator Framework is the toolkit you need for building that kind of application. The Omnigator is just one possible implementation.

1.2. About this user guide

This guide starts with a brief tour of one of the topic maps included in the Omnigator distribution, explaining the various aspects of the user interface and the information it provides. It that assumes you have some basic knowledge about topic maps. (If you don't, try reading one of the simple introductions, such as The TAO of Topic Maps, available from the Ontopia web site, or the chapter "Topic maps: Knowledge navigation aids" in the XML Handbook. You might also want to look at the XTM Specification and the ISO 13250 standard.)

Following the Guided Tour we discuss some of the more sophisticated aspects of the Omnigator. Finally, for those that have never created their own topic map, we offer a short tutorial to prove just how easy it is to get up and running with your very first topic map in the Omnigator!

If you want to know how the Omnigator works, a brief description follows. If you're not interested, go straight to the next chapter.

1.3. How the Omnigator works

The Omnigator uses a simple client-server architecture based on a standard http protocol.

On the server side there is a J2EE web application built using the Ontopia Topic Map Engine and Navigator Framework, that runs in the Tomcat web server. This application reads (and writes) topic maps and generates HTML pages on the fly. On the client, a standard web browser receives these HTML pages and displays a view of some portion of the topic map. This view is rich in links, built from the data structures that constitute the topic map. Each time the user clicks on a link, a request is sent to the server application, resulting in a new set of information extracted from the topic map.

If you have a standard installation of the free Omnigator download, the server will be running on the same machine as the client. Alternatively, your local technical support team may have installed the server on another machine. If you are using our online demo, the server is on the Ontopia web site. But whatever the configuration, the view from the client side will be pretty much the same.

2. The Guided Tour

This chapter assumes that you have a correctly configured installation of the Omnigator, or that you are using the online demo. (For installation information, see the installation guide that accompanies your distribution.)

2.1. The Welcome Page

To begin this demonstration start your web browser and point it at one of the following URLs:

Local installation
http://localhost:8080/navigator/
Online demo
http://www.ontopia.net/navigator/
Custom installation
Contact your local technical support team for details.

You should now see the Welcome Page, saying "Welcome to the Omnigator". If you have difficulty getting to this starting point, then please refer to the install documentation, contact your local technical support team, or contact the Ontopia support team at support@ontopia.net.

The Welcome Page

On the Welcome Page there is a list of topic maps that have been loaded into the application. (You will see how to add one of your own in section 3.1 of this user guide). The Welcome Page also contains a number of useful links to provide you with short cuts to topic map information and examples.

This demonstration uses Steve Pepper's Italian Opera topic map, a fairly small but semantically rich topic map that has been used in many talks and tutorials in the last few years. This topic map exists in two versions. The definitive version is maintained in the syntax defined by the ISO 13250 topic map standard; a derived version uses the XTM syntax defined by TopicMaps.Org. The XTM version is slightly smaller, since it takes advantage of the mergeMap facility introduced by XTM. Our demo uses the XTM version.

2.2. The Topic Map Page

To go to the opera.xtm topic map, click on it in the list of topic maps, which is on the left hand side of the Welcome Page. A new page opens, shown in the figure below. We call this page the Topic Map Page. At the top you will see a row of buttons. The Welcome button takes you back to the Welcome Page. The other buttons are generated by plugins, to which we will return in section 3.4.

The Topic Map Page for the Italian Opera topic map

The purpose of the Topic Map Page is to provide you with various overviews of the topic map as a whole. The views can be chosen from the drop-down list on the left, as follows:

Ontology
The ontology view shows the "classes", or "kinds of things" that exist in the topic map. It does so by providing lists of topic types (labelled "Subject Indexes"), association types ("Relationship Indexes"), association role types ("Role Indexes"), and occurrence types ("Resource Indexes"). For topic maps that use facets (available only in the ISO syntax), there will also be a list of facet types ("Metadata Indexes"). All of these types are also topics and clicking on any one of them makes it the current topic, but more about that in a moment.
Master Index
The master index view counts and lists all the topics in the topic map, in alphabetical order, under the heading "Complete subject index".
Themes
The themes view lists all topics that are used as themes in the topic map. (Themes are topics that are used to defined scope.) The themes are grouped according to the kinds of topic characteristics (names, variant names, occurrences, and associations) they are used to scope.

2.3. The Topic Page (of a topic type)

Having investigated these three views, and hopefully gained some idea of what the topic map itself is all about, go to the ontology view and click on the topic 'composer'. A new page opens, shown in the diagram below. We call this page the Topic Page and 'composer' is the current topic.

The Topic Page for 'composer' (a topic type)

The Topic Page presents the information held in the topic map about the current topic, in this case the information about the topic 'composer'.

The kind of information presented will depend on the nature of the current topic. The main title will always be the most appropriate name of the topic, based on the current context (described in section 3.4.2). In addition, all the base names (and any variant names) of this topic will be shown, along with the themes that defined their scope. In the illustration we see that the topic 'composer' has three names: one in the unconstrained scope, one in the scope 'Italian', and one in the scope 'Norwegian'.

Most topics will have a "Key facts" section. In the case of the topic 'composer' (which defines a class of topic) we see its superclasses, 'musician' and 'person'. For other kinds of topics we might see metadata, definitions, or other information, as the screen shots to follow will show.

Because 'composer' is a topic type (i.e., a topic that defines a class of topics), we also get a list of topics of this type, in other words, an index of composers. Because 'composer' is also a role that is played in associations of certain types (e.g., the 'composed by' association), we also get a list of topics that play the role of composer. (Not surprisingly, it is identical to the list of topics of type composer. Other topics, that are only used as topic types or association role types, but not both, e.g. 'play' and 'person', will only have one such list.)

2.4. The Topic Page (of an individual topic)

All the themes, classes, topic instances, and role players on a Topic Page are also topics. You can click on any one of them, and it then becomes the current topic. Try this by clicking on the topic 'Puccini'. The result is a new Topic Page, shown below, with Puccini as the current topic.

The Topic Page for 'Puccini' (an individual topic)

'Puccini' is a different kind of topic than 'composer'. Whereas 'composer' is a topic type and association role type, 'Puccini' is an individual, and therefore the kind of information that is presented is different. We still have the main title and a list of names. We also have a "Key Facts" section, but this time the contents are rather different. What we now see are the subheadings Types, Metadata, and Description, which consist of the following:

Types simply lists the classes (or topic types) of which 'Puccini' is an instance, in this case, composer.

Metadata displays occurrences of the topic 'Puccini' that belong to the class metadata occurrence. This is a special kind of occurrence defined by Ontopia as a published subject. (Ontopia published subjects are described in section 4.6 of the tutorial.) In the case of Puccini, the metadata is the composer's dates of birth and death.

Description displays occurrences belonging to the class description occurrence, also defined as a published subject (see section 4.6).

All the other occurrences of the topic 'Puccini' are shown on the right, under the heading "Resources". Note that occurrences are displayed in different ways, depending on whether the occurrences are internal or external to the topic map. With internal resources (encoded using <resourceData> elements in XTM syntax, or data URLs in ISO syntax), the contents of the resource are shown inline. (The dates of birth and death shown under the heading "Metadata" are examples of this.) With external resources (encoded using <resourceRef> elements in XTM syntax or regular URLs in ISO syntax), only the address of the resource is shown. Clicking on the address brings up the resource in a new window. In both cases, the type of the occurrence (also called the occurrence role) is shown in parentheses.

The final element on this page, headed "Related Subjects", lists topics that are related with the current topic through associations, grouped according to the type of the association. It is the equivalent of "see also's" in a back-of-book index. For 'Puccini' we have associations labelled 'born in', 'composed', 'died in', 'exponent of', and 'pupil of'. Under each of these labels are the associated topics. We see that Puccini was born in Lucca, that he composed a number of operas, including La Bohème, Tosca, and Turandot, that he died in Brussels, was an exponent of the musical style known as verismo, and that he was a pupil of Ponchielli. (The topics in parentheses behind each of the related topics denote the roles played by the related topics in their associations with the current topic. Thus 'Lucca' plays the role of 'place' in the born in association.)

2.5. Cruising the Knowledge Web

Click now on 'Lucca'. A new topic page opens, and Lucca is the current topic. It is a topic of type 'city', located in Italy, and the birthplace of both Puccini and Catalani. The association with Puccini is the same as the one we just used to get to this page, it is simply labelled differently. This illustrates an important point about topic maps: There is no directionality in associations, just different roles played by the participants, thus giving a structure which can be navigated in any direction required by an application. (To find out how to label your association types differently in different contexts, see section 4.7 in the tutorial.)

This Topic Page contains one piece of information of a different kind than those we have seen so far: the subject indicator. Subject indicators establish the subject that a topic represents (or reifies) and is the preferred mechanism for ensuring the successful merging of topic maps. (Reification is described in section 4.8.)

Now click on 'Catalani'. He becomes the current topic. We see that he too was a composer of operas, born in Lucca (well, we already knew that: that's how we found him), and that he died in Milan.

Click on 'Milan'. Milan is an interesting city: Only one person was born there, but lots of people died there! Why? Well, if you know anything about Italian opera, you know that Milan is the home of the opera house La Scala, the "Mecca" of Italian Opera. A composer may not have happened to be born in Milan, but if he was any good he would tend to gravitate there during his lifetime, and might well end up dying there! (This, by the way, is an interesting example of the kind of new insights revealed by the juxtaposition of information found in a topic map. The author is this topic map did not set out to illustrate Milan's role as the Mecca of Italian opera; that fact was "revealed" by the characteristics that collectively constitute the topic 'Milan'.)

Click now on 'Teatro alla Scala', and you will see a list of all the operas that were first performed there. Choose 'Madame Butterfly'. You see the date of the first performance, the name of its most famous aria, the play on which it was based, its principal characters, who the composer was (our old friend, Puccini), etc.

What you are essentially doing now is wandering around a semantic network, or knowledge web, about Italian opera. Hopefully you are learning a lot about that domain in the process, even without visiting any of the information resources themselves. To delve deeper into a particular topic of interest, simply follow a link to one of the resources. For Madame Butterfly they include two synopses, the libretto, and more.

2.6. The Topic Page (of an occurrence type)

So far we have only looked at topics that type other topics and association roles ('composer'), and topics that are individuals ('Puccini', 'Lucca', 'Catalani', 'Milan', 'La Scala', 'Madame Butterfly'). Now let's look at a topic that is an occurrence type. Under "Resources" find one of the occurrences that is of type 'AZ Opera synopsis' and click on the link in parentheses; 'AZ Opera synopsis' becomes the current topic. The information shown for a topic that types occurrences is of a different kind: What you see now is (on the left) a list of topics that have occurrences of this type, and (on the right) the addresses of all those occurrences. (If any of them had been internal resources you would see the contents of the resource rather than its address.)

The Topic Page for 'AZ Opera synopsis' (an occurrence type)

To see another example of an occurrence type topic, click on 'Aida' (at the top of the list of occurrences), and then on 'première' (under the "Metadata" heading). The result is an alphabetically ordered list of every topic that has a première date, and a chronological list of all the corresponding dates.

The Topic Page for 'première' (an occurrence type)

2.7. The Topic Page (of an association type)

Now go back to Tosca (first performed in 1900). Note the association type 'death of character' (of which there are four instances in Tosca). Click on the phrase 'death of character'. The topic 'death of character', which types these associations, becomes the current topic. The information shown for a topic that types associations is different yet again. This time we see all topics that play roles in associations of this type, grouped according to the role they play. (The association type 'death of character', is interesting in that, unlike most, it is not binary; that is, it can have more than two roles. In this case they are 'perpetrator', 'opera', 'victim', and 'cause of death'.)

The Topic Page for 'death of character' (an association type)

On this gory note, we end our guided tour of the basic Omnigator interface. The following chapter describes some of the more sophisticated aspects of the application, including the Manage Page, the Customise Page, and the Plugins. Thereafter follows a tutorial on creating your first topic map.

3. Advanced Omnigator Topics

3.1. The Manage Page

The Manage Page is used to control various aspects of the Omnigator's configuration, and to load, reload, and drop topic maps. (Note: The Manage Page is not accessible in the online demo, and may also have been disabled by your system administrator.) The functionality available via this page is described in detail in the documentation that accompanies the Developer's Edition of the Ontopia Navigator. Users of the Omnigator will primarily be interested in two Manage Page functions: controlling which topic maps are loaded and controlling which plugins are activated.

The Manage Page

Under the heading "Registry Items" the page presents a complete list of all the topic maps known to the system, based on the paths, extensions, and other information provided in the source.xml file. The default is to recognise all files with the extensions .xtm, .iso, or .ltm in the WEB-INF/xml/ directory. (LTM is the Linear Topic Map Notation, a compact clear-text syntax for topic maps, defined by Ontopia and useful for rapid prototyping. An example LTM file is included in the distribution of the Omnigator. Documentation is included in the distribution and can also be found at http://www.ontopia.net/download/ltm.html.)

Some of these topic maps (those listed in the application.xml configuration file) are loaded automatically. Others can be loaded manually by clicking on the Load button. Once loaded, the name of the topic map document is shown in a larger font, and the Load button changes to Drop and Reload buttons. Clicking on the name of a loaded topic map takes you straight to its Topic Map Page.

If the topic map document is not well-formed, or contains errors, it will not load. In such a case you will need to fix the errors and then try again. Some typical errors are:

Well-formedness error
The error message will tell you which line the error occurred on. You may have misspelt (or omitted) a start-tag or end-tag.
Character encoding error
You have used a character that is not legal in the character encoding the XML parser thinks you are using. This tends to happen when using one of the ISO 8859-x character encodings without declaring them in the XML declaration, since the parser will then assume that you are using the Unicode encoding UTF-8. The error message will suggest that an XML encoding declaration may be missing.
Namespace error
If you get the error message "No topic maps in document" you have either made a mistake in the namespace declaration (see section 4.2 for what it should look like), or you do not have a <topicMap> element in your document.

The Refresh Sources button is used to refresh the list of topic maps available to the system without restarting the application. This is useful if you have just added a new topic map (perhaps your own!) to the WEB-INF/xml/ directory.

3.2. The Plugin Page

The other part of the Manage Page that you might want to experiment with is the Plugins section. Plugins are modules that can be added to Navigator applications to provide additional functionality. (Some of those that are shipped with the Omnigator are described in section 3.4.) Clicking the Change button brings up the Plugins Page, which lists the names and descriptions of all the currently installed plugins and allows you to switch them on or off according to your needs.

3.3. The Customise Page

An Ontopia Navigator application such as the Omnigator is built in three layers, called Model, View, and Skin, respectively.

Models control the set of information that is extracted from the topic map and placed in each page. The Omnigator is shipped with three models, called "Simple" (the default), "Detail", and "Example".

Views control the visual structure or layout of the HTML pages appearing in the client browser. Two views are shipped: "No frames" (the default) and "Frames". The latter provides a more complex layout that allows topic map information and the content of occurrences to be viewed in different frames in the same window. The Frames layout is particularly well-suited to topic maps that have a relatively small number of associations per topic, and occurrences that you want to display automatically for each topic. (These are called "default occurrences" and are described in section 4.6.)

Skins are CSS stylesheets that control the styling of a page, i.e., improving its detailed appearance in browsers that support CSS. The Omnigator ships with four style sheets, some tasteful, others less so. (Try creating your own and send us the results!)

Clicking on the Customise button from anywhere in the Omnigator brings up the Customise Page:

The Customise Page

Experiment with changing the settings on this page to get a feel for the kind of flexibility offered to application designers. (Note: Depending on the caching used by your browser, you may have to use its reload command to see the effect of the changes.)

3.4. The Plugins

Plugins are a general concept that allows extra functionality to be dropped into any Navigator application by simply adding files to a directory. One example of how this could be used is to add a topic map visualisation application into the Omnigator. This section describes some of the plugins that are shipped with the product.

3.4.1. The Statistics plugin

This plugin is a report generator for topic maps. It provides an overview of the map's "vital statistics" and a detailed breakdown of some of its structures. Surprisingly often this information can be used to reveal inconsistencies or other problems with the topic map.

The Statistics Page

Most of the Statistics Page speaks for itself but it is worth pointing out some of the details. Under the heading "Association structure summary" is a list of association types broken down according to the roles that are played in those associations. Some association types only appear once (e.g., 'born in', with the roles 'person' and 'place'). Others may appear more than once (e.g., 'death of character'); when this happens it is due to different combinations of roles, which may either be perfectly legitimate (as in this case), or the result of an error in the topic map.

Note also that there are links from the typing topics (e.g. 'aria') straight to the Topic Page for that topic, and also links from the numbers in the second column to more detailed statistics on the particular typing topic in question.

3.4.2. The Filter plugin

This plugin allows you to customise your view of the topic map by establishing a context within which the scope of topic characteristics is evaluated. You do this by simply specifying the themes you are interested in via the Set Context Page.

The Set Context Page

Clicking on the Filter button brings up the Set Context Page. Here themes are grouped in two levels: first according to whether they are used to scope names, associations, or occurrences; and then by axis. Axes are determined automatically based on the classes to which themes belong. (Themes that don't belong to any class are grouped along an axis labelled "[unspecified]".)

Context themes are currently used for two purposes: selecting (i.e., choosing the most relevant name), and filtering (i.e., removing unwanted associations and occurrences).

Since name context is used for selection, it usually makes sense to only specify one name theme (at most) from each axis. Once you have set your preferences, the application will endeavour to use the most appropriate name based on whatever themes you have specified. To test this using the Italian Opera topic map, go to Puccini's opera La fanciulla del West, click on the Filter button, set your language preference (under Name Context) to English, and press "Activate". You will be returned to the same Topic Page, but now the name of the topic has changed to "The Girl of the Golden West".

Association context and occurrence context is used differently. In this case, the more themes you specify, the more associations and occurrences will be shown (unless you don't specify any themes, in which case all the associations and occurrences will be shown). To test this functionality, return to 'Puccini' and take careful note of the number of "Related Subjects" and "Resources". Now click on the Filter button and set your preferences to 'biography' (for association context) and 'Italian' (for occurrence context). Click "Activate" and compare the results. You should see only three association types ('born in', 'died in', and 'pupil of', all biographical) and a shorter list of occurrences.

Scope is a powerful mechanism but the ISO standard and the XTM specification neither specify nor constrain the ways in which it might be used. Since the Omnigator is designed to work across a wide range of topic maps, the implementation of selection and filtering by scope is based on certain general principles:

  1. A distinction is made between principal themes and incidental themes. Only principal themes are shown for selection on the Filter Page, otherwise the task of choosing among them would be difficult, to say the least. (The Italian Opera topic map uses over 70 topics as themes, but only half of them appear on the Set Context Page.)

    A principal theme is one that the author has deliberately employed in order to provide different kinds of topic names (e.g., in different languages) for use in different contexts, or to provide ways of reducing the number of associations or occurrences. An incidental theme, on the other hand, is one whose sole purpose is to disambiguate topic names (i.e., to avoid the topic naming constraint), or some other specific purpose that is under the control of the application rather than the user.

  2. The Omnigator only uses context to govern the selection of names (in situations in which just one name is required), and the filtering of associations and occurrences.

    When a name context is specified, the name whose scope has the most themes in common with the context is selected. (If there are no names whose scope contains a context theme, a name in the unconstrained scope is used, if it exists. If not, a name is chosen at random.)

    When an association or occurrence context is specified, only associations and occurrences that have at least one theme in common with the context are allowed through the filter (along with any that are in the unconstrained scope).

  3. Themes are grouped on the Set Context Page along axes of scope, according to the classes to which they belong. (The concept of axes was introduced in the paper Towards a General Theory of Scope, available at the Ontopia web site.)

    In the current version of the Omnigator the only purpose of axes is to provide a less cluttered user interface. However, later versions may exploit this concept to provide more powerful filtering capabilities. Topic map authors are therefore advised to follow what in any case is a sound design principle: Ensure that any topics used as themes have explicit types.

3.4.3. The Merge plugin

This plugin (which is not available in the online demo) allows you to merge a second topic map with the current one. Clicking on the Merge button takes you to a page with a scroll box from which you can choose any of the topic maps registered with the system (except the current topic map). After merging you can browse the resulting topic map.

The "Use name based merging" checkbox allows you to control whether or not topics with the same base names in the same scope will be merged in accordance with the topic naming constraint. If for whatever reason you don't want the system to check for violations of the topic naming constraint, uncheck this box.

Whatever your setting for the name based merging option, topics will be merged if they have the same subject indicator or subject address. In addition, duplicate names, associations, and occurrences will be removed.

Tip: A useful trick for testing the consistency of your topic map is to merge it with itself and compare the statistics of the result with those of the original. Put two copies of your topic map in the WEB-INF/xml/ directory under different names, and "Refresh Sources" from the Manage Page. Load one of them and run the Statistics plugin. Open the same topic map in a new browser window and merge it with the copy using the Merge plugin. (Note the way that the URL of the resulting merged topic map contains the names of both the source topic maps.) Run the Statistics plugin on the merged topic map and compare the results with the statistics of the first topic map. Any discrepancies between the two indicate inconsistencies in your topic map.

3.4.4. The Export plugin

This plugin creates and XTM or ISO 13250 serialisation of the current topic map and allows you to either save it directly to a disk file or loaded it as XML into your browser. Some of the situations in which you might want to use it are:

you have loaded a topic map in one format (ISO, XTM, or LTM) and want to write it out in another (ISO or XTM);

you have merged two or more topic maps and want to persist the result; or

you have modified the topic map in some way (for example, via a plugin) and want to save the result.

3.4.5. The Reload plugin

This plugin provides a useful shortcut when you are continually modifying your topic map and want to reload it often. To save you the trouble of going to the Manage Page every time, this plugin provides you with a button on the Topic Map and Topic Pages.

Since the Reload plugin is not automatically loaded when the application starts you will need to go to the Manage Page, find "Plugins", click on "Change", check the box beside "Reload", and click on "Apply". When you now go to a Topic Map Page or a Topic Page, the Reload button will be directly available. (If you want the Reload plugin to be automatically loaded every time the application starts, you will need to modify the file plugin.xml in the plugins/samples/ directory by changing the contents of the <activated> subelement of the <plugin> element with the id "reload" from "no" to "yes".)

4. Building Your Own Topic Map

This chapter provides a simple step by step tutorial for creating a (small) topicmap and loading it into your local copy of the Omnigator. You may be surprised just how easy it is. (We do assume a passing familiarity with start-tags, end-tags, and attributes, as used in SGML, XML, and HTML.)

In following the tutorial, you can of course cheat by copying and pasting the markup examples instead of typing everything in by hand. Our advice, though, is to do it the hard way. Nothing beats laboriously typing in angle brackets if you really want to understand the syntax (and, by extension, the concepts themselves). You will make mistakes – but you will also learn from them!

In time there will be user friendly editing tools that spare topic map authors from having to mark up their topic maps by hand. At the moment there are no good topic map editors available, but Ontopia plans to release one in October 2001. In the meantime, if you need to create and maintain large topic maps manually, you might investigate the Linear Topic Map notation (LTM), which is another of the input formats supported by the Ontopia Topic Map Engine. It is vastly more compact than XTM! (Documentation of LTM is included in all Ontopia distributions and can also be found at http://www.ontopia.net/download/ltm.html.

4.1. Step 1: Determining scope and basic ontology

Before you start, you need to know exactly what it is that you want to represent in your topic map. There are two parts to this: delimiting the scope of the topic map – that is, deciding the extent of the domain it should cover; and designing the basic ontology. In topic map terminology, an ontology is a precise description of the kinds of things which are found in the domain covered by the topic map: in other words, the set of topics that are used to define classes of topics, associations, roles, and occurrences. (The term is also used in other fields, such as philosophy, where it has other meanings.)

To make things easy we have chosen a subject domain that ought to appeal to you. The subject is you and the company you work for (or may one day work for). The scope can easily be extended to cover your colleagues, the projects in which you are involved, the products your company builds or services it provides, etc. In the examples that follow, we will assume that your name is Jill Hacker, and that you are a developer working for Ontopia. The basic ontology therefore consists of the topic types 'developer' and 'company', the association type 'employs/employed by', and the roles 'employee' and 'employer'.

4.2. Step 2: Getting the framework in place

To start with, here is the simplest possible valid topic map in XTM syntax. It is empty, but it does at least declare itself to be a topic map in XTM syntax with a specific character encoding. (If you leave out the encoding attribute, UTF-8 will be assumed.)

The simplest possible topic map

<?xml version="1.0" encoding="ISO-8859-1"?>
<topicMap xmlns="http://www.topicmaps.org/xtm/1.0/"
          xmlns:xlink="http://www.w3.org/1999/xlink">
</topicMap>

To see this topic map in the Omnigator, type it in (no cheating!) using your favourite text editor (e.g., emacs, TextPad, Notepad, etc.), and save it under a name with the extension .xtm, in the appropriate directory. (By default this is ${basedir}/jakarta-tomcat/webapps/navigator/WEB-INF/xml/, where ${basedir} is the Omnigator base directory (see the installation documentation or your technical support team for further information).

Once the topic map file is in the correct place, start the Omnigator, go to the Manage Page, and there you will see your XTM document among the Registry Items. (If the Omnigator was already running you will need to click on "Refresh Sources" first.) Now click on "Load". Assuming no parsing errors occur, the document will be loaded and its name will become a link.

If you get parsing errors, you will need to go back and fix the document. Look for missing quotes, misspelt tag names, wrong use of case, etc. If you get the error message "No topic maps in document", it means you have made a mistake in the namespace declaration, or have a misspelling in the <topicMap> start-tag.

At this point you might want to consider loading the Reload plugin (if it isn't already loaded), as described in section 3.4.5. It will save you time as you go through the rest of these exercises!

Once your topic map has been successfully loaded, click on its name and you will be taken to the Topic Map Page. Not surprisingly, you won't see very much, either in the "Ontology", the "Master Index", or the "Themes" view, but at least you have the topic map in the Omnigator! Now is the time to start adding topics.

4.3. Step 3: Creating the first topic

If you were going about the creation of this topic map in a serious way, you would first create all the typing topics and then create instances of them. However, doing things in the wrong order can sometimes be quite instructive, so that is what we will do! Add a single topic – yourself – to the topic map:

A one-topic topic map

<?xml version="1.0" encoding="UTF-8"?>
<topicMap xmlns="http://www.topicmaps.org/xtm/1.0/"
          xmlns:xlink="http://www.w3.org/1999/xlink">

<topic id="jill">
  <baseName>
    <baseNameString>Jill Hacker</baseNameString>
  </baseName>
</topic>

</topicMap>

Pay careful attention to the case of your tag names (it is "baseName", not "basename"). Save the file, go to the Omnigator, and click on the Reload button. Assuming no errors, the topic map will be reloaded. Click on the name of the topic map to go to the Topic Map Page.

Again nothing in the ontology view. Don't be alarmed: An ontology consists of topics that represent classes or types and you don't have any yet. All you have is an individual (yourself). However, if you now choose "Master Index" from the pull-down list you will notice a difference. (You may have to use the browser's Reload command, normally Ctrl-R, if your browser is doing caching. In fact, you might want to switch caching off while doing these exercises: Every time you modify your topic map you run the risk that the internal IDs will have changed, and this can cause confusion.)

What you should see in the master index view is a single topic, Jill Hacker. If you click on it, you are taken to the Topic Page where you see that this topic has just one characteristic: its name.

4.4. Step 4: Adding a topic type

Now let's give this topic a type by adding an <instanceOf> subelement:

A topic map with an (erroneously) typed topic

<?xml version="1.0" encoding="UTF-8"?>
<topicMap xmlns="http://www.topicmaps.org/xtm/1.0/"
          xmlns:xlink="http://www.w3.org/1999/xlink">

<topic id="jill">
  <instanceOf>
    <topicRef xlink:href="#developer"/>
  </instanceOf>
  <baseName>
    <baseNameString>Jill Hacker</baseNameString>
  </baseName>
</topic>

</topicMap>

This example is incomplete, since it references a topic ('developer') that does not yet exist. But the Omnigator is quite forgiving in situations like this and simply instantiates an unnamed topic, as you will see if you reload your topic map. In the Ontology view you will now see that topic (with the name "[no name]" under the heading "Subject Indexes". If you click on it, you are taken to a Topic Page for this topic type and you will see yourself in the list of "Topics of this Type".

Now let's create a real 'developer' topic, and while we're at it, topics for the company 'Ontopia' and the topic type 'company':

A topic map with two correctly typed topics

<?xml version="1.0" encoding="UTF-8"?>
<topicMap xmlns="http://www.topicmaps.org/xtm/1.0/"
          xmlns:xlink="http://www.w3.org/1999/xlink">

<topic id="jill">
  <instanceOf>
    <topicRef xlink:href="#developer"/>
  </instanceOf>
  <baseName>
    <baseNameString>Jill Hacker</baseNameString>
  </baseName>
</topic>

<topic id="developer">
  <baseName>
    <baseNameString>developer</baseNameString>
  </baseName>
</topic>

<topic id="ontopia">
  <instanceOf>
    <topicRef xlink:href="#company"/>
  </instanceOf>
  <baseName>
    <baseNameString>Ontopia</baseNameString>
  </baseName>
</topic>

<topic id="company">
  <baseName>
    <baseNameString>company</baseNameString>
  </baseName>
</topic>

</topicMap>

When you reload your topic map (Reload button, Back, Ctrl-R) you will see that the ontology now consists of two topics, and that there are four topics in the master index. So far, so good. Now for the next step.

4.5. Step 5: Adding occurrences

Adding occurrences is a simple matter, as the following examples show (look for the <occurrence> elements):

Topics with occurrences

<topic id="ontopia">
  <instanceOf>
    <topicRef xlink:href="#company"/>
  </instanceOf>
  <baseName>
    <baseNameString>Ontopia</baseNameString>
  </baseName>
  <occurrence>
    <instanceOf>
      <topicRef xlink:href="#website"/>
    </instanceOf>
    <resourceRef xlink:href="http://www.ontopia.net/"/>
  </occurrence>
</topic>

<topic id="jill">
  <instanceOf>
    <topicRef xlink:href="#developer"/>
  </instanceOf>
  <baseName>
    <baseNameString>Jill Hacker</baseNameString>
  </baseName>
  <occurrence>
    <instanceOf>
      <topicRef xlink:href="#kudo"/>
    </instanceOf>
    <resourceData>Jill's a cool girl and a great hacker</resourceData>
  </occurrence>
</topic>

<topic id="website">
  <baseName>
    <baseNameString>web site</baseNameString>
  </baseName>
</topic>

<topic id="kudo">
  <baseName>
    <baseNameString>kudo</baseNameString>
  </baseName>
</topic>

The occurrence for Ontopia points to the resource (using a <resourceRef> element with a URL as the address), while the occurrence for you, 'Jill', contains the resource (in the form of a <resourceData> element. (Note that we need to add topics for the occurrence types 'website' and 'kudo' in order to avoid more "[no name]" topics.)

4.6. Step 6: Using Ontopia published subjects

Now let's say that you want to give your kudo occurrences some kind of privileged status, and have them appear in the Key Facts section instead of among the Resources. Ontopia has defined a published subject for the concept of a description occurrence using the following URL: http://psi.ontopia.net/xtm/occurrence-type/description, and it just so happens that the Omnigator displays occurrences of this type in the Key Facts section. All you need do to exploit this is to establish that the subject identity of the kudo topic is this concept of description occurrence, like this:

Using the description occurrence PSI

<topic id="kudo">
  <subjectIdentity>
    <subjectIndicatorRef
      xlink:href="http://psi.ontopia.net/xtm/occurrence-type/description"/>
  </subjectIdentity>
  <baseName>
    <baseNameString>kudo</baseNameString>
  </baseName>
</topic>

If you reload the topic map now, you will see that this occurrence moves to the Key Facts section, under the subheading "Description".

If you want to treat more than one occurrence type (say 'kudo' and 'definition') as description occurrences, you cannot simply give those topics the same identity, because then they will be merged into a single topic. What you need to do is to make both those topics instances of a third topic (called here 'description'), that itself has the subject identity "description occurrence":

Using multiple description occurrence types

<topic id="description">
  <subjectIdentity>
    <subjectIndicatorRef
      xlink:href="http://psi.ontopia.net/xtm/occurrence-type/description"/>
  </subjectIdentity>
  <baseName>
    <baseNameString>description</baseNameString>
  </baseName>
</topic>

<topic id="kudo">
  <instanceOf>
    <topicRef xlink:href="#description"/>
  </instanceOf>
  <baseName>
    <baseNameString>kudo</baseNameString>
  </baseName>
</topic>

<topic id="definition">
  <instanceOf>
    <topicRef xlink:href="#description"/>
  </instanceOf>
  <baseName>
    <baseNameString>definition</baseNameString>
  </baseName>
</topic>

Ontopia has defined two other published subjects that you might want to experiment with: metadata occurrence and default occurrence. (For completeness, we include here a description of the description occurrence as well.)

Metadata occurrence

http://psi.ontopia.net/xtm/occurrence-type/metadata

A class of occurrences (or occurrence types) used to convey metadata about the subject that a topic represents. Metadata occurrences are typically concise units of information represented as internal occurrences via a <resourceData> element (or in ISO 13250 syntax, a data URL). Typical examples are a person's birthdate or date of death, the population of a country, etc. In the Omnigator, metadata occurrences are placed in the Key Facts section, under the heading "Metadata".

Default occurrence

http://psi.ontopia.net/xtm/occurrence-type/default

A class of occurrences (or occurrence types) that are regarded as the primary (or default) information resource relating to a particular subject. Default occurrences are typically external occurrences addressed via a <resourceRef> element (or in ISO 13250 syntax, a non-data URL). Typical examples might be the main article about a subject in an encyclopedia, the definition in a thesaurus, the biography of a person, etc. In the Frames view of the Omnigator, default occurrences are loaded automatically into the resource frame.

Description occurrence

http://psi.ontopia.net/xtm/occurrence-type/description

A class of occurrences (or occurrence types) that are regarded as the basic description of a subject. In the Omnigator, description occurrences are placed in the Key Facts section under the heading "Description".

4.7. Step 7: Adding associations

Having by now become an expert on topics, occurrences, and Ontopia PSIs, it is time to add an association asserting that you work for Ontopia. (You never know your luck!) The association will look like this:

An association element

<association>
  <instanceOf>
    <topicRef xlink:href="#employment"/>
  </instanceOf>
  <member>
    <roleSpec><topicRef xlink:href="#employee"/></roleSpec>
    <topicRef xlink:href="#jill"/>
  </member>
  <member>
    <roleSpec><topicRef xlink:href="#employer"/></roleSpec>
    <topicRef xlink:href="#ontopia"/>
  </member>
</association>

This association element contains references to three topics that we don't yet have in our topic map: 'employer' and 'employee' (the association role types) and 'employment' (the association type). If you insert it as is, without adding these three topics, you will get more "[no name]" topics in the Omnigator. Try it if you like and see.

The three new topics you need to add could look like this:

Association type and association role type topics

<topic id="employment">
  <baseName>
    <baseNameString>employment</baseNameString>
  </baseName>
  <baseName>
    <scope><topicRef xlink:href="#employer"/></scope>
    <baseNameString>employs</baseNameString>
  </baseName>
  <baseName>
    <scope><topicRef xlink:href="#employee"/></scope>
    <baseNameString>employed by</baseNameString>
  </baseName>
</topic>

<topic id="employer">
  <baseName>
    <baseNameString>employer</baseNameString>
  </baseName>
</topic>

<topic id="employee">
  <baseName>
    <baseNameString>employee</baseNameString>
  </baseName>
</topic>

Look carefully at the 'employment' topic that defines the association type. We have given it three base names: one (a noun, "employment") in the unconstrained scope, which serves as the default name used to characterise the relationship type, and two others (the verb forms "employs" and "employed by") in the scope 'employer' and 'employee' respectively.

Is it necessary to do this? No. But the advantage is that it enables an application like the Omnigator to choose the most appropriate label for the association type depending on the context:

When the association type itself is the current topic, the name in the unconstrained scope ("employment") will be chosen.

When associations of this type are being viewed from the vantage point of a topic playing the role 'employer' (e.g., when Ontopia is the current topic), the name in the scope 'employer' ("employs") will be chosen.

When associations of this type are being viewed from the vantage point of a topic playing the role 'employee' (e.g., when the current topic is you), the name in the scope 'employee' ("employed by") will be chosen.

This is a simple but effective use of scope that helps overcome the conflict between the fact that relationships (as expressed by associations in topic maps) have no direction, and the fact that the serialisation syntax used to talk about relationships (natural language) often does have a direction (subject-verb-object in most Western European languages). To test the intuitiveness of this technique, load the complete topic map into the Omnigator and go back and forth between the topics you ('Jill') and 'Ontopia', noting how the label for the relationship changes depending on the role played by the current topic.

4.8. Step 8: Reification

Before letting you loose on your own, there is one final, slightly tricky concept that you should try your hand at. It's called reification. Don't be put off by the name; the basic concept is really quite simple. Reification in general is about turning something into a "thing" ("re" in Latin); it could also be called "thingification".

In topic map land, reification means making something into a topic. Every time we create a topic we are reifying some "real world" subject (you, Ontopia, the concept of developer, or company, etc.), so you've been reifying all through this tutorial without even knowing it. (No wonder you feel exhausted!)

So why do we need a special step to learn about reification? Because you can also reify things in the topic map that are not already topics, e.g., associations, occurrences, or even the topic map itself. How is it done? It's quite simple. There are two steps:

  1. Give the element representing the topic map object you want to reify an ID.

  2. Create a topic whose subject identity has a subject indicator reference to that element.

Piece of cake, right? So let's try it. Start by reifying the topic map. Modify your <topicMap> start-tag by adding an ID, and create a topic that references the topic map element as its subject indicator:

Reifying the topic map

<?xml version="1.0" encoding="UTF-8"?>
<topicMap id="jillstm"
          xmlns="http://www.topicmaps.org/xtm/1.0/"
          xmlns:xlink="http://www.w3.org/1999/xlink">

<!-- other topics and associations omitted for brevity -->

<topic id="jillstm-topic">
  <subjectIdentity>
    <subjectIndicatorRef xlink:href="#jillstm"/>
  </subjectIdentity>
  <baseName>
    <baseNameString>Jill's First TM</baseNameString>
  </baseName>
</topic>

</topicMap>

When you load this topic map into the Omnigator, you will see that the name of the topic that reifies the topic map ("Jill's First TM") is used as the title of the Topic Map Page, and also replaces the Topic Map button. If you were using the Frames view, and had a default occurrence for the 'Jill's First TM' topic, that resource would be automatically loaded into the resource frame. (This facility could be used to provide the equivalent of a preface or introduction for your topic map.)

Now let's reify an association.

Why would you want to do that? Well, you might want to say something more about the relationship asserted by an association, over and above its type and members – and the only way to "say something" about anything in topic map land is by making that thing into a topic. For example, you might have information resources that pertain to your relationship with Ontopia, such as your contract, terms of employment, assessments, or whatever. By reifying the association, you obtain a topic on which to hang these resources as occurrences, like this:

Reifying an association

<topic id="jill-ontopia-topic">
  <subjectIdentity>
    <subjectIndicatorRef xlink:href="#jill-ontopia-association"/>
  </subjectIdentity>
  <instanceOf>
    <topicRef xlink:href="#employment"/>
  </instanceOf>
  <baseName>
    <baseNameString>Jill's position with Ontopia</baseNameString>
  </baseName>
  <occurrence>
    <instanceOf>
      <topicRef xlink:href="#contract"/>
    </instanceOf>
    <resourceRef
      xlink:href="http://www.ontopia.net/internal/employees/contracts/jill.htm"/>
  </occurrence>
</topic>

We haven't shown how to add the ID (jill-ontopia-association) to the association that we created in Step 7; we assume you can add that yourself. (If you can't, you are allowed to cheat by looking at the complete example at the end of this document) We also assume that by now you can create a topic for 'contract'.

You'll see the result when you reload the topic map: The association between you and Ontopia now has a more... link which will take you to the topic that represents the association. That association has its own occurrence (your contract with Ontopia), and the Key Facts section now has a heading for "Main Subject(s)", under which you will see the topics (you and 'Ontopia') that participate in the reified association.

Since a reified association is also a topic, it can have its own characteristics. Yours already has a name and an occurrence. It could also play roles in associations with other topics, and those associations could themselves be reified. This leads to a multilayered topic map that can be browsed at varying levels of detail. A user can start at the topic level, and then "zoom in" on an association or other characteristic that is of particular interest and get a new level of detail.

The Omnigator also supports reification of occurrences, base names, and variant names, but we'll leave it to you to experiment with these.

4.9. Step 9: Over to you

From this point there are many directions in which you could take your topic map. For example, you could extend the ontology to include departments and projects, and the kinds of relationships that exist between them and your existing categories. Or you can add your colleagues, create new associations and occurrences, or provide more names in different scopes to those topics that already exist. Now you know the syntax you could also autogenerate topic maps from existing structured information (e.g., an LDAP database) and merge it with topic maps you have created by hand.

The possibilities are almost unlimited. We hope that this tutorial has been useful in getting you started with your own topic maps. If you decide that this paradigm is the way to go for you and your organisation, feel free to contact Ontopia for more advice, to book our training courses, or license our software. Full details of our offerings are available via the web site at http://www.ontopia.net/. Good luck!

4.10. Jill's First TM

Here is the complete version of the topic map used for the tutorial, including comments. It is available as jill.xtm in the WEB-INF/xml/ directory of the Omnigator distribution, and you can also view it as XML in your browser.

Jill's First TM

<?xml version="1.0" encoding="UTF-8"?>
<topicMap xmlns="http://www.topicmaps.org/xtm/1.0/"
          xmlns:xlink="http://www.w3.org/1999/xlink"
          id="jillstm">

<!-- .................... THE TOPIC MAP TOPIC .................... -->

<topic id="jillstm-topic">
  <!-- Reifies the topic map and gives it a name -->
  <subjectIdentity>
    <subjectIndicatorRef xlink:href="#jillstm"/>
  </subjectIdentity>
  <baseName>
    <baseNameString>Jill's First TM</baseNameString>
  </baseName>
</topic>

<!-- ..................... ASSOCIATION TYPES ..................... -->

<topic id="employment">
  <!-- Illustrates the use of names scoped by roles -->
  <baseName>
    <baseNameString>employment</baseNameString>
  </baseName>
  <baseName>
    <scope><topicRef xlink:href="#employer"/></scope>
    <baseNameString>employs</baseNameString>
  </baseName>
  <baseName>
    <scope><topicRef xlink:href="#employee"/></scope>
    <baseNameString>employed by</baseNameString>
  </baseName>
</topic>

<!-- .................. ASSOCIATION ROLE TYPES.................... -->

<topic id="employer">
  <baseName>
    <baseNameString>employer</baseNameString>
  </baseName>
</topic>

<topic id="employee">
  <baseName>
    <baseNameString>employee</baseNameString>
  </baseName>
</topic>

<!-- ........................ TOPIC TYPES ........................ -->

<topic id="developer">
  <baseName>
    <baseNameString>developer</baseNameString>
  </baseName>
</topic>

<topic id="company">
  <baseName>
    <baseNameString>company</baseNameString>
  </baseName>
</topic>

<!-- ..................... INDIVIDUAL TOPICS ..................... -->

<topic id="ontopia">
  <instanceOf>
    <topicRef xlink:href="#company"/>
  </instanceOf>
  <baseName>
    <baseNameString>Ontopia</baseNameString>
  </baseName>
  <occurrence>
    <instanceOf>
      <topicRef xlink:href="#website"/>
    </instanceOf>
    <resourceRef xlink:href="http://www.ontopia.net/"/>
  </occurrence>
</topic>

<topic id="jill">
  <instanceOf>
    <topicRef xlink:href="#developer"/>
  </instanceOf>
  <baseName>
    <baseNameString>Jill Hacker</baseNameString>
  </baseName>
  <occurrence>
    <instanceOf>
      <topicRef xlink:href="#kudo"/>
    </instanceOf>
    <resourceData>Jill's a cool girl and a great hacker</resourceData>
  </occurrence>
</topic>

<!-- ..................... OCCURRENCE TYPES ...................... -->

<topic id="description">
  <!-- Uses Ontopia's "description occurrence" PSI -->
  <subjectIdentity>
    <subjectIndicatorRef
      xlink:href="http://psi.ontopia.net/xtm/occurrence-type/description"/>
  </subjectIdentity>
  <baseName>
    <baseNameString>description</baseNameString>
  </baseName>
</topic>

<topic id="kudo">
  <!-- An instance of the "description occurrence" class -->
  <instanceOf>
    <topicRef xlink:href="#description"/>
  </instanceOf>
  <baseName>
    <baseNameString>kudo</baseNameString>
  </baseName>
</topic>

<topic id="website">
  <baseName>
    <baseNameString>web site</baseNameString>
  </baseName>
</topic>

<topic id="contract">
  <baseName>
    <baseNameString>contract</baseNameString>
  </baseName>
</topic>

<!-- ........................ ASSOCIATIONS ....................... -->

<association id="jill-ontopia-association">
  <instanceOf>
    <topicRef xlink:href="#employment"/>
  </instanceOf>
  <member>
    <roleSpec><topicRef xlink:href="#employee"/></roleSpec>
    <topicRef xlink:href="#jill"/>
  </member>
  <member>
    <roleSpec><topicRef xlink:href="#employer"/></roleSpec>
    <topicRef xlink:href="#ontopia"/>
  </member>
</association>

<!-- ................... REIFIED ASSOCIATIONS .................... -->

<topic id="jill-ontopia-topic">
  <!-- reifies the Jill/Ontopia association -->
  <subjectIdentity>
    <subjectIndicatorRef xlink:href="#jill-ontopia-association"/>
  </subjectIdentity>
  <instanceOf>
    <topicRef xlink:href="#employment"/>
  </instanceOf>
  <baseName>
    <baseNameString>Jill's position with Ontopia</baseNameString>
  </baseName>
  <occurrence id="jills-contract">
    <instanceOf>
      <topicRef xlink:href="#contract"/>
    </instanceOf>
    <resourceRef
      xlink:href="http://www.ontopia.net/internal/employees/contracts/jill.htm"/>
  </occurrence>
</topic>

<!-- .................... REIFIED OCCURRENCES .................... -->

<topic id="jills-contract-topic">
  <!-- Reifies the occurrence of the reified Jill/Ontopia association -->
  <subjectIdentity>
    <subjectIndicatorRef xlink:href="#jills-contract"/>
  </subjectIdentity>
  <instanceOf>
    <topicRef xlink:href="#contract"/>
  </instanceOf>
  <baseName>
    <baseNameString>Jill's contract with Ontopia</baseNameString>
  </baseName>
  <occurrence>
    <instanceOf>
      <topicRef xlink:href="#contract"/>
    </instanceOf>
    <resourceRef
      xlink:href="http://www.ontopia.net/internal/employees/contracts/jill.htm"/>
  </occurrence>
</topic>

</topicMap>