001/** 002 * 003 * Copyright 2003-2007 Jive Software. 004 * 005 * Licensed under the Apache License, Version 2.0 (the "License"); 006 * you may not use this file except in compliance with the License. 007 * You may obtain a copy of the License at 008 * 009 * http://www.apache.org/licenses/LICENSE-2.0 010 * 011 * Unless required by applicable law or agreed to in writing, software 012 * distributed under the License is distributed on an "AS IS" BASIS, 013 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 014 * See the License for the specific language governing permissions and 015 * limitations under the License. 016 */ 017package org.jivesoftware.smackx.bookmarks; 018 019import org.jivesoftware.smack.util.XmlStringBuilder; 020import org.jivesoftware.smackx.iqprivate.packet.PrivateData; 021import org.jivesoftware.smackx.iqprivate.provider.PrivateDataProvider; 022import org.xmlpull.v1.XmlPullParser; 023import org.xmlpull.v1.XmlPullParserException; 024 025import java.io.IOException; 026import java.util.ArrayList; 027import java.util.List; 028 029/** 030 * Bookmarks is used for storing and retrieving URLS and Conference rooms. 031 * Bookmark Storage (XEP-0048) defined a protocol for the storage of bookmarks to conference rooms and other entities 032 * in a Jabber user's account. 033 * See the following code sample for saving Bookmarks: 034 * <p/> 035 * <pre> 036 * XMPPConnection con = new XMPPTCPConnection("jabber.org"); 037 * con.login("john", "doe"); 038 * Bookmarks bookmarks = new Bookmarks(); 039 * <p/> 040 * // Bookmark a URL 041 * BookmarkedURL url = new BookmarkedURL(); 042 * url.setName("Google"); 043 * url.setURL("http://www.jivesoftware.com"); 044 * bookmarks.addURL(url); 045 * // Bookmark a Conference room. 046 * BookmarkedConference conference = new BookmarkedConference(); 047 * conference.setName("My Favorite Room"); 048 * conference.setAutoJoin("true"); 049 * conference.setJID("dev@conference.jivesoftware.com"); 050 * bookmarks.addConference(conference); 051 * // Save Bookmarks using PrivateDataManager. 052 * PrivateDataManager manager = new PrivateDataManager(con); 053 * manager.setPrivateData(bookmarks); 054 * <p/> 055 * <p/> 056 * LastActivity activity = LastActivity.getLastActivity(con, "xray@jabber.org"); 057 * </pre> 058 * 059 * @author Derek DeMoro 060 */ 061public class Bookmarks implements PrivateData { 062 063 public static final String NAMESPACE = "storage:bookmarks"; 064 public static final String ELEMENT = "storage"; 065 066 private List<BookmarkedURL> bookmarkedURLS; 067 private List<BookmarkedConference> bookmarkedConferences; 068 069 /** 070 * Required Empty Constructor to use Bookmarks. 071 */ 072 public Bookmarks() { 073 bookmarkedURLS = new ArrayList<BookmarkedURL>(); 074 bookmarkedConferences = new ArrayList<BookmarkedConference>(); 075 } 076 077 /** 078 * Adds a BookmarkedURL. 079 * 080 * @param bookmarkedURL the bookmarked bookmarkedURL. 081 */ 082 public void addBookmarkedURL(BookmarkedURL bookmarkedURL) { 083 bookmarkedURLS.add(bookmarkedURL); 084 } 085 086 /** 087 * Removes a bookmarked bookmarkedURL. 088 * 089 * @param bookmarkedURL the bookmarked bookmarkedURL to remove. 090 */ 091 public void removeBookmarkedURL(BookmarkedURL bookmarkedURL) { 092 bookmarkedURLS.remove(bookmarkedURL); 093 } 094 095 /** 096 * Removes all BookmarkedURLs from user's bookmarks. 097 */ 098 public void clearBookmarkedURLS() { 099 bookmarkedURLS.clear(); 100 } 101 102 /** 103 * Add a BookmarkedConference to bookmarks. 104 * 105 * @param bookmarkedConference the conference to remove. 106 */ 107 public void addBookmarkedConference(BookmarkedConference bookmarkedConference) { 108 bookmarkedConferences.add(bookmarkedConference); 109 } 110 111 /** 112 * Removes a BookmarkedConference. 113 * 114 * @param bookmarkedConference the BookmarkedConference to remove. 115 */ 116 public void removeBookmarkedConference(BookmarkedConference bookmarkedConference) { 117 bookmarkedConferences.remove(bookmarkedConference); 118 } 119 120 /** 121 * Removes all BookmarkedConferences from Bookmarks. 122 */ 123 public void clearBookmarkedConferences() { 124 bookmarkedConferences.clear(); 125 } 126 127 /** 128 * Returns a Collection of all Bookmarked URLs for this user. 129 * 130 * @return a collection of all Bookmarked URLs. 131 */ 132 public List<BookmarkedURL> getBookmarkedURLS() { 133 return bookmarkedURLS; 134 } 135 136 /** 137 * Returns a Collection of all Bookmarked Conference for this user. 138 * 139 * @return a collection of all Bookmarked Conferences. 140 */ 141 public List<BookmarkedConference> getBookmarkedConferences() { 142 return bookmarkedConferences; 143 } 144 145 146 /** 147 * Returns the root element name. 148 * 149 * @return the element name. 150 */ 151 public String getElementName() { 152 return ELEMENT; 153 } 154 155 /** 156 * Returns the root element XML namespace. 157 * 158 * @return the namespace. 159 */ 160 public String getNamespace() { 161 return NAMESPACE; 162 } 163 164 /** 165 * Returns the XML representation of the PrivateData. 166 * 167 * @return the private data as XML. 168 */ 169 @Override 170 public XmlStringBuilder toXML() { 171 XmlStringBuilder buf = new XmlStringBuilder(); 172 buf.openElement(ELEMENT).xmlnsAttribute(NAMESPACE); 173 174 for (BookmarkedURL urlStorage : getBookmarkedURLS()) { 175 if(urlStorage.isShared()) { 176 continue; 177 } 178 buf.openElement("url").attribute("name", urlStorage.getName()).attribute("url", urlStorage.getURL()); 179 buf.condAttribute(urlStorage.isRss(), "rss", "true"); 180 buf.closeEmptyElement(); 181 } 182 183 // Add Conference additions 184 for (BookmarkedConference conference : getBookmarkedConferences()) { 185 if(conference.isShared()) { 186 continue; 187 } 188 buf.openElement("conference"); 189 buf.attribute("name", conference.getName()); 190 buf.attribute("autojoin", Boolean.toString(conference.isAutoJoin())); 191 buf.attribute("jid", conference.getJid()); 192 buf.rightAngelBracket(); 193 194 buf.optElement("nick", conference.getNickname()); 195 buf.optElement("password", conference.getPassword()); 196 197 buf.closeElement("conference"); 198 } 199 200 buf.closeElement(ELEMENT); 201 return buf; 202 } 203 204 /** 205 * The IQ Provider for BookmarkStorage. 206 * 207 * @author Derek DeMoro 208 */ 209 public static class Provider implements PrivateDataProvider { 210 211 /** 212 * Empty Constructor for PrivateDataProvider. 213 */ 214 public Provider() { 215 super(); 216 } 217 218 public PrivateData parsePrivateData(XmlPullParser parser) throws Exception { 219 Bookmarks storage = new Bookmarks(); 220 221 boolean done = false; 222 while (!done) { 223 int eventType = parser.next(); 224 if (eventType == XmlPullParser.START_TAG && "url".equals(parser.getName())) { 225 final BookmarkedURL urlStorage = getURLStorage(parser); 226 if (urlStorage != null) { 227 storage.addBookmarkedURL(urlStorage); 228 } 229 } 230 else if (eventType == XmlPullParser.START_TAG && 231 "conference".equals(parser.getName())) 232 { 233 final BookmarkedConference conference = getConferenceStorage(parser); 234 storage.addBookmarkedConference(conference); 235 } 236 else if (eventType == XmlPullParser.END_TAG && "storage".equals(parser.getName())) 237 { 238 done = true; 239 } 240 } 241 242 243 return storage; 244 } 245 } 246 247 private static BookmarkedURL getURLStorage(XmlPullParser parser) throws IOException, XmlPullParserException { 248 String name = parser.getAttributeValue("", "name"); 249 String url = parser.getAttributeValue("", "url"); 250 String rssString = parser.getAttributeValue("", "rss"); 251 boolean rss = rssString != null && "true".equals(rssString); 252 253 BookmarkedURL urlStore = new BookmarkedURL(url, name, rss); 254 boolean done = false; 255 while (!done) { 256 int eventType = parser.next(); 257 if(eventType == XmlPullParser.START_TAG 258 && "shared_bookmark".equals(parser.getName())) { 259 urlStore.setShared(true); 260 } 261 else if (eventType == XmlPullParser.END_TAG && "url".equals(parser.getName())) { 262 done = true; 263 } 264 } 265 return urlStore; 266 } 267 268 private static BookmarkedConference getConferenceStorage(XmlPullParser parser) throws Exception { 269 String name = parser.getAttributeValue("", "name"); 270 String autojoin = parser.getAttributeValue("", "autojoin"); 271 String jid = parser.getAttributeValue("", "jid"); 272 273 BookmarkedConference conf = new BookmarkedConference(jid); 274 conf.setName(name); 275 conf.setAutoJoin(Boolean.valueOf(autojoin).booleanValue()); 276 277 // Check for nickname 278 boolean done = false; 279 while (!done) { 280 int eventType = parser.next(); 281 if (eventType == XmlPullParser.START_TAG && "nick".equals(parser.getName())) { 282 conf.setNickname(parser.nextText()); 283 } 284 else if (eventType == XmlPullParser.START_TAG && "password".equals(parser.getName())) { 285 conf.setPassword(parser.nextText()); 286 } 287 else if(eventType == XmlPullParser.START_TAG 288 && "shared_bookmark".equals(parser.getName())) { 289 conf.setShared(true); 290 } 291 else if (eventType == XmlPullParser.END_TAG && "conference".equals(parser.getName())) { 292 done = true; 293 } 294 } 295 296 297 return conf; 298 } 299}