From: <lh...@us...> - 2009-07-02 11:20:44
|
Revision: 300 http://tinytim.svn.sourceforge.net/tinytim/?rev=300&view=rev Author: lheuer Date: 2009-07-02 11:20:22 +0000 (Thu, 02 Jul 2009) Log Message: ----------- - Update to the inofficial TMAPI 2.0 a2 version - Moved TinyTimMapInputHandler into the core - Updated changes, and build.xml to reflect these changes Modified Paths: -------------- tinytim/trunk/CHANGES.txt tinytim/trunk/build.xml Added Paths: ----------- tinytim/trunk/lib/semagia-mio-0.9.4.jar tinytim/trunk/lib/tmapi-2.0a2-tests.jar tinytim/trunk/lib/tmapi-2.0a2.jar tinytim/trunk/src/main/java/org/tinytim/mio/ tinytim/trunk/src/main/java/org/tinytim/mio/TinyTimMapInputHandler.java tinytim/trunk/src/test/java/org/tinytim/mio/ tinytim/trunk/src/test/java/org/tinytim/mio/TestTinyTimMapInputHandler.java Removed Paths: ------------- tinytim/trunk/lib/tmapi-2.0a1-tests.jar tinytim/trunk/lib/tmapi-2.0a1.jar Modified: tinytim/trunk/CHANGES.txt =================================================================== --- tinytim/trunk/CHANGES.txt 2009-07-02 11:07:24 UTC (rev 299) +++ tinytim/trunk/CHANGES.txt 2009-07-02 11:20:22 UTC (rev 300) @@ -2,6 +2,17 @@ Changes Log =========== +2.0.0 a5 (xx.yy.2009) +--------------------- + +Bugfixes: +--------- +* Bug #2812460 -- Port the Check class from Ontopia back to + tinyTiM +* Bug #2809821 -- Ensure same topic map constraint +* + + 2.0.0 a4 (06.12.2008) --------------------- Modified: tinytim/trunk/build.xml =================================================================== --- tinytim/trunk/build.xml 2009-07-02 11:07:24 UTC (rev 299) +++ tinytim/trunk/build.xml 2009-07-02 11:20:22 UTC (rev 300) @@ -12,8 +12,9 @@ <property name="lib.junit" value="${dir.lib}/junit-4.5.jar"/> <property name="lib.trove" value="${dir.lib}/trove-2.0.4.jar"/> - <property name="lib.tmapi" value="${dir.lib}/tmapi-2.0a1.jar"/> - <property name="lib.tmapi.tests" value="${dir.lib}/tmapi-2.0a1-tests.jar"/> + <property name="lib.mio" value="${dir.lib}/semagia-mio-0.9.4.jar"/> + <property name="lib.tmapi" value="${dir.lib}/tmapi-2.0a2.jar"/> + <property name="lib.tmapi.tests" value="${dir.lib}/tmapi-2.0a2-tests.jar"/> <property name="lib.emma" value="${dir.lib}/emma.jar"/> <property name="lib.emma.task" value="${dir.lib}/emma_ant.jar"/> @@ -64,6 +65,7 @@ <pathelement location="${dir.build.classes}" /> <pathelement location="${dir.build.tests}" /> <pathelement location="${lib.junit}"/> + <pathelement location="${lib.mio}"/> <pathelement location="${lib.tmapi}"/> <pathelement location="${lib.tmapi.tests}"/> <pathelement location="${lib.trove}"/> @@ -98,6 +100,7 @@ <classpath> <pathelement location="${dir.build.classes}"/> <pathelement location="${lib.junit}"/> + <pathelement location="${lib.mio}"/> <pathelement location="${lib.tmapi}"/> <pathelement location="${lib.tmapi.tests}"/> <pathelement location="${lib.trove}"/> @@ -128,6 +131,7 @@ <classpath> <pathelement location="${dir.build.classes}"/> <pathelement location="${lib.junit}"/> + <pathelement location="${lib.mio}"/> <pathelement location="${lib.tmapi}"/> <pathelement location="${lib.tmapi.tests}"/> <pathelement location="${lib.trove}"/> @@ -155,6 +159,7 @@ <classpath> <pathelement location="${lib.tmapi}"/> <pathelement location="${lib.trove}"/> + <pathelement location="${lib.mio}"/> </classpath> <src path="${dir.src}"/> </javac> Added: tinytim/trunk/lib/semagia-mio-0.9.4.jar =================================================================== (Binary files differ) Property changes on: tinytim/trunk/lib/semagia-mio-0.9.4.jar ___________________________________________________________________ Added: svn:mime-type + application/octet-stream Deleted: tinytim/trunk/lib/tmapi-2.0a1-tests.jar =================================================================== (Binary files differ) Deleted: tinytim/trunk/lib/tmapi-2.0a1.jar =================================================================== (Binary files differ) Added: tinytim/trunk/lib/tmapi-2.0a2-tests.jar =================================================================== (Binary files differ) Property changes on: tinytim/trunk/lib/tmapi-2.0a2-tests.jar ___________________________________________________________________ Added: svn:mime-type + application/octet-stream Added: tinytim/trunk/lib/tmapi-2.0a2.jar =================================================================== (Binary files differ) Property changes on: tinytim/trunk/lib/tmapi-2.0a2.jar ___________________________________________________________________ Added: svn:mime-type + application/octet-stream Added: tinytim/trunk/src/main/java/org/tinytim/mio/TinyTimMapInputHandler.java =================================================================== --- tinytim/trunk/src/main/java/org/tinytim/mio/TinyTimMapInputHandler.java (rev 0) +++ tinytim/trunk/src/main/java/org/tinytim/mio/TinyTimMapInputHandler.java 2009-07-02 11:20:22 UTC (rev 300) @@ -0,0 +1,530 @@ +/* + * Copyright 2008 Lars Heuer (heuer[at]semagia.com) + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ +package org.tinytim.mio; + +import java.util.List; + +import org.tinytim.core.Scope; +import org.tinytim.core.value.Literal; +import org.tinytim.internal.api.IConstruct; +import org.tinytim.internal.api.IConstructFactory; +import org.tinytim.internal.api.ILiteralAware; +import org.tinytim.internal.api.IName; +import org.tinytim.internal.api.IScope; +import org.tinytim.internal.api.IScoped; +import org.tinytim.internal.api.ITopic; +import org.tinytim.internal.api.ITopicMap; +import org.tinytim.internal.api.IVariant; +import org.tinytim.internal.utils.CollectionFactory; +import org.tinytim.utils.TypeInstanceConverter; +import org.tinytim.voc.TMDM; + +import org.tmapi.core.Association; +import org.tmapi.core.Construct; +import org.tmapi.core.Locator; +import org.tmapi.core.Reifiable; +import org.tmapi.core.Role; +import org.tmapi.core.Scoped; +import org.tmapi.core.Topic; +import org.tmapi.core.TopicMap; +import org.tmapi.core.Typed; + +import com.semagia.mio.IMapHandler; +import com.semagia.mio.IRef; +import com.semagia.mio.MIOException; + +/** + * Implementation of a {@link com.semagia.mio.IMapHandler} for tinyTiM. + * + * @author Lars Heuer (heuer[at]semagia.com) <a href="http://www.semagia.com/">Semagia</a> + * @version $Rev: 267 $ - $Date: 2009-02-24 14:56:47 +0100 (Di, 24 Feb 2009) $ + */ +public final class TinyTimMapInputHandler implements IMapHandler { + + private static final byte + INITIAL = 1, + TOPIC = 2, + ASSOCIATION = 3, + ROLE = 4, + OCCURRENCE = 5, + NAME = 6, + VARIANT = 7, + SCOPE = 8, + THEME = 9, + REIFIER = 10, + PLAYER = 11, + ISA = 12, + TYPE = 13; + + private static final int _CONSTRUCT_SIZE = 6; + private static final int _STATE_SIZE = 10; + private static final int _SCOPE_SIZE = 6; + + private final IConstructFactory _factory; + private final ITopicMap _tm; + private final List<Topic> _scope; + private byte[] _stateStack; + private int _stateSize; + private IConstruct[] _constructStack; + private int _constructSize; + + public TinyTimMapInputHandler(TopicMap topicMap) { + if (topicMap == null) { + throw new IllegalArgumentException("The topic map must not be null"); + } + _tm = (ITopicMap) topicMap; + _factory = _tm.getConstructFactory(); + _scope = CollectionFactory.createList(_SCOPE_SIZE); + } + + /* (non-Javadoc) + * @see com.semagia.mio.IMapHandler#startTopicMap() + */ + public void startTopicMap() throws MIOException { + _constructStack = new IConstruct[_CONSTRUCT_SIZE]; + _stateStack = new byte[_STATE_SIZE]; + _constructSize = 0; + _stateSize = 0; + _enterState(INITIAL, _tm); + } + + /* (non-Javadoc) + * @see com.semagia.mio.IMapHandler#endTopicMap() + */ + public void endTopicMap() throws MIOException { + TypeInstanceConverter.convertAssociationsToTypes(_tm); + _constructStack = null; + _stateStack = null; + _scope.clear(); + } + + /* (non-Javadoc) + * @see com.semagia.mio.IMapHandler#startTopic(com.semagia.mio.IRef) + */ + public void startTopic(IRef identity) throws MIOException { + _enterState(TOPIC, _createTopic(identity)); + } + + /* (non-Javadoc) + * @see com.semagia.mio.IMapHandler#endTopic() + */ + public void endTopic() throws MIOException { + _handleTopic((Topic) _leaveStatePopConstruct(TOPIC)); + } + + /* (non-Javadoc) + * @see com.semagia.mio.IMapHandler#startAssociation() + */ + public void startAssociation() throws MIOException { + _enterState(ASSOCIATION, _factory.createAssociation()); + } + + /* (non-Javadoc) + * @see com.semagia.mio.IMapHandler#endAssociation() + */ + public void endAssociation() throws MIOException { + _leaveStatePopConstruct(ASSOCIATION); + } + + /* (non-Javadoc) + * @see com.semagia.mio.IMapHandler#startRole() + */ + public void startRole() throws MIOException { + assert _state() == ASSOCIATION; + _enterState(ROLE, _factory.createRole((Association) _peekConstruct())); + } + + /* (non-Javadoc) + * @see com.semagia.mio.IMapHandler#endRole() + */ + public void endRole() throws MIOException { + _leaveStatePopConstruct(ROLE); + } + + /* (non-Javadoc) + * @see com.semagia.mio.IMapHandler#startPlayer() + */ + public void startPlayer() throws MIOException { + assert _state() == ROLE; + _enterState(PLAYER); + } + + /* (non-Javadoc) + * @see com.semagia.mio.IMapHandler#endPlayer() + */ + public void endPlayer() throws MIOException { + _leaveState(PLAYER); + assert _state() == ROLE; + } + + /* (non-Javadoc) + * @see com.semagia.mio.IMapHandler#startOccurrence() + */ + public void startOccurrence() throws MIOException { + _enterState(OCCURRENCE, _factory.createOccurrence(_peekTopic())); + } + + /* (non-Javadoc) + * @see com.semagia.mio.IMapHandler#endOccurrence() + */ + public void endOccurrence() throws MIOException { + _leaveStatePopConstruct(OCCURRENCE); + } + + /* (non-Javadoc) + * @see com.semagia.mio.IMapHandler#startName() + */ + public void startName() throws MIOException { + _enterState(NAME, _factory.createName(_peekTopic())); + } + + /* (non-Javadoc) + * @see com.semagia.mio.IMapHandler#endName() + */ + public void endName() throws MIOException { + IName name = (IName) _leaveStatePopConstruct(NAME); + if (name.getType() == null) { + name.setType(_tm.createTopicBySubjectIdentifier(TMDM.TOPIC_NAME)); + } + } + + /* (non-Javadoc) + * @see com.semagia.mio.IMapHandler#startVariant() + */ + public void startVariant() throws MIOException { + assert _state() == NAME; + _enterState(VARIANT, _factory.createVariant((IName) _peekConstruct())); + } + + /* (non-Javadoc) + * @see com.semagia.mio.IMapHandler#endVariant() + */ + public void endVariant() throws MIOException { + IVariant variant = (IVariant) _leaveStatePopConstruct(VARIANT); + IName name = (IName) _peekConstruct(); + IScope scope = variant.getScopeObject(); + if (scope.isUnconstrained() || name.getScopeObject().equals(scope)) { + _reportError("The variant has no scope"); + } + } + + /* (non-Javadoc) + * @see com.semagia.mio.IMapHandler#startType() + */ + public void startType() throws MIOException { + assert _peekConstruct() instanceof Typed; + _enterState(TYPE); + } + + /* (non-Javadoc) + * @see com.semagia.mio.IMapHandler#endType() + */ + public void endType() throws MIOException { + _leaveState(TYPE); + assert _peekConstruct() instanceof Typed; + } + + /* (non-Javadoc) + * @see com.semagia.mio.IMapHandler#startScope() + */ + public void startScope() throws MIOException { + assert _peekConstruct() instanceof Scoped; + _enterState(SCOPE); + } + + /* (non-Javadoc) + * @see com.semagia.mio.IMapHandler#endScope() + */ + public void endScope() throws MIOException { + _leaveState(SCOPE); + ((IScoped) _peekConstruct()).setScopeObject(Scope.create(_scope)); + _scope.clear(); + } + + /* (non-Javadoc) + * @see com.semagia.mio.IMapHandler#startTheme() + */ + public void startTheme() throws MIOException { + assert _state() == SCOPE; + _enterState(THEME); + } + + /* (non-Javadoc) + * @see com.semagia.mio.IMapHandler#endTheme() + */ + public void endTheme() throws MIOException { + _leaveState(THEME); + assert _state() == SCOPE; + } + + /* (non-Javadoc) + * @see com.semagia.mio.IMapHandler#subjectIdentifier(java.lang.String) + */ + public void subjectIdentifier(String subjectIdentifier) throws MIOException { + Locator sid = _tm.createLocator(subjectIdentifier); + ITopic topic = _peekTopic(); + Topic existing = _tm.getTopicBySubjectIdentifier(sid); + if (existing != null && !(existing.equals(topic))) { + _merge(existing, topic); + } + else { + IConstruct tmo = (IConstruct) _tm.getConstructByItemIdentifier(sid); + if (tmo != null && tmo.isTopic() && !tmo.equals(topic)) { + _merge((Topic) tmo, topic); + } + } + topic.addSubjectIdentifier(sid); + } + + /* (non-Javadoc) + * @see com.semagia.mio.IMapHandler#subjectLocator(java.lang.String) + */ + public void subjectLocator(String subjectLocator) throws MIOException { + Locator slo = _tm.createLocator(subjectLocator); + ITopic topic = _peekTopic(); + Topic existing = _tm.getTopicBySubjectLocator(slo); + if (existing != null && !(existing.equals(topic))) { + _merge(existing, topic); + } + topic.addSubjectLocator(slo); + } + + /* (non-Javadoc) + * @see com.semagia.mio.IMapHandler#itemIdentifier(java.lang.String) + */ + public void itemIdentifier(String itemIdentifier) throws MIOException { + Locator iid = _tm.createLocator(itemIdentifier); + IConstruct tmo = _peekConstruct(); + if (_state() == TOPIC) { + IConstruct existing = (IConstruct) _tm.getConstructByItemIdentifier(iid); + if (existing != null && existing.isTopic() && !existing.equals(tmo)) { + _merge((Topic) existing, (ITopic) tmo); + } + else { + Topic topic = _tm.getTopicBySubjectIdentifier(iid); + if (topic != null && !topic.equals(tmo)) { + _merge(topic, (ITopic) tmo); + } + } + } + tmo.addItemIdentifier(iid); + } + + /* (non-Javadoc) + * @see com.semagia.mio.IMapHandler#startIsa() + */ + public void startIsa() throws MIOException { + assert _state() == TOPIC; + _enterState(ISA); + } + + /* (non-Javadoc) + * @see com.semagia.mio.IMapHandler#endIsa() + */ + public void endIsa() throws MIOException { + _leaveState(ISA); + assert _state() == TOPIC; + } + + /* (non-Javadoc) + * @see com.semagia.mio.IMapHandler#startReifier() + */ + public void startReifier() throws MIOException { + assert _peekConstruct() instanceof Reifiable; + _enterState(REIFIER); + } + + /* (non-Javadoc) + * @see com.semagia.mio.IMapHandler#endReifier() + */ + public void endReifier() throws MIOException { + _leaveState(REIFIER); + assert _peekConstruct() instanceof Reifiable; + } + + /* (non-Javadoc) + * @see com.semagia.mio.IMapHandler#topicRef(com.semagia.mio.IRef) + */ + public void topicRef(IRef identity) throws MIOException { + _handleTopic(_createTopic(identity)); + } + + /* (non-Javadoc) + * @see com.semagia.mio.IMapHandler#value(java.lang.String) + */ + public void value(String value) throws MIOException { + assert _state() == NAME; + ((IName) _peekConstruct()).setValue(value); + } + + /* (non-Javadoc) + * @see com.semagia.mio.IMapHandler#value(java.lang.String, java.lang.String) + */ + public void value(String value, String datatype) throws MIOException { + ((ILiteralAware) _peekConstruct()).setLiteral(Literal.create(value, datatype)); + } + + /** + * Enters a state. + * + * @param state The state to push ontop of the state stack. + */ + private void _enterState(byte state) { + if (_stateSize >= _stateStack.length) { + byte[] states = new byte[_stateStack.length*2]; + System.arraycopy(_stateStack, 0, states, 0, _stateStack.length); + _stateStack = states; + } + _stateStack[_stateSize++] = state; + } + + /** + * Enters a state and pushes the Topic Maps construct ontop of the construct + * stack. + * + * @param state The state to enter. + * @param tmo The Topic Maps construct which should be pushed to the stack. + */ + private void _enterState(byte state, Construct tmo) { + _enterState(state); + if (_constructSize >= _constructStack.length) { + IConstruct[] constructs = new IConstruct[_constructStack.length*2]; + System.arraycopy(_constructStack, 0, constructs, 0, _constructStack.length); + _constructStack = constructs; + } + _constructStack[_constructSize++] = (IConstruct) tmo; + } + + /** + * Leaves a state. + * + * @param state The state to leave. + * @throws MIOException If the state is not equals to the current state. + */ + private void _leaveState(byte state) throws MIOException { + if (state != _state()) { + _reportError("Unexpected state: " + _state() + ", expected: " + state); + } + _stateSize--; + } + + /** + * Leaves a state and removed the Topic Maps construct from the top of the + * construct stack. + * + * @param state The state to leave. + * @throws MIOException If the state is not equals to the current state. + */ + private IConstruct _leaveStatePopConstruct(byte state) throws MIOException { + _leaveState(state); + final IConstruct construct = _peekConstruct(); + _constructSize--; + _constructStack[_constructSize] = null; + return construct; + } + + /** + * Returns the Topic Maps construct on top of the stack. + * + * @return The Topic Maps construct. + */ + private IConstruct _peekConstruct() { + return _constructStack[_constructSize-1]; + } + + /** + * Returns the topic on top of the stack. + * + * @return The topic. + */ + private ITopic _peekTopic() { + return (ITopic) _peekConstruct(); + } + + /** + * Returns the current state. + * + * @return The current state. + */ + private byte _state() { + return _stateStack[_stateSize-1]; + } + + /** + * Handles the topic dependent on the current state. + * + * @param topic The topic to handle. + */ + private void _handleTopic(Topic topic) { + switch (_state()) { + case ISA: _peekTopic().addType(topic); break; + case TYPE: ((Typed) _peekConstruct()).setType(topic); break; + case PLAYER: ((Role) _peekConstruct()).setPlayer(topic); break; + case THEME: _scope.add(topic); break; + case REIFIER: ((Reifiable) _peekConstruct()).setReifier(topic); break; + } + } + + /** + * Merges the <tt>source</tt> topic with the <tt>target</tt>. + * + * Further, this method ensures that the construct stack stays valid: If + * the <tt>source</tt> is part of the stack, it is replaced with + * <tt>target</tt>. + * + * @param source The source topic (will be removed). + * @param target The target topic. + */ + private void _merge(Topic source, ITopic target) { + for (int i=0; i <_constructSize; i++) { + if (_constructStack[i].equals(source)) { + _constructStack[i] = target; + } + } + target.mergeIn(source); + } + + /** + * Returns either an existing topic with the specified identity or creates + * a topic with the given identity. + * + * @param ref The identity of the topic. + * @return A topic instance. + * @throws MIOException + */ + private ITopic _createTopic(IRef ref) throws MIOException { + Locator loc = _tm.createLocator(ref.getIRI()); + switch (ref.getType()) { + case IRef.ITEM_IDENTIFIER: return (ITopic) _tm.createTopicByItemIdentifier(loc); + case IRef.SUBJECT_IDENTIFIER: return (ITopic) _tm.createTopicBySubjectIdentifier(loc); + case IRef.SUBJECT_LOCATOR: return (ITopic) _tm.createTopicBySubjectLocator(loc); + default: _reportError("Unknown reference type " + ref.getType()); + } + // Never returned, an exception was thrown + return null; + } + + /** + * Reports an error. + * + * @param msg The error message. + * @throws MIOException Thrown in any case. + */ + private static void _reportError(String msg) throws MIOException { + throw new MIOException(msg); + } + +} Added: tinytim/trunk/src/test/java/org/tinytim/mio/TestTinyTimMapInputHandler.java =================================================================== --- tinytim/trunk/src/test/java/org/tinytim/mio/TestTinyTimMapInputHandler.java (rev 0) +++ tinytim/trunk/src/test/java/org/tinytim/mio/TestTinyTimMapInputHandler.java 2009-07-02 11:20:22 UTC (rev 300) @@ -0,0 +1,368 @@ +/* + * Copyright 2008 Lars Heuer (heuer[at]semagia.com) + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ +package org.tinytim.mio; + +import org.tinytim.core.TinyTimTestCase; +import org.tinytim.voc.TMDM; +import org.tinytim.voc.XSD; +import org.tmapi.core.Locator; +import org.tmapi.core.Name; +import org.tmapi.core.Occurrence; +import org.tmapi.core.Topic; + +import com.semagia.mio.IRef; +import com.semagia.mio.MIOException; +import com.semagia.mio.helpers.Ref; + +/** + * Tests against the {@link org.tinytim.mio.TinyTimMapInputHandler}. + * + * @author Lars Heuer (heuer[at]semagia.com) <a href="http://www.semagia.com/">Semagia</a> + * @version $Rev: 209 $ - $Date: 2008-11-19 14:45:23 +0100 (Mi, 19 Nov 2008) $ + */ +public class TestTinyTimMapInputHandler extends TinyTimTestCase { + + private static final String _XSD_STRING = XSD.STRING.getReference(); + private static final String _XSD_ANY_URI = XSD.ANY_URI.getReference(); + + private TinyTimMapInputHandler _handler; + + /* (non-Javadoc) + * @see junit.framework.TestCase#setUp() + */ + @Override + protected void setUp() throws Exception { + super.setUp(); + _handler = new TinyTimMapInputHandler(_tm); + } + + public void testMappaIssue23() throws Exception { + // http://code.google.com/p/mappa/issues/detail?id=23 + String iid = "http://mappa.semagia.com/issue-23"; + String iid2 = "http://mappa.semagia.com/issue-23_"; + final IRef TOPIC_NAME = Ref.createSubjectIdentifier(TMDM.TOPIC_NAME.getReference()); + TinyTimMapInputHandler handler = this._handler; + handler.startTopicMap(); + handler.startTopic(Ref.createItemIdentifier(iid)); + handler.startName(); + handler.value("test"); + handler.startType(); + handler.topicRef(TOPIC_NAME); + handler.endType(); + handler.endName(); + handler.endTopic(); + handler.startTopic(Ref.createItemIdentifier(iid2)); + handler.startName(); + handler.value("a test"); + handler.startType(); + handler.topicRef(TOPIC_NAME); + handler.endType(); + handler.endName(); + handler.subjectIdentifier(TOPIC_NAME.getIRI()); + handler.endTopic(); + handler.endTopicMap(); + } + + /** + * Simple startTopicMap, followed by an endTopicMap event. + */ + public void testEmpty() throws Exception { + assertEquals(0, _tm.getTopics().size()); + assertEquals(0, _tm.getAssociations().size()); + _handler.startTopicMap(); + _handler.endTopicMap(); + assertEquals(0, _tm.getTopics().size()); + assertEquals(0, _tm.getAssociations().size()); + } + + /** + * Tests reifying a topic map. + */ + public void testTMReifier() throws Exception { + String itemIdent = "http://sf.net/projects/tinytim/test#1"; + assertEquals(0, _tm.getTopics().size()); + assertEquals(0, _tm.getAssociations().size()); + _handler.startTopicMap(); + _handler.startReifier(); + _handler.startTopic(Ref.createItemIdentifier(itemIdent)); + _handler.endTopic(); + _handler.endReifier(); + _handler.endTopicMap(); + assertEquals(1, _tm.getTopics().size()); + assertEquals(0, _tm.getAssociations().size()); + Topic topic = (Topic) _tm.getConstructByItemIdentifier(_tm.createLocator(itemIdent)); + assertNotNull(topic); + assertNotNull(_tm.getReifier()); + assertEquals(topic, _tm.getReifier()); + } + + /** + * Tests topic creation with an item identifier. + */ + public void testTopicIdentityItemIdentifier() throws Exception { + String itemIdent = "http://sf.net/projects/tinytim/test#1"; + _handler.startTopicMap(); + _handler.startTopic(Ref.createItemIdentifier(itemIdent)); + _handler.endTopic(); + _handler.endTopicMap(); + assertEquals(1, _tm.getTopics().size()); + Topic topic = (Topic) _tm.getConstructByItemIdentifier(_tm.createLocator(itemIdent)); + assertNotNull(topic); + } + + /** + * Tests topic creation with a subject identifier. + */ + public void testTopicIdentitySubjectIdentifier() throws Exception { + String subjIdent = "http://sf.net/projects/tinytim/test#1"; + _handler.startTopicMap(); + _handler.startTopic(Ref.createSubjectIdentifier(subjIdent)); + _handler.endTopic(); + _handler.endTopicMap(); + assertEquals(1, _tm.getTopics().size()); + Topic topic = _tm.getTopicBySubjectIdentifier(_tm.createLocator(subjIdent)); + assertNotNull(topic); + } + + /** + * Tests topic creation with a subject locator. + */ + public void testTopicIdentitySubjectLocator() throws Exception { + String subjLoc = "http://sf.net/projects/tinytim/test#1"; + _handler.startTopicMap(); + _handler.startTopic(Ref.createSubjectLocator(subjLoc)); + _handler.endTopic(); + _handler.endTopicMap(); + assertEquals(1, _tm.getTopics().size()); + Topic topic = _tm.getTopicBySubjectLocator(_tm.createLocator(subjLoc)); + assertNotNull(topic); + } + + /** + * Tests transparent merging. + */ + public void testTopicMerging() throws Exception { + String ref = "http://sf.net/projects/tinytim/test#1"; + String itemIdent = "http://example.org/1"; + _handler.startTopicMap(); + _handler.startTopic(Ref.createSubjectIdentifier(ref)); + // Topic in topic event + _handler.startTopic(Ref.createItemIdentifier(itemIdent)); + _handler.itemIdentifier(ref); + _handler.endTopic(); + _handler.startOccurrence(); + _handler.value("tinyTiM", _XSD_STRING); + _handler.endOccurrence(); + _handler.endTopic(); + _handler.endTopicMap(); + assertEquals(1, _tm.getTopics().size()); + Topic topic = _tm.getTopicBySubjectIdentifier(_tm.createLocator(ref)); + assertNotNull(topic); + assertEquals(topic, _tm.getConstructByItemIdentifier(_tm.createLocator(ref))); + assertEquals(topic, _tm.getConstructByItemIdentifier(_tm.createLocator(itemIdent))); + assertEquals(1, topic.getOccurrences().size()); + Occurrence occ = (Occurrence) topic.getOccurrences().iterator().next(); + assertEquals("tinyTiM", occ.getValue()); + } + + /** + * Tests assigning identities to a topic. + */ + public void testTopicIdentities1() throws Exception { + String ref = "http://sf.net/projects/tinytim/test#1"; + _handler.startTopicMap(); + _handler.startTopic(Ref.createSubjectIdentifier(ref)); + _handler.itemIdentifier(ref); + _handler.endTopic(); + _handler.endTopicMap(); + assertEquals(1, _tm.getTopics().size()); + Locator loc = _tm.createLocator(ref); + Topic topic = _tm.getTopicBySubjectIdentifier(loc); + assertNotNull(topic); + assertEquals(topic, _tm.getConstructByItemIdentifier(loc)); + } + + /** + * Tests assigning identities to a topic. + */ + public void testTopicIdentities2() throws Exception { + String ref = "http://sf.net/projects/tinytim/test#1"; + _handler.startTopicMap(); + _handler.startTopic(Ref.createItemIdentifier(ref)); + _handler.subjectIdentifier(ref); + _handler.endTopic(); + _handler.endTopicMap(); + assertEquals(1, _tm.getTopics().size()); + Locator loc = _tm.createLocator(ref); + Topic topic = _tm.getTopicBySubjectIdentifier(loc); + assertNotNull(topic); + assertEquals(topic, _tm.getConstructByItemIdentifier(loc)); + } + + /** + * Tests reifying the topic map. + */ + public void testTopicMapReifier() throws Exception { + String ref = "http://sf.net/projects/tinytim/test#1"; + _handler.startTopicMap(); + _handler.startReifier(); + _handler.startTopic(Ref.createSubjectIdentifier(ref)); + _handler.endTopic(); + _handler.endReifier(); + _handler.endTopicMap(); + assertNotNull(_tm.getReifier()); + Topic topic = _tm.getTopicBySubjectIdentifier(_tm.createLocator(ref)); + assertNotNull(topic); + assertEquals(topic, _tm.getReifier()); + } + + /** + * Tests occurrence creation with a value of datatype xsd:string. + */ + public void testOccurrenceValueString() throws Exception { + String ref = "http://sf.net/projects/tinytim/test#1"; + String val = "tinyTiM"; + _handler.startTopicMap(); + _handler.startTopic(Ref.createSubjectIdentifier(ref)); + _handler.startOccurrence(); + _handler.value(val, _XSD_STRING); + _handler.endOccurrence(); + _handler.endTopic(); + _handler.endTopicMap(); + Topic topic = _tm.getTopicBySubjectIdentifier(_tm.createLocator(ref)); + assertNotNull(topic); + Occurrence occ = (Occurrence) topic.getOccurrences().iterator().next(); + assertEquals(val, occ.getValue()); + assertEquals(XSD.STRING, occ.getDatatype()); + } + + /** + * Tests occurrence creation with a value of datatype xsd:anyURI. + */ + public void testOccurrenceValueURI() throws Exception { + String ref = "http://sf.net/projects/tinytim/test#1"; + String val = "http://sf.net/projects/tinytim"; + _handler.startTopicMap(); + _handler.startTopic(Ref.createSubjectIdentifier(ref)); + _handler.startOccurrence(); + _handler.value(val, _XSD_ANY_URI); + _handler.endOccurrence(); + _handler.endTopic(); + _handler.endTopicMap(); + Topic topic = _tm.getTopicBySubjectIdentifier(_tm.createLocator(ref)); + assertNotNull(topic); + Occurrence occ = (Occurrence) topic.getOccurrences().iterator().next(); + assertEquals(val, occ.getValue()); + assertEquals(XSD.ANY_URI, occ.getDatatype()); + } + + /** + * Tests if the name type is automatically set. + */ + public void testDefaultNameType() throws Exception { + String ref = "http://sf.net/projects/tinytim/test#1"; + String val = "tinyTiM"; + _handler.startTopicMap(); + _handler.startTopic(Ref.createSubjectIdentifier(ref)); + _handler.startName(); + _handler.value(val); + _handler.endName(); + _handler.endTopic(); + _handler.endTopicMap(); + Topic topic = _tm.getTopicBySubjectIdentifier(_tm.createLocator(ref)); + assertNotNull(topic); + Name name = topic.getNames().iterator().next(); + assertEquals(val, name.getValue()); + assertNotNull(name.getType()); + assertTrue(name.getType().getSubjectIdentifiers().contains(TMDM.TOPIC_NAME)); + } + + /** + * Tests if a variant with no scope is reported as error. + */ + public void testVariantNoScopeError() throws Exception { + String ref = "http://sf.net/projects/tinytim/test#1"; + String val = "tinyTiM"; + _handler.startTopicMap(); + _handler.startTopic(Ref.createSubjectIdentifier(ref)); + _handler.startName(); + _handler.value(val); + _handler.startVariant(); + _handler.value(val, _XSD_STRING); + try { + _handler.endVariant(); + fail("A variant with no scope shouldn't be allowed"); + } + catch (MIOException ex) { + // noop. + } + } + + /** + * Tests if a variant with a scope equals to the parent's scope is rejected. + */ + public void testVariantNoScopeError2() throws Exception { + String ref = "http://sf.net/projects/tinytim/test#1"; + String theme = "http://sf.net/projects/tinytim/test#theme"; + String val = "tinyTiM"; + _handler.startTopicMap(); + _handler.startTopic(Ref.createSubjectIdentifier(ref)); + _handler.startName(); + _handler.startScope(); + _handler.startTheme(); + _handler.topicRef(Ref.createItemIdentifier(theme)); + _handler.endTheme(); + _handler.endScope(); + _handler.value(val); + + _handler.startVariant(); + _handler.value(val, _XSD_STRING); + _handler.startScope(); + _handler.startTheme(); + _handler.topicRef(Ref.createItemIdentifier(theme)); + _handler.endTheme(); + _handler.endScope(); + try { + _handler.endVariant(); + fail("A variant with a scope equals to the parent's scope shouldn't be allowed"); + } + catch (MIOException ex) { + // noop. + } + } + + /** + * Tests nested startTopic/endTopic events. + */ + public void testNestedTopics() throws Exception { + String base = "http://tinytim.sourceforge.net/test-nesting#"; + final int MAX = 10000; + String[] iids = new String[MAX]; + _handler.startTopicMap(); + for (int i=0; i<MAX; i++) { + iids[i] = base + i; + _handler.startTopic(Ref.createItemIdentifier(iids[i])); + } + for (int i=0; i<MAX; i++) { + _handler.endTopic(); + } + _handler.endTopicMap(); + for (String iid: iids) { + assertNotNull(_tm.getConstructByItemIdentifier(createLocator(iid))); + } + } + +} This was sent by the SourceForge.net collaborative development platform, the world's largest Open Source development site. |