The TMCL validator is an open source project available under an Apache 2.0 license. The project is hosted on http://code.google.com/p/tmcl-validator/. If you find bugs or have feature requests please file a ticket. The current version is 1.2.

1. Scope

The Topic Maps Constraint Language (TMCL, ISO 19756) is a language defined to specify constraints and schemas for topic maps. The TMCL validator validates a given topic map against schemas compatible to the current draft (2010-05-03, http://www.isotopicmaps.org/tmcl/tmcl.html).

While the TMCL Draft requires a strict validation, the current implementation of the TMCL validator only supports loose validation. See 1.1 for a more detailed description on the validator behavior.

1.1. Validation behavior

Loose validation means that the validator ignores the global validation rule in most of the cases, i.e. constructs for which no constraints exist are considered valid. The behavior with respect to each constraint is described in the following table.

Table 1: Behavior of the TMCL validator
constraint description

tmcl:abstract-constraint

Each specified type for which an instance exist is invalid.

tmcl:subject-identifier-constraint

Topic of the specified type which number of subject identifier are out of bounds, or for which a subject identifier exist who does not match the specified regular expression, are invalid.

tmcl:subject-locator-constraint

Topic of the specified type which number of subject locator are out of bounds, or for which a subject locator exist who does not match the specified regular expression, are invalid.

tmcl:item-identifier-constraint

Constructs of the specified type which number of item identifiers is out of bounds or for which an item identifier exist who does not match the specified regular expression, are invalid.

tmcl:topic-name-constraint

Topics of the specified type are invalid if the number of names of the specified name-type are is out of bounds.

tmcl:variant-name-constraint

Topics of the specified type are invalid if they have names of the specified name-type which number of variants having the specified scope are out of bounds.

tmcl:topic-occurrence-constraint

Topics of the specified type are invalid if the number of occurrences of the specified occurrence-type are is out of bounds.

tmcl:topic-role-constraint

Topic of the specified type are invalid of the number of roles of the specified role-type played in associations of the specified association-type are out of bounds.

tmcl:scope-constraint

Names, occurrences and associations of the specified type are invalid when the number of themes of the specified type are out of bounds.

tmcl:scope-required-constraint

Names, occurrences and associations of the specified type belonging to topics of the specified topic-type are invalid if the number of themes of the specified theme instance are out of bounds.

tmcl:reifier-constraint

Names, occurrences and associations of the specified type are invalid if the number of reifier (0 or 1) of the specified type is out of bounds.

tmcl:topic-reifies-constraint

Topics of the specified type are invalid of the number of construct (0 or 1) which are reified by them is out of bounds.

tmcl:association-role-constraint

Associations of the specified type are invalid of the number of roles of the specified role-type are out of bounds.

tmcl:role-combination-constraint

Associations of the specified type are invalid if any combination of two roles exist for which no appropriate role combination constraint exist.

tmcl:occurrence-datatype-constraint

Occurrences of the specified type are invalid of their datatype is unequal the specified datatype.

tmcl:unique-value-constraint

Names and occurrences of the specified type are invalid if an other name or occurrence of the same type has the same value.

tmcl:regular-expression-constraint

Names and occurrences of the specified type are invalid of their value does not match the specified regular expression.

2. Getting started

You can check out the validator from code.google.com using the following command:

hg clone https://tmcl-validator.googlecode.com/hg/ tmcl-validator

For using the TMCL validator you have to have some dependent libraries within your search path. The following table shows a list of those libraries. You could also use Maven to resolve those dependencies.

Table 2: dependencies of the TMCL validator
library description scope

tmapi 2.0a2

TMAPI interface

compile

slf4j-api 1.5.8

Java logging library

compile

junit 4.7

Java unit test framework

test

TMCL loader

Loader which allows reading CTM file which uses include statements

test

semagia-mio 0.9.5

Semagia IO libraries

test

semagia-mio-xtm 0.9.4

XTM extension of Semagio IO

test

latest ontopia build

Ontopio Topic Map Engine

test

The TMCL loader which is used to running the tests has some addition dependencies:

Table 3: dependencies of the TMCL Loader
library description

tmapi 2.0a2

TMAPI interface

tmapix-io 0.3.0

TMAPI extension for serialisation

tmapi 2.0a2

TMAPI interface

semagia-mio-ctm

CTM extension of Semagio IO

The TMCL loader is only used for running the tests. It simply copies the TMCL Templates (http://www.isotopicmaps.org/tmcl/templates.ctm) into the schema file before the reader is invoked. This is necessary since the used CTM Reader dosn’t supports includes.

3. Functionality

The main functionality is to validate a topic map against a topic map schema.

To use the validator you have to create a new instance of the TMCLValidator class and call the validate() method. You can whether validate a single topic map which also contains the schema information or you can give the schema topic map as an additional parameter. In this case the topic map and the schema will be merged using the mergeIn() method of the used topic map engine. The method returns a map of invalid topic map constructs together with a set of results for each construct. A result consists of the constraint id, i.e the subject identifier of the violated TMCL constraint, and an error message. For each result, you can access the constraint id via getConstraintId() and the error message via getMessage().

4. Example

import java.io.File;
import java.io.IOException;
import java.util.Map;
import java.util.Set;

import org.tmapi.core.Construct;
import org.tmapi.core.FactoryConfigurationException;
import org.tmapi.core.TMAPIException;
import org.tmapi.core.TopicMap;
import org.tmapi.core.TopicMapSystem;
import org.tmapi.core.TopicMapSystemFactory;
import org.tmapix.io.CTMTopicMapReader;

import de.topicmapslab.tmclvalidator.TMCLValidator;
import de.topicmapslab.tmclvalidator.TMCLValidatorException;
import de.topicmapslab.tmclvalidator.ValidationResult;

public class Excample {

        public void validationExample(){

        try {

                // create factor and system

                TopicMapSystemFactory factory = TopicMapSystemFactory.newInstance();
                TopicMapSystem system = factory.newTopicMapSystem();

                // read a CTM topic map and schema

                TopicMap map = system.createTopicMap("test:topicmap.ctm");

                File fmap = new File("topicmap.ctm");

                CTMTopicMapReader reader = new CTMTopicMapReader(map, fmap);
                reader.read();

                // validate

                TMCLValidator validator = new TMCLValidator();
                Map<Construct, Set<ValidationResult>> invalidConstructs = validator.validate(map);

                // plot result

                for(Map.Entry<Construct, Set<ValidationResult>> invalidConstruct:invalidConstructs.entrySet()){

                        System.out.println("Invalid construct " + invalidConstruct.getKey() + ":");

                        for(ValidationResult result:invalidConstruct.getValue()){

                                System.out.println("Constraint " + result.getConstraintId() + " violated:");
                                System.out.println(result.getMessage());

                        }

                }


        } catch (FactoryConfigurationException e) {
                e.printStackTrace();
        } catch (TMAPIException e) {
                e.printStackTrace();
        } catch (IOException e) {
                e.printStackTrace();
        } catch (TMCLValidatorException e) {
                e.printStackTrace();
        }

        }

}
topicmapslab.de