Return-Path: Delivered-To: apmail-labs-commits-archive@locus.apache.org Received: (qmail 25563 invoked from network); 31 Aug 2007 21:48:37 -0000 Received: from hermes.apache.org (HELO mail.apache.org) (140.211.11.2) by minotaur.apache.org with SMTP; 31 Aug 2007 21:48:37 -0000 Received: (qmail 71139 invoked by uid 500); 31 Aug 2007 21:48:32 -0000 Delivered-To: apmail-labs-commits-archive@labs.apache.org Received: (qmail 71023 invoked by uid 500); 31 Aug 2007 21:48:31 -0000 Mailing-List: contact commits-help@labs.apache.org; run by ezmlm Precedence: bulk List-Help: List-Unsubscribe: List-Post: List-Id: Reply-To: labs@labs.apache.org Delivered-To: mailing list commits@labs.apache.org Received: (qmail 70071 invoked by uid 99); 31 Aug 2007 21:48:29 -0000 Received: from nike.apache.org (HELO nike.apache.org) (192.87.106.230) by apache.org (qpsmtpd/0.29) with ESMTP; Fri, 31 Aug 2007 14:48:28 -0700 X-ASF-Spam-Status: No, hits=-100.0 required=10.0 tests=ALL_TRUSTED X-Spam-Check-By: apache.org Received: from [140.211.11.3] (HELO eris.apache.org) (140.211.11.3) by apache.org (qpsmtpd/0.29) with ESMTP; Fri, 31 Aug 2007 21:49:34 +0000 Received: by eris.apache.org (Postfix, from userid 65534) id A10961A9832; Fri, 31 Aug 2007 14:48:08 -0700 (PDT) Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit Subject: svn commit: r571610 - in /labs/vysper/src: main/java/org/apache/vysper/xmpp/delivery/ main/java/org/apache/vysper/xmpp/stanza/ main/java/org/apache/vysper/xmpp/xmlfragment/ test/java/org/apache/vysper/xmpp/xmlfragment/ Date: Fri, 31 Aug 2007 21:48:07 -0000 To: commits@labs.apache.org From: berndf@apache.org X-Mailer: svnmailer-1.0.8 Message-Id: <20070831214808.A10961A9832@eris.apache.org> X-Virus-Checked: Checked by ClamAV on apache.org Author: berndf Date: Fri Aug 31 14:48:07 2007 New Revision: 571610 URL: http://svn.apache.org/viewvc?rev=571610&view=rev Log: [vysper] message stanza and xml processing Added: labs/vysper/src/main/java/org/apache/vysper/xmpp/stanza/MessageStanzaType.java - copied, changed from r542950, labs/vysper/src/main/java/org/apache/vysper/xmpp/stanza/IQStanzaType.java labs/vysper/src/main/java/org/apache/vysper/xmpp/xmlfragment/XMLSemanticError.java labs/vysper/src/test/java/org/apache/vysper/xmpp/xmlfragment/ labs/vysper/src/test/java/org/apache/vysper/xmpp/xmlfragment/XMLElementTestCase.java Removed: labs/vysper/src/main/java/org/apache/vysper/xmpp/delivery/StanzaRelayImpl.java Modified: labs/vysper/src/main/java/org/apache/vysper/xmpp/stanza/MessageStanza.java labs/vysper/src/main/java/org/apache/vysper/xmpp/stanza/XMPPCoreStanza.java labs/vysper/src/main/java/org/apache/vysper/xmpp/xmlfragment/XMLElement.java Modified: labs/vysper/src/main/java/org/apache/vysper/xmpp/stanza/MessageStanza.java URL: http://svn.apache.org/viewvc/labs/vysper/src/main/java/org/apache/vysper/xmpp/stanza/MessageStanza.java?rev=571610&r1=571609&r2=571610&view=diff ============================================================================== --- labs/vysper/src/main/java/org/apache/vysper/xmpp/stanza/MessageStanza.java (original) +++ labs/vysper/src/main/java/org/apache/vysper/xmpp/stanza/MessageStanza.java Fri Aug 31 14:48:07 2007 @@ -17,6 +17,11 @@ package org.apache.vysper.xmpp.stanza; +import org.apache.vysper.xmpp.xmlfragment.XMLElement; +import org.apache.vysper.xmpp.xmlfragment.XMLSemanticError; + +import java.util.Map; + /** * message stanza (push) */ @@ -36,4 +41,64 @@ public String getName() { return NAME; } + + public MessageStanzaType getIQType() { + String type = getType(); + if (type == null) return null; + return MessageStanzaType.valueOfWithDefault(type); + } + + /** + * + * @param lang + * @return + * @throws XMLSemanticError - if language attribtues are not unqiue RFC3921.2.1.2.1 + */ + public String getSubject(String lang) throws XMLSemanticError { + XMLElement element = getSubjects().get(lang); + if (element == null) return null; + return element.getSingleInnerText().getText(); + } + + /** + * @return all subject elements, keyed by their lang attribute + * @throws XMLSemanticError + */ + public Map getSubjects() throws XMLSemanticError { + return getInnerElementsByXMLLangNamed("subject"); + } + + /** + * + * @param lang + * @return + * @throws XMLSemanticError - if langauge attributes are not unique, RFC3921.2.1.2.2 + */ + public String getBody(String lang) throws XMLSemanticError { + XMLElement element = getBodies().get(lang); + if (element == null) return null; + return element.getSingleInnerText().getText(); + } + + /** + * @return all body elements, keyed by their lang attribute + * @throws XMLSemanticError + */ + public Map getBodies() throws XMLSemanticError { + return getInnerElementsByXMLLangNamed("body"); + } + + /** + * + * @return thread identifier, or NULL, if not given + * @throws XMLSemanticError - if thread element is not unique, or no unqiue inner text + * is given, RFC3921 2.1.2.3 + */ + public String getThread() throws XMLSemanticError { + XMLElement element = getSingleInnerElementsNamed("thread"); + if (element == null) return null; // thread is optional, see RFC3921.2.1.2.3 + return element.getSingleInnerText().getText(); + } + + } Copied: labs/vysper/src/main/java/org/apache/vysper/xmpp/stanza/MessageStanzaType.java (from r542950, labs/vysper/src/main/java/org/apache/vysper/xmpp/stanza/IQStanzaType.java) URL: http://svn.apache.org/viewvc/labs/vysper/src/main/java/org/apache/vysper/xmpp/stanza/MessageStanzaType.java?p2=labs/vysper/src/main/java/org/apache/vysper/xmpp/stanza/MessageStanzaType.java&p1=labs/vysper/src/main/java/org/apache/vysper/xmpp/stanza/IQStanzaType.java&r1=542950&r2=571610&rev=571610&view=diff ============================================================================== --- labs/vysper/src/main/java/org/apache/vysper/xmpp/stanza/IQStanzaType.java (original) +++ labs/vysper/src/main/java/org/apache/vysper/xmpp/stanza/MessageStanzaType.java Fri Aug 31 14:48:07 2007 @@ -19,25 +19,29 @@ /** */ -public enum IQStanzaType { +public enum MessageStanzaType { - GET ("get"), - SET ("set"), - RESULT ("result"), - ERROR ("error"); + CHAT ("chat"), + ERROR ("error"), + GROUPCHAT ("groupchat"), + HEADLINE ("headline"), + NORMAL ("normal"); private final String value; - public static IQStanzaType valueOfOrNull(String value) { + /** + * RFC3921.2.1.1: type is NORMAL per default, if no (valid) value is + * given + */ + public static MessageStanzaType valueOfWithDefault(String value) { try { - return valueOf(value.toUpperCase()); + return MessageStanzaType.valueOf(value.toUpperCase()); } catch (IllegalArgumentException e) { - return null; + return NORMAL; } } - - IQStanzaType(String value) { + MessageStanzaType(String value) { this.value = value; } @@ -45,4 +49,4 @@ return value; } -} +} \ No newline at end of file Modified: labs/vysper/src/main/java/org/apache/vysper/xmpp/stanza/XMPPCoreStanza.java URL: http://svn.apache.org/viewvc/labs/vysper/src/main/java/org/apache/vysper/xmpp/stanza/XMPPCoreStanza.java?rev=571610&r1=571609&r2=571610&view=diff ============================================================================== --- labs/vysper/src/main/java/org/apache/vysper/xmpp/stanza/XMPPCoreStanza.java (original) +++ labs/vysper/src/main/java/org/apache/vysper/xmpp/stanza/XMPPCoreStanza.java Fri Aug 31 14:48:07 2007 @@ -66,10 +66,6 @@ return getEntity("from"); } - public String getXMLLang() { - return getVerifier().attributePresent("xml:lang") ? getAttribute("xml:lang").getValue() : null; - } - public String getType() { return getVerifier().attributePresent("type") ? getAttribute("type").getValue() : null; } Modified: labs/vysper/src/main/java/org/apache/vysper/xmpp/xmlfragment/XMLElement.java URL: http://svn.apache.org/viewvc/labs/vysper/src/main/java/org/apache/vysper/xmpp/xmlfragment/XMLElement.java?rev=571610&r1=571609&r2=571610&view=diff ============================================================================== --- labs/vysper/src/main/java/org/apache/vysper/xmpp/xmlfragment/XMLElement.java (original) +++ labs/vysper/src/main/java/org/apache/vysper/xmpp/xmlfragment/XMLElement.java Fri Aug 31 14:48:07 2007 @@ -17,8 +17,12 @@ package org.apache.vysper.xmpp.xmlfragment; +import java.util.ArrayList; import java.util.Collections; +import java.util.HashMap; +import java.util.Iterator; import java.util.List; +import java.util.Map; /** * an immutable xml element specialized for XMPP. @@ -71,6 +75,10 @@ return null; } + public String getXMLLang() { + return getVerifier().attributePresent("xml:lang") ? getAttribute("xml:lang").getValue() : null; + } + public List getInnerFragments() { return innerFragments; } @@ -81,6 +89,85 @@ if (xmlFragment instanceof XMLElement) return (XMLElement)xmlFragment; } return null; + } + + public List getInnerElements() { + List innerElements = new ArrayList(); + if (innerFragments == null || innerFragments.size() < 1) return null; + for (XMLFragment xmlFragment : innerFragments) { + if (xmlFragment instanceof XMLElement) innerElements.add((XMLElement) xmlFragment); + } + return innerElements; + } + + public List getInnerTexts() { + List innerTexts = new ArrayList(); + if (innerFragments == null || innerFragments.size() < 1) return null; + for (XMLFragment xmlFragment : innerFragments) { + if (xmlFragment instanceof XMLText) innerTexts.add((XMLText) xmlFragment); + } + return innerTexts; + } + + public XMLText getFirstInnerText() { + if (innerFragments == null || innerFragments.size() < 1) return null; + for (XMLFragment xmlFragment : innerFragments) { + if (xmlFragment instanceof XMLText) return (XMLText) xmlFragment; + } + return null; + } + + public XMLText getSingleInnerText() throws XMLSemanticError { + List innerTexts = getInnerTexts(); + if (innerTexts.isEmpty()) return null; + if (innerTexts.size() > 1) throw new XMLSemanticError("element has more than one inner text fragment"); + return innerTexts.get(0); + } + + /** + * collects all inner elements named as given parameter + * @param name - must not be NULL + */ + public List getInnerElementsNamed(String name) { + if (name == null) return null; + List innerElements = getInnerElements(); + Iterator elementIterator = innerElements.iterator(); // this List will be modified now! + while (elementIterator.hasNext()) { + XMLElement xmlElement = elementIterator.next(); + if (!name.equals(xmlElement.getName())) elementIterator.remove(); + } + return innerElements; + } + + public XMLElement getSingleInnerElementsNamed(String name) throws XMLSemanticError { + List innerElements = getInnerElementsNamed(name); + if (innerElements.isEmpty()) return null; + if (innerElements.size() > 1) throw new XMLSemanticError("element has more than one inner element named: " + name); + return innerElements.get(0); + } + + /** + * collects all inner elements with given name and puts them in a map indexed by + * @param name + * @return Map + * @exception no language attribute may occur more than once for the same element + */ + public Map getInnerElementsByXMLLangNamed(String name) throws XMLSemanticError { + if (name == null) return null; + + List innerElements = getInnerElementsNamed(name); + Map langMap = new HashMap(); + + Iterator elementIterator = innerElements.iterator(); // this List will be modified now! + while (elementIterator.hasNext()) { + XMLElement xmlElement = elementIterator.next(); + String xmlLang = xmlElement.getXMLLang(); + if (langMap.containsKey(xmlLang)) { + throw new XMLSemanticError("two inner elements '" + name + "' with same language attribute " + xmlLang); + } + langMap.put(xmlLang, xmlElement); + } + return langMap; } public boolean equals(Object o) { Added: labs/vysper/src/main/java/org/apache/vysper/xmpp/xmlfragment/XMLSemanticError.java URL: http://svn.apache.org/viewvc/labs/vysper/src/main/java/org/apache/vysper/xmpp/xmlfragment/XMLSemanticError.java?rev=571610&view=auto ============================================================================== --- labs/vysper/src/main/java/org/apache/vysper/xmpp/xmlfragment/XMLSemanticError.java (added) +++ labs/vysper/src/main/java/org/apache/vysper/xmpp/xmlfragment/XMLSemanticError.java Fri Aug 31 14:48:07 2007 @@ -0,0 +1,39 @@ +/*********************************************************************** + * Copyright (c) 2006-2007 The Apache Software Foundation. * + * All rights reserved. * + * ------------------------------------------------------------------- * + * 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.apache.vysper.xmpp.xmlfragment; + +/** + * the XML was syntactically ok, but business logic applied on xml level revealed semantical problems + * (wrong attributes, doubled elements etc.) + */ +public class XMLSemanticError extends Exception { + public XMLSemanticError() { + super(); + } + + public XMLSemanticError(String s) { + super(s); + } + + public XMLSemanticError(String s, Throwable throwable) { + super(s, throwable); + } + + public XMLSemanticError(Throwable throwable) { + super(throwable); + } +} Added: labs/vysper/src/test/java/org/apache/vysper/xmpp/xmlfragment/XMLElementTestCase.java URL: http://svn.apache.org/viewvc/labs/vysper/src/test/java/org/apache/vysper/xmpp/xmlfragment/XMLElementTestCase.java?rev=571610&view=auto ============================================================================== --- labs/vysper/src/test/java/org/apache/vysper/xmpp/xmlfragment/XMLElementTestCase.java (added) +++ labs/vysper/src/test/java/org/apache/vysper/xmpp/xmlfragment/XMLElementTestCase.java Fri Aug 31 14:48:07 2007 @@ -0,0 +1,130 @@ +/*********************************************************************** + * Copyright (c) 2006-2007 The Apache Software Foundation. * + * All rights reserved. * + * ------------------------------------------------------------------- * + * 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.apache.vysper.xmpp.xmlfragment; + +import junit.framework.TestCase; +import org.apache.vysper.xmpp.stanza.StanzaBuilder; + +import java.util.List; + +/** + */ +public class XMLElementTestCase extends TestCase { + + public void testBasicGetters() { + XMLElement xmlElement = new StanzaBuilder("message", "jabber:test"). + addAttribute("lang", "de"). + addAttribute("xml:lang", "cn"). + addAttribute("xmllang", "en"). + getFinalStanza(); + + assertEquals("message", xmlElement.getName()); + assertEquals("jabber:test", xmlElement.getNamespace()); + assertEquals("cn", xmlElement.getXMLLang()); + + assertNull(xmlElement.getInnerElements()); + List list = xmlElement.getAttributes(); + assertNotNull(list); + assertEquals(3, list.size()); + } + + public void testInnerTextGetters() { + + XMLElement xmlElement = new StanzaBuilder("message", "jabber:test"). + addText("t1"). + startInnerElement("i1"). + endInnerElement(). + addText("t2"). + addText("t3"). + startInnerElement("i2"). + endInnerElement(). + addText("t4"). + getFinalStanza(); + + List list = xmlElement.getInnerTexts(); + assertEquals(4, list.size()); + assertEquals("t1", list.get(0).getText()); + assertEquals("t2", list.get(1).getText()); + assertEquals("t3", list.get(2).getText()); + assertEquals("t4", list.get(3).getText()); + + assertEquals("t1", xmlElement.getFirstInnerText().getText()); + try { + xmlElement.getSingleInnerText(); + fail("must raise exception"); + } catch (XMLSemanticError xmlSemanticError) { + // test succeeded + } + + xmlElement = new StanzaBuilder("message", "jabber:test"). + startInnerElement("i1"). + endInnerElement(). + getFinalStanza(); + try { + assertNull(xmlElement.getSingleInnerText()); + } catch (XMLSemanticError xmlSemanticError) { + fail("must not raise error"); + } + } + + public void testInnerElementGetters() { + + XMLElement xmlElement = new StanzaBuilder("message", "jabber:test"). + addText("t1"). + startInnerElement("i1"). + endInnerElement(). + startInnerElement("i2"). + addAttribute("order", "1"). + endInnerElement(). + startInnerElement("i2"). + addAttribute("order", "2"). + endInnerElement(). + addText("t2"). + addText("t3"). + startInnerElement("i3"). + endInnerElement(). + addText("t4"). + getFinalStanza(); + + List list = xmlElement.getInnerElements(); + assertEquals(4, list.size()); + + assertEquals("i1", xmlElement.getFirstInnerElement().getName()); + try { + xmlElement.getSingleInnerElementsNamed("i2"); + fail("must raise exception"); + } catch (XMLSemanticError xmlSemanticError) { + // test succeeded + } + + try { + XMLElement xmlElement1 = xmlElement.getSingleInnerElementsNamed("i3"); + assertEquals("i3", xmlElement1.getName()); + } catch (XMLSemanticError xmlSemanticError) { + fail("must not raise exception"); + } + + xmlElement = new StanzaBuilder("message", "jabber:test"). + addText("t1"). + getFinalStanza(); + try { + assertNull(xmlElement.getSingleInnerElementsNamed("none")); + } catch (XMLSemanticError xmlSemanticError) { + fail("must not raise error"); + } + } +} --------------------------------------------------------------------- To unsubscribe, e-mail: commits-unsubscribe@labs.apache.org For additional commands, e-mail: commits-help@labs.apache.org