xmppreader.java
来自「RESIN 3.2 最新源码」· Java 代码 · 共 638 行
JAVA
638 行
/* * Copyright (c) 1998-2008 Caucho Technology -- all rights reserved * * This file is part of Resin(R) Open Source * * Each copy or derived work must preserve the copyright notice and this * notice unmodified. * * Resin Open Source is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or * (at your option) any later version. * * Resin Open Source is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE, or any warranty * of NON-INFRINGEMENT. See the GNU General Public License for more * details. * * You should have received a copy of the GNU General Public License * along with Resin Open Source; if not, write to the * * Free Software Foundation, Inc. * 59 Temple Place, Suite 330 * Boston, MA 02111-1307 USA * * @author Scott Ferguson */package com.caucho.xmpp;import com.caucho.bam.BamStream;import com.caucho.bam.BamError;import com.caucho.bam.BamConnection;import com.caucho.bam.BamBroker;import com.caucho.server.connection.*;import com.caucho.util.*;import com.caucho.vfs.*;import com.caucho.xml.stream.*;import com.caucho.xmpp.im.XmppRosterQueryMarshal;import com.caucho.xmpp.im.Text;import com.caucho.xmpp.im.ImSessionQuery;import com.caucho.xmpp.im.ImPresence;import com.caucho.xmpp.im.ImMessage;import com.caucho.xmpp.im.XmlData;import java.io.*;import java.util.*;import java.util.logging.*;import javax.servlet.*;import javax.xml.namespace.QName;import javax.xml.stream.*;/** * Protocol handler from the TCP/XMPP stream forwarding to the broker */public class XmppReader{ private static final Logger log = Logger.getLogger(XmppReader.class.getName()); private BamStream _toReply; private BamStream _handler; private ReadStream _is; private XmppStreamReader _in; private XmppContext _xmppContext; private XmppMarshalFactory _marshalFactory; private String _uid; private String _jid; private boolean _isFinest; XmppReader(XmppContext context, ReadStream is, XmppStreamReader in, BamStream toReply, BamStream handler) { _xmppContext = context; _marshalFactory = context.getMarshalFactory(); _is = is; _in = in; _toReply = toReply; _handler = handler; _isFinest = log.isLoggable(Level.FINEST); } void setHandler(BamStream handler) { _handler = handler; } void setUid(String uid) { _uid = uid; } void setJid(String jid) { _jid = jid; } boolean readNext() throws IOException { XmppStreamReader in = _in; if (in == null) return false; try { int tag; while ((tag = _in.next()) > 0) { if (_isFinest) debug(_in); if (tag == XMLStreamConstants.END_ELEMENT) { if ("stream".equals(_in.getLocalName())) { if (log.isLoggable(Level.FINE)) log.fine(this + " end-stream"); } else { log.warning(this + " " + _in.getLocalName()); } return false; } if (tag == XMLStreamConstants.START_ELEMENT) { boolean valid = false; if ("iq".equals(_in.getLocalName())) valid = handleIq(); else if ("presence".equals(_in.getLocalName())) valid = handlePresence(); else if ("message".equals(_in.getLocalName())) valid = handleMessage(); else { if (log.isLoggable(Level.FINE)) log.fine(this + " " + _in.getLocalName() + " is an unknown tag"); return false; } if (! valid) return false; if (_in.available() < 1) return true; } } if (_isFinest) log.finest(this + " end of stream"); return false; } catch (Exception e) { log.log(Level.WARNING, e.toString(), e); return false; } } /** * Processes a message */ boolean handleMessage() throws IOException, XMLStreamException { String type = _in.getAttributeValue(null, "type"); String id = _in.getAttributeValue(null, "id"); String from = _in.getAttributeValue(null, "from"); String to = _in.getAttributeValue(null, "to"); if (type == null) type = "chat"; int tag; ArrayList<Text> subjectList = new ArrayList<Text>(); ArrayList<Text> bodyList = new ArrayList<Text>(); ArrayList<Serializable> extraList = new ArrayList<Serializable>(); String thread = null; while ((tag = _in.next()) > 0 && ! (tag == XMLStreamReader.END_ELEMENT && "message".equals(_in.getLocalName()))) { if (_isFinest) debug(_in); if (tag != XMLStreamReader.START_ELEMENT) continue; if ("body".equals(_in.getLocalName()) && "jabber:client".equals(_in.getNamespaceURI())) { String lang = null; if (_in.getAttributeCount() > 0 && "lang".equals(_in.getAttributeLocalName(0))) { lang = _in.getAttributeValue(0); } tag = _in.next(); if (_isFinest) debug(_in); String body = _in.getText(); bodyList.add(new Text(body, lang)); expectEnd("body"); } else if ("subject".equals(_in.getLocalName()) && "jabber:client".equals(_in.getNamespaceURI())) { String lang = null; if (_in.getAttributeCount() > 0 && "lang".equals(_in.getAttributeLocalName(0))) lang = _in.getAttributeValue(0); tag = _in.next(); if (_isFinest) debug(_in); String text = _in.getText(); subjectList.add(new Text(text, lang)); expectEnd("subject"); } else if ("thread".equals(_in.getLocalName()) && "jabber:client".equals(_in.getNamespaceURI())) { tag = _in.next(); if (_isFinest) debug(_in); thread = _in.getText(); expectEnd("thread"); } else { String name = _in.getLocalName(); String uri = _in.getNamespaceURI(); String data = _in.readAsXmlString(); extraList.add(new XmlData(name, uri, data)); } } expectEnd("message", tag); Text []subjectArray = null; if (subjectList.size() > 0) { subjectArray = new Text[subjectList.size()]; subjectList.toArray(subjectArray); } Text []bodyArray = null; if (bodyList.size() > 0) { bodyArray = new Text[bodyList.size()]; bodyList.toArray(bodyArray); } Serializable []extra = null; if (extraList.size() > 0) { extra = new Serializable[extraList.size()]; extraList.toArray(extra); } if (_jid != null) from = _jid; if (to == null) to = _uid; ImMessage message = new ImMessage(to, from, type, subjectArray, bodyArray, thread, extra); if (_handler != null) _handler.message(to, from, message); return true; } /** * Processes a query */ boolean handleIq() throws IOException, XMLStreamException { String type = _in.getAttributeValue(null, "type"); String id = _in.getAttributeValue(null, "id"); String from = _in.getAttributeValue(null, "from"); String to = _in.getAttributeValue(null, "to"); int tag = _in.nextTag(); if (_isFinest) debug(_in); String localName = _in.getLocalName(); String uri = _in.getNamespaceURI(); QName name = _in.getName(); Serializable query = null; XmppMarshal marshal = _marshalFactory.getUnserialize(name); if (marshal != null) query = marshal.fromXml(_in); else query = readAsXmlString(_in); BamError error = null; skipToEnd("iq"); if (_jid != null) from = _jid; if (to == null) { to = _uid; if (query instanceof ImSessionQuery && "set".equals(type)) { long bamId = _xmppContext.addId(id); _toReply.queryResult(bamId, from, to, query); return true; } } if ("get".equals(type)) { long bamId = _xmppContext.addId(id); if (_handler != null) _handler.queryGet(bamId, to, from, query); } else if ("set".equals(type)) { long bamId = _xmppContext.addId(id); if (_handler != null) _handler.querySet(bamId, to, from, query); } else if ("result".equals(type)) { long bamId = Long.parseLong(id); if (_handler != null) _handler.queryResult(bamId, to, from, query); } else if ("error".equals(type)) { long bamId = Long.parseLong(id); if (_handler != null) _handler.queryError(bamId, to, from, query, error); } else { if (log.isLoggable(Level.FINE)) { log.fine(this + " <" + _in.getLocalName() + " xmlns=" + _in.getNamespaceURI() + "> unknown type"); } } return true; } boolean handlePresence() throws IOException, XMLStreamException { String type = _in.getAttributeValue(null, "type"); String id = _in.getAttributeValue(null, "id"); String from = _in.getAttributeValue(null, "from"); String to = _in.getAttributeValue(null, "to"); String target = to; if (type == null) type = ""; int tag; String show = null; Text status = null; int priority = 0; ArrayList<Serializable> extraList = new ArrayList<Serializable>(); BamError error = null; while ((tag = _in.nextTag()) > 0 && ! ("presence".equals(_in.getLocalName()) && tag == XMLStreamReader.END_ELEMENT)) { if (_isFinest) debug(_in); if (tag != XMLStreamReader.START_ELEMENT) continue; if ("status".equals(_in.getLocalName())) { tag = _in.next(); if (_isFinest) debug(_in); status = new Text(_in.getText()); skipToEnd("status"); } else if ("show".equals(_in.getLocalName())) { tag = _in.next(); if (_isFinest) debug(_in); show = _in.getText(); skipToEnd("show"); } else if ("priority".equals(_in.getLocalName())) { tag = _in.next(); if (_isFinest) debug(_in); priority = Integer.parseInt(_in.getText()); skipToEnd("priority"); } else { String name = _in.getLocalName(); String uri = _in.getNamespaceURI(); String data = _in.readAsXmlString(); extraList.add(new XmlData(name, uri, data)); } } if (_isFinest) debug(_in); expectEnd("presence", tag); if (_jid != null) from = _jid; if (target == null) target = _uid; ImPresence presence = new ImPresence(to, from, show, status, priority, extraList); if (_handler != null) { if ("".equals(type)) _handler.presence(target, from, presence); else if ("probe".equals(type)) _handler.presenceProbe(target, from, presence); else if ("unavailable".equals(type)) _handler.presenceUnavailable(target, from, presence); else if ("subscribe".equals(type)) _handler.presenceSubscribe(target, from, presence); else if ("subscribed".equals(type)) _handler.presenceSubscribed(target, from, presence); else if ("unsubscribe".equals(type)) _handler.presenceUnsubscribe(target, from, presence); else if ("unsubscribed".equals(type)) _handler.presenceUnsubscribed(target, from, presence); else if ("error".equals(type)) _handler.presenceError(target, from, presence, error); else log.warning(this + " " + type + " is an unknown presence type"); } return true; } protected void skipToEnd(String tagName) throws IOException, XMLStreamException { XMLStreamReader in = _in; if (in == null) return; int tag; while ((tag = in.next()) > 0) { if (_isFinest) debug(in); if (tag == XMLStreamReader.START_ELEMENT) { } else if (tag == XMLStreamReader.END_ELEMENT) { if (tagName.equals(in.getLocalName())) return; } } } private void expectEnd(String tagName) throws IOException, XMLStreamException { expectEnd(tagName, _in.nextTag()); } private void expectEnd(String tagName, int tag) throws IOException, XMLStreamException { if (tag != XMLStreamReader.END_ELEMENT) throw new IllegalStateException("expected </" + tagName + "> at <" + _in.getLocalName() + ">"); else if (! tagName.equals(_in.getLocalName())) throw new IllegalStateException("expected </" + tagName + "> at </" + _in.getLocalName() + ">"); } private String readAsXmlString(XMLStreamReader in) throws IOException, XMLStreamException { StringBuilder sb = new StringBuilder(); int depth = 0; while (true) { if (XMLStreamReader.START_ELEMENT == in.getEventType()) { depth++; String prefix = in.getPrefix(); sb.append("<"); if (! "".equals(prefix)) { sb.append(prefix); sb.append(":"); } sb.append(in.getLocalName()); if (in.getNamespaceURI() != null) { if ("".equals(prefix)) sb.append(" xmlns"); else sb.append(" xmlns:").append(prefix); sb.append("=\""); sb.append(in.getNamespaceURI()).append("\""); } for (int i = 0; i < in.getAttributeCount(); i++) { sb.append(" "); sb.append(in.getAttributeLocalName(i)); sb.append("=\""); sb.append(in.getAttributeValue(i)); sb.append("\""); } sb.append(">"); log.finest(this + " " + sb); } else if (XMLStreamReader.END_ELEMENT == in.getEventType()) { depth--; sb.append("</"); String prefix = in.getPrefix(); if (! "".equals(prefix)) sb.append(prefix).append(":"); sb.append(in.getLocalName()); sb.append(">"); if (depth == 0) return sb.toString(); } else if (XMLStreamReader.CHARACTERS == in.getEventType()) { sb.append(in.getText()); } else { log.finer(this + " tag=" + in.getEventType()); return sb.toString(); } if (in.next() < 0) { log.finer(this + " unexpected end of file"); return sb.toString(); } } } private void debug(XMLStreamReader in) throws IOException, XMLStreamException { if (XMLStreamReader.START_ELEMENT == in.getEventType()) { StringBuilder sb = new StringBuilder(); sb.append("<").append(in.getLocalName()); if (in.getNamespaceURI() != null) sb.append("{").append(in.getNamespaceURI()).append("}"); for (int i = 0; i < in.getAttributeCount(); i++) { sb.append(" "); sb.append(in.getAttributeLocalName(i)); sb.append("='"); sb.append(in.getAttributeValue(i)); sb.append("'"); } sb.append(">"); log.finest(this + " " + sb); } else if (XMLStreamReader.END_ELEMENT == in.getEventType()) { log.finest(this + " </" + in.getLocalName() + ">"); } else if (XMLStreamReader.CHARACTERS == in.getEventType()) { String text = in.getText().trim(); if (! "".equals(text)) log.finest(this + " text='" + text + "'"); } else log.finest(this + " tag=" + in.getEventType()); } @Override public String toString() { return getClass().getSimpleName() + "[]"; }}
⌨️ 快捷键说明
复制代码Ctrl + C
搜索代码Ctrl + F
全屏模式F11
增大字号Ctrl + =
减小字号Ctrl + -
显示快捷键?