In the software industry, use cases are used to gather information about how a software application interacts with its users. The OASIS Darwin Information Typing Architecture (DITA) is an XML-based technical documentation framework used to map and then publish information on a given topic. In DITA, a single topic represents a unit of information, with related topics associated with one another using a topic map. Similarly, a use case represents a single piece of the larger process, with a use case model representing the entirety. Using DITA structural specialization, which extends existing topic types into new ones while maintaining compatibility with existing tooling, you can extend the basic DITA topic types to support use case gathering.
This article continues from a previous developerWorks article, Create walk-through and acceptance scripts with single-sourced DITA, that described how to re-purpose a simple usage document for use as a quality assurance (QA) document during acceptance testing. Whereas the previous article uses the basic DITA topic types, this article takes the more robust approach of extending the basic topic types into new specialized types while maintaining an emphasis on the benefits of single-sourcing and re-purposing.
Manage use cases
In software development, a use case represents a discrete unit of interaction between a user and the system being described. Many use cases are related to each other in a use case model. Typically, use cases are elaborated on during the requirements phase of a software project. After use cases have been sufficiently elaborated on, they are delivered to the development team, which uses them as a specification for the developed product. These use cases are not just a blueprint. They are also a contract, which is then subsequently delivered to in-house, factory, and user acceptance testers, who verify that the developed software fulfills the original requirements that the use case model provided.
A use case document in itself is static, passed from business analysts to developers and testers. The format of the document itself does not change—although different pieces of information in the document are used during different phases of the software development life cycle (SDLC).
A good use case closes the loop between business requirement gathering, software construction, and acceptance testing. At the best of times, however, these are different phases of the SDLC, and the way a use case is used during each of these phases is bound to be different. In a software project, discovering that a use case does not contain the necessary categories of information to move forward can be at best costly—at worst, disastrous.
When I manage software development projects, much of my time is spent on "content wrangling" that organizes and prepares documentation such as use cases. As I have pointed out elsewhere (see Resources for a link), a more flexible approach is timely.
Define DITA using DTD and XSD
As mentioned, DITA is an XML-based documentation framework that represents
each documented topic separately. For instance, a manual might consist of
a number of topics describing how to perform a variety of tasks. These
topics are then related to one another by an XML document called a
topic map. In addition to the basic topic map and topic, the
DITA framework has been extended to provide an assortment of more
specialized topics that are appropriate for different types of
documentation. The basic specialized topic types are
You can define DITA documents using either a DTD or XSD. Both are provided
as part of the DITA Open Toolkit and are readily available with many XML
editors. I prefer to use the XSD schemas, but the choice of schema
language is up to you. In either case, the schema definition for a DITA
topic type consists of two main pieces: the schema itself (for example,
concept.dtd or reference.xsd), which defines the high-level domain of the
topic type, and the module (for example, concept.mod or referenceMod.xsd),
which defines the elements and attributes that make up the schema. If you
are using XSD schemas, you also modify a group (such as referenceGrp.xsd),
which includes placeholder
xs:group elements for each DITA
element defined. Structural specialization involves creation of the schema
definition, module, and group files.
The general topic type is specialized into the three basic topic types by the creation of a new schema for each, defining all new elements in the topic type and how the new schema relates to the original. You use a class attribute, described in greater detail in the text that follows, to describe this relationship. The process of specialization need not end there, however, as the three basic topic types can in turn be specialized to create new DITA topic types using the same process. In this way, you can use DITA structural specialization to extend DITA into the use case domain.
In Listing 1, taken from the DITA schema for the basic
task type, you can see how the default class strings
taskbody begin with a hyphen (
indicates that this specialization is structural, followed by a
space-delimited list of pairings of topic type and topic element,
separated by a slash (
/). This list defines the new element,
mapping it back to the more general element—for instance, mapping
taskbody back to the more generic
Listing 1. The task.class is extended from topic.class
<!-- Base type: topic.class --> <xs:complexType name="task.class"> ... <xs:attribute ref="class" default="- topic/topic task/task "/> </xs:complexType> <!-- Base type: body.class --> <xs:complexType name="taskbody.class"> ... <xs:attribute ref="class" default="- topic/body task/taskbody "/> </xs:complexType>
DITA Open Toolkit
The DITA Open Toolkit (see Resources) is an open
source project that you can use to generate various output types
(including PDF) from a DITA source. Because you can always map new
elements back to more general elements in structural specialization, any
new topic types created using the basic topic types inherit styles from
these and from those related to the original
Elaborate on use cases using DITA
As in my previous article, the sample application provided here is introduced exclusively for illustrative purposes. It describes requirements for a simple wizard with a home page, main flow ( also called a "sunny day path"), and an alternate flow. The main interaction between the two actors (the application's user and the system) requires that the user type in his or her name and is subsequently able to modify personal details.
As before, the application consists of a single module containing several
pages. A DITA topic map relating
reference topics describes
these pages to the related use cases. The DITA topic map plays the role of
a use case model. Previously I used
task topics; now I will
task topic by using structural specialization to
create a new topic type, which I call a
Constraints and invariants
A typical use case consists of a set of pre- and post-conditions that
describe the state of the software described as the use case is triggered
and upon its completion. In addition, you can define state
invariants, which are like rules that do not change over the
course of the use case—for example, "the last name shown on screen
will always be capitalized." You can model these constraints, conditions,
and invariants independently using DITA specialization, probably by
concept topic type. For simplicity's sake, I
chose to add these details directly to the body of the
task topic that is standardly defined as part of the
DITA architecture contains elements for prerequisite, post-requisite, and
context (which bears similarities to the state invariant defined
previously). These elements are all extended from the section heading
class in the base topic, which allows a single heading element to contain
multiple paragraphs. For the use case topic, you want these elements (or
similar elements that extend them) to allow an unordered list of rules
because this approach is closer to the functionality that you are
attempting to emulate. To accomplish this task, extend the DITA unordered
list element instead of a section header for all three categories.
Listing 2 extends the DITA base unordered list
ul) and list item (
li) elements to create new
elements that inherit from them to represent a collection of preconditions
or constraints. Notice that I chose to map the
class not only to the
ul element in the base topic but also
prereq element in the intermediary task. I am
replacing the task/prerequisite with case/constraints, so I want it to
inherit style from both predecessors. The
has no intermediary predecessor. The result of this specialization is
that, while the
task topic allowed a single prerequisite, the
case topic requires a list of prerequisite constraints.
Listing 2. Constraint classes in caseMod.xsd
<!-- Base type: ul.class --> <xs:complexType name="constraints.class"> <xs:choice maxOccurs="unbounded"> <xs:group ref="constraint"/> </xs:choice> ... <xs:attribute ref="class" default="- topic/ul task/prereq case/constraints "/> </xs:complexType> <!-- Base type: li.class --> <xs:complexType name="constraint.class" mixed="true"> <xs:choice minOccurs="0" maxOccurs="unbounded"> <xs:group ref="listitem.cnt"/> </xs:choice> ... <xs:attribute ref="class" default="- topic/li case/constraint "/> </xs:complexType>
As you can see from the sample files that accompany this article (see Download), a similar approach defines
post-conditions and invariants. In each case, an element from the
task topic schema, which was defined stylistically as a
section heading (
context) is replaced by an unordered list of constraints,
conditions, and invariants. Modelling the use case in this way is more
rigorous but allows the
case topic to inherit from the more
The code in Listing 3 shows how the constraint groups are set up in the schema group file.
Listing 3. Constraint groups in caseGrp.xsd
<xs:group name="constraints"> <xs:sequence> <xs:element ref="constraints"/> </xs:sequence> </xs:group> <xs:group name="constraint"> <xs:sequence> <xs:element ref="constraint"/> </xs:sequence> </xs:group>
Scenarios, steps, and interactions
At the heart of any use case is the interaction between the software's user
and the software itself (often described as the system). A use
case might involve many actors and interactions, and in a broader sense,
these items should be described using DITA
References are typically used to represent real-world objects, so they are
a natural fit for application users, modules, and pages. Again, for the
sake of simplicity, I opt to represent many of these references within the
body of the
case topic, although you might reference these
separately from the topic map you use to represent your use case model and
then tie these references into the individual use case topics.
Unfortunately, doing so goes beyond the scope of this article.
At the core of a DITA task is a series of steps, which can be generalized
back to the ordered list class,
ol.class. This class is close
to the model you are trying to produce, with the exception of one
important limitation: As defined, a
step is not attributed to
an actor. This distinction is important because each step in a use case
scenario must be attributed to an actor. Often, the set of steps that
defines a use case represents a dialogue of sorts between the application
user and the system. Other actors might be involved, but this simple
reduction serves for now. The
step element, however, does
not. Also, the standard DITA
task topic contains only a
provision for a single set of steps, and you would like your use case to
contain not only a main flow but also potentially several alternate flows.
In Listing 4, observe how the class of the step is
extended to create
scenario.class, which is similar to the
predecessor class. The specialized class requires an attribute describing
whether this is a main flow or an alternate flow, defaulting to
main. This multiplicity is handled elsewhere in the schema
casebody element is defined. As the body in a task
allowed only a single set of steps to perform a task, the use case allows
multiple alternate steps to perform the use case.
Listing 4. The scenario.class in caseMod.xsd
<!-- Base type: ol.class --> <xs:complexType name="scenario.class"> <xs:choice>> <xs:group ref="interaction" maxOccurs="unbounded"/> </xs:choice> <xs:attribute name="type" default="main"> <xs:simpleType> <xs:restriction base="xs:string"> <xs:enumeration value="main"/> <xs:enumeration value="alternate"/> </xs:restriction> </xs:simpleType> </xs:attribute> <xs:attribute ref="class" default="- topic/ol task/steps case/scenario "/> </xs:complexType>
In Listing 4, you can also see how the new
scenario element inherits from both
ol. This inheritance allows the new element to perform as its
predecessors when it is encountered by DITA applications such as the DITA
Open Toolkit while still encapsulating new functionality.
Listing 5 shows the class that defines the use case
interaction element, which is again similar to the
step class from which it is specialized, with the exception
that you must attribute this new element to an actor. In this case, I
restricted the set of actors to "system" and "user," but you can add more,
and these actors can reference separate topics (this topic again falls
beyond the scope of this article).
Listing 5. interaction.class in caseMod.xsd
<!-- Base type: li.class --> <xs:complexType name="interaction.class"> <xs:sequence> <xs:group ref="cmd"/> ... </xs:sequence> <xs:attribute name="actor" default="system"> <xs:simpleType> <xs:restriction base="xs:string"> <xs:enumeration value="user"/> <xs:enumeration value="system"/> </xs:restriction> </xs:simpleType> </xs:attribute> <xs:attribute ref="class" default="- topic/li task/step case/interaction "/> </xs:complexType>
Again, you can see how this new element is based on a predecessor in the
task topic and a predecessor in the base DITA topic,
inheriting behavior from both.
Bring it all together
Now that you have extended one of the DITA basic topics, you can quickly
create a new use case using your favorite XML editor and, based on the new
schema, add content to it. When you have done so, you can create a topic
map referencing this and other DITA topics that you can then use as a use
case model and produce a PDF document from it using the DITA Open Toolkit.
You might find that this approach allows you to leverage one of the
collaborative construction environments that are becoming available for
DITA, or you might find that you can leverage the transformative power of
XSL or XQuery to re-purpose your requirements documentation to make it
more useful for different members of your software development team. You
can see a sample
case document in Listing
Listing 6. Use case file created using dita/case.xsd
<case id="UC5" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:noNamespaceSchemaLocation="Schemas\dita\case.xsd"> <title>Use Case 5: Review personal information</title> <casebody> <constraints> <constraint>First and Last Name have been entered</constraint> </constraints> <invariants> <invariant>First Name is capitalized</invariant> <invariant>Last Name is capitalized</invariant> </invariants> <scenario type="main"> <interaction actor="system"> <cmd>displays current First and Last Name</cmd> </interaction> <interaction actor="user"> <cmd>accepts current First and Last Name</cmd> </interaction> </scenario> <scenario type="alternate"> <interaction actor="user"> <cmd>rejects current First Name</cmd> <stepresult>loads edit screen for First Name</stepresult> </interaction> </scenario> <scenario type="alternate"> <interaction actor="user"> <cmd>rejects current Last Name</cmd> <stepresult>loads edit screen for Last Name</stepresult> </interaction> </scenario> <conditions> <condition>returns to home page</condition> </conditions> </casebody> </case>
With the DITA framework, you can document how a software application and its users interact. Likewise, software use cases are used to gather information about how a software application interacts with its users, so it stands to reason that the two technologies should be a natural fit. When you use DITA structural specialization to extend the existing topic types into new ones that support your use case-gathering effort, you can maintain compatibility with and leverage existing tooling. After you extend the basic DITA task topic, you can use this new schema to build use cases; from these use cases, you can build a use case model that is flexible and easy to maintain.
|Sample files for this article||examplecode.zip||21KB|
- Create walk-through and acceptance scripts with single-sourced DITA (Piers Michael Hollott, developerWorks, November 2010): Read the earlier article which describes how to leverage single-source documentation using DITA.
- Specializing topic types in DITA (Michael Priestley, developerWorks, September 2005): Explore the mechanics of DITA specialization as described in greater depth.
- An XML-based information architecture for learning content (John P. Hunt and Robert Bernard, developerWorks, August 2005): Learn about a DITA-based information architecture to develop reusable learning content in this two-part series.
- XSD schema specialization module coding requirements: Learn more about the OASIS design standards for specializing DITA using XSD.
- More DITA-related content (developerWorks, January 2005 - current): Find articles and tutorials about DITA.
- More articles by this author (Piers Michael Hollott, developerWorks, November 2010-current): Read articles about DITA and other technologies.
- XML area on developerWorks: Get the resources you need to advance your skills in the XML arena.
- XML technical library: See the developerWorks XML Zone library for a wide range of technical articles and tips, tutorials, standards, and IBM Redbooks. Also, read more XML tips.
- My developerWorks: Personalize your developerWorks experience.
- developerWorks technical events and webcasts: Stay current with technology in these sessions.
- developerWorks on Twitter: Join today to follow developerWorks tweets.
- developerWorks podcasts: Listen to interesting interviews and discussions for software developers.
- developerWorks on-demand demos: Watch demos ranging from product installation and setup for beginners to advanced functionality for experienced developers.
Get products and technologies
- IBM product evaluation versions: Download and get your hands on application development tools and middleware products from DB2®, Lotus®, Rational®, Tivoli®, and WebSphere®.
- The developerWorks community: Connect with other developerWorks users while exploring the developer-driven blogs, forums, groups, and wikis.