1 23 24 28 29 package org.infoglue.cms.applications.common.actions; 30 31 import java.io.IOException ; 32 import java.io.InputStream ; 33 import java.io.OutputStream ; 34 import java.io.OutputStreamWriter ; 35 import java.io.PrintWriter ; 36 import java.io.StringWriter ; 37 import java.io.UnsupportedEncodingException ; 38 import java.net.URLEncoder ; 39 import java.util.Collection ; 40 import java.util.Date ; 41 import java.util.HashMap ; 42 import java.util.Iterator ; 43 import java.util.List ; 44 import java.util.Map ; 45 import java.util.Properties ; 46 47 import org.apache.log4j.Logger; 48 import org.dom4j.Document; 49 import org.dom4j.DocumentHelper; 50 import org.dom4j.Element; 51 import org.dom4j.io.OutputFormat; 52 import org.dom4j.io.XMLWriter; 53 import org.infoglue.cms.applications.common.VisualFormatter; 54 import org.infoglue.cms.controllers.kernel.impl.simple.ContentController; 55 import org.infoglue.cms.controllers.kernel.impl.simple.ContentTypeDefinitionController; 56 import org.infoglue.cms.controllers.kernel.impl.simple.ContentVersionController; 57 import org.infoglue.cms.controllers.kernel.impl.simple.LanguageController; 58 import org.infoglue.cms.controllers.kernel.impl.simple.RepositoryController; 59 import org.infoglue.cms.controllers.kernel.impl.simple.TransactionHistoryController; 60 import org.infoglue.cms.entities.content.ContentVersionVO; 61 import org.infoglue.cms.entities.kernel.BaseEntityVO; 62 import org.infoglue.cms.entities.management.ContentTypeDefinitionVO; 63 import org.infoglue.cms.entities.management.RepositoryVO; 64 import org.infoglue.cms.entities.management.TransactionHistoryVO; 65 import org.infoglue.cms.entities.management.impl.simple.ContentTypeDefinitionImpl; 66 import org.infoglue.cms.exception.ConstraintException; 67 import org.infoglue.cms.exception.SystemException; 68 import org.infoglue.cms.security.InfoGluePrincipal; 69 import org.infoglue.cms.util.ChangeNotificationController; 70 import org.infoglue.cms.util.CmsPropertyHandler; 71 import org.infoglue.cms.util.XMLNotificationWriter; 72 73 import com.frovi.ss.Tree.BaseNode; 74 import com.frovi.ss.Tree.INodeSupplier; 75 76 public abstract class SimpleXmlServiceAction extends InfoGlueAbstractAction 77 { 78 private final static Logger logger = Logger.getLogger(SimpleXmlServiceAction.class.getName()); 79 80 private static final String protectedPropertyFragments = "password,administrator,authorizer,authenticator,masterserver,slaveserver,log"; 81 82 protected static final String SERVICEREVISION = "$Revision: 1.19 $"; 83 protected static String ENCODING = "UTF-8"; 84 protected static String TYPE_FOLDER = "Folder"; 85 protected static String TYPE_ITEM = "Item"; 86 protected static String TYPE_REPOSITORY = "Repository"; 87 protected String showLeafs = "yes"; 88 protected Integer parent = null; 89 protected Integer repositoryId = null; 90 protected String urlArgSeparator = "&"; 91 protected String action = ""; 92 protected boolean createAction = false; 93 protected boolean useTemplate = false; 94 protected VisualFormatter formatter = new VisualFormatter(); 95 protected String [] allowedContentTypeIds = null; 96 97 102 protected static Map changeNotificationBuffer = new HashMap (); 103 104 105 public abstract INodeSupplier getNodeSupplier() throws SystemException; 106 107 protected abstract BaseEntityVO getRootEntityVO(Integer repositoryId, InfoGluePrincipal principal) throws ConstraintException, SystemException; 108 109 public List getContentTypeDefinitions() throws Exception  110 { 111 return ContentTypeDefinitionController.getController().getContentTypeDefinitionVOList(); 112 } 113 114 public String encode(String text) 115 { 116 return text; 117 } 118 119 protected String makeAction(BaseNode node) throws UnsupportedEncodingException  120 { 121 String action = "javascript:onTreeItemClick(this,"; 122 action+="'" + node.getId() + "','" + repositoryId + "','" + new VisualFormatter().escapeForAdvancedJavascripts(node.getTitle()) + "');"; 125 return action; 126 } 127 128 protected String getFormattedDocument(Document doc) 129 { 130 return getFormattedDocument(doc, true, false); 131 } 132 133 protected String getFormattedDocument(Document doc, boolean compact, boolean supressDecl) 134 { 135 OutputFormat format = compact ? OutputFormat.createCompactFormat() : OutputFormat.createPrettyPrint(); 136 format.setSuppressDeclaration(supressDecl); 137 format.setEncoding(ENCODING); 138 format.setExpandEmptyElements(false); 139 StringWriter stringWriter = new StringWriter (); 140 XMLWriter writer = new XMLWriter(stringWriter, format); 141 try 142 { 143 writer.write(doc); 144 } 145 catch (IOException e) 146 { 147 e.printStackTrace(); 148 } 149 return stringWriter.toString(); 150 } 151 152 protected String out(String string) throws IOException  153 { 154 getResponse().setContentType("text/xml; charset=" + ENCODING); 155 getResponse().setHeader("Cache-Control","no-cache"); 156 getResponse().setHeader("Pragma","no-cache"); 157 getResponse().setDateHeader ("Expires", 0); 158 159 PrintWriter out = getResponse().getWriter(); 160 out.println(string); 161 return null; 162 } 163 164 167 public String doLanguage() throws Exception  168 { 169 return null; 170 } 171 172 public String doApplicationSettings() throws Exception  173 { 174 Document doc = DocumentHelper.createDocument(); 175 Element root = doc.addElement("applicationSettings"); 176 Properties props = CmsPropertyHandler.getProperties(); 177 for(Iterator i = props.keySet().iterator(); i.hasNext();) 178 { 179 String key = (String ) i.next(); 180 String elmKey = key; 181 if(key.matches("^\\d.*")) elmKey = "_" + key; 182 String value = (String ) props.get(key); 183 if(!isProtectedProperty(key)) 184 root.addElement(elmKey).setText(value); 185 } 186 187 root.addElement("serviceRevision").setText(SERVICEREVISION); 188 return out(getFormattedDocument(doc)); 189 } 190 191 private boolean isProtectedProperty(String key) 192 { 193 String [] fragments = protectedPropertyFragments.split(","); 194 for(int i=0; i<fragments.length;i++) 195 if(key.toLowerCase().indexOf(fragments[i].toLowerCase()) > -1) 196 return true; 197 return false; 198 } 199 200 203 public String doContentTypeDefinitions() throws Exception  204 { 205 List contentTypeDefinitions = getContentTypeDefinitions(); 206 Document doc = DocumentHelper.createDocument(); 207 Element root = doc.addElement("definitions"); 208 TransactionHistoryController transactionHistoryController = TransactionHistoryController.getController(); 209 210 for(Iterator i=contentTypeDefinitions.iterator();i.hasNext();) 211 { 212 ContentTypeDefinitionVO vo = (ContentTypeDefinitionVO) i.next(); 213 if(vo.getType().compareTo(ContentTypeDefinitionVO.CONTENT)==0) 214 { 215 TransactionHistoryVO transactionHistoryVO = transactionHistoryController.getLatestTransactionHistoryVOForEntity(ContentTypeDefinitionImpl.class, vo.getContentTypeDefinitionId()); 216 217 Element definition = DocumentHelper.createElement("definition"); 218 definition 219 .addAttribute("id", "" + vo.getContentTypeDefinitionId()) 220 .addAttribute("type", "" + vo.getType()) 221 .addAttribute("name", vo.getName()) 222 ; 223 224 if(transactionHistoryVO!=null) 225 definition.addAttribute("mod", formatDate(transactionHistoryVO.getTransactionDateTime())); 226 227 Element schemaValue = definition.addElement("schemaValue"); 228 schemaValue.addCDATA(vo.getSchemaValue()); 229 root.add(definition); 230 } 231 } 232 return out(getFormattedDocument(doc)); 233 234 } 235 236 public String doGetChangeNotifications() throws IOException  237 { 238 String id = getRequest().getSession().getId(); 239 StringWriter buffer = (StringWriter ) changeNotificationBuffer.get(id); 240 if(buffer==null) 241 { 242 buffer = new StringWriter (); 243 buffer.write("<changeNotifications>"); 244 changeNotificationBuffer.put(id, buffer); 245 XMLNotificationWriter streamWriter = new XMLNotificationWriter(buffer, ENCODING, "", null, true, true); 246 ChangeNotificationController.getInstance().registerListener(streamWriter); 247 } 248 249 buffer.write("</changeNotifications>"); 250 try 251 { 252 out(getFormattedDocument(DocumentHelper.parseText(buffer.toString()))); 253 } 254 catch(Exception e) 255 { 256 out("<exception/>"); 257 } 258 buffer.getBuffer().delete(0, buffer.getBuffer().length()); 259 buffer.write("<changeNotifications>"); 260 return null; 261 } 262 263 public String doGetChangeNotificationsStream() throws IOException  264 { 265 boolean open = true; 266 String remoteId = getRequest().getRemoteAddr() + " / " + getInfoGluePrincipal().getName(); 267 268 String boundary = getRequest().getParameter("boundary"); 269 if(boundary==null) boundary = "-----------------infoglue-multipart-1d4faa3ac353573"; 270 getResponse().setHeader("boundary", boundary); 271 getResponse().setBufferSize(0); 272 getResponse().setContentType("text/plain; charset=" + ENCODING); 273 getResponse().flushBuffer(); 274 Thread thread = Thread.currentThread(); 275 OutputStream out = getResponse().getOutputStream(); 276 InputStream in = getRequest().getInputStream(); 277 278 XMLNotificationWriter streamWriter = new XMLNotificationWriter(new OutputStreamWriter (out), ENCODING, boundary, thread, true, false); 279 280 logger.info("Notification stream listen started from:" + remoteId); 281 ChangeNotificationController.getInstance().registerListener(streamWriter); 282 283 while(open) 284 { 285 try 286 { 287 Thread.sleep(Long.MAX_VALUE); 288 out.flush(); 289 } 290 catch (Exception e) 291 { 292 open = false; 293 } 294 } 295 ChangeNotificationController.getInstance().unregisterListener(streamWriter); 296 logger.info("Notification stream listen ended from:" + remoteId); 297 return null; 298 } 299 300 protected String formatDate(Date date) 301 { 302 return "" + date; 303 } 304 305 308 public String doExecute() throws Exception  309 { 310 if (useTemplate) return "success"; 311 312 Document doc = DocumentHelper.createDocument(); 313 Element root = doc.addElement("tree"); 314 315 INodeSupplier sup; 316 317 if(repositoryId == null) 318 { 319 List repositories = RepositoryController.getController().getAuthorizedRepositoryVOList(this.getInfoGluePrincipal(), false); 320 for(Iterator i=repositories.iterator();i.hasNext();) 321 { 322 RepositoryVO r = (RepositoryVO) i.next(); 323 BaseEntityVO entityVO = getRootEntityVO(r.getId(), this.getInfoGluePrincipal()); 324 325 String SRC= action + "?repositoryId=" + r.getId() + urlArgSeparator + "parent=" + entityVO.getId(); 326 if(createAction && src.length() >0) src += urlArgSeparator + "createAction=true"; 327 if(action.length()>0 && src.length() >0) src += urlArgSeparator + "action=" + action; 328 String allowedContentTypeIdsUrlEncodedString = getAllowedContentTypeIdsAsUrlEncodedString(); 329 logger.info("allowedContentTypeIdsUrlEncodedString1:" + allowedContentTypeIdsUrlEncodedString); 330 if(allowedContentTypeIdsUrlEncodedString.length()>0 && src.length() >0) 331 src += urlArgSeparator + allowedContentTypeIdsUrlEncodedString; 332 333 logger.info("src:" + src); 334 335 String text=r.getName(); 336 Element element = root.addElement("tree"); 337 element 338 .addAttribute("id", "" + r.getId()) 339 .addAttribute("repositoryId", "" + r.getId()) 340 .addAttribute("text", encode(text)) 341 .addAttribute("src", src) 342 .addAttribute("hasChildren", "true") 343 .addAttribute("type", TYPE_REPOSITORY); 344 } 345 out(getFormattedDocument(doc)); 346 return null; 347 } 348 349 sup = getNodeSupplier(); 350 351 if(parent == null) 352 { 353 BaseNode node = sup.getRootNode(); 354 String text = node.getTitle(); 355 String type = TYPE_FOLDER; 356 String src = action + "?repositoryId=" + repositoryId + urlArgSeparator + "parent=" + node.getId(); 357 if(createAction && src.length() >0) src += urlArgSeparator + "createAction=true"; 358 if(action.length()>0 && src.length() >0) src += urlArgSeparator + "action=" + action; 359 String allowedContentTypeIdsUrlEncodedString = getAllowedContentTypeIdsAsUrlEncodedString(); 360 logger.info("allowedContentTypeIdsUrlEncodedString2:" + allowedContentTypeIdsUrlEncodedString); 361 if(allowedContentTypeIdsUrlEncodedString.length()>0 && src.length() >0) 362 src += urlArgSeparator + allowedContentTypeIdsUrlEncodedString; 363 364 logger.info("src2:" + src); 365 366 Element elm = root.addElement("tree"); 367 elm 368 .addAttribute("id", "" + node.getId()) 369 .addAttribute("repositoryId", "" + repositoryId) 370 .addAttribute("text", encode(text)) 371 .addAttribute("src", src) 372 .addAttribute("isHidden", (String )node.getParameters().get("isHidden")) 373 .addAttribute("hasChildren", "true") 374 .addAttribute("type", type); 375 376 out(getFormattedDocument(doc)); 377 return null; 378 } 379 380 if(parent.intValue() > -1) 381 { 382 Collection containerNodes = sup.getChildContainerNodes(parent); 383 Collection childNodes = sup.getChildLeafNodes(parent); 384 385 ContentController contentController = ContentController.getContentController(); 386 ContentVersionController contentVersionController = ContentVersionController.getContentVersionController(); 387 388 Iterator it = containerNodes.iterator(); 389 while (it.hasNext()) 390 { 391 BaseNode theNode = (BaseNode) it.next(); 392 if (theNode.isContainer() && sup.hasChildren()) 393 { 394 theNode.setChildren(sup.hasChildren(theNode.getId())); 395 } 396 397 String src = action + "?repositoryId=" + repositoryId + urlArgSeparator + "parent=" + theNode.getId(); 399 if(createAction && src.length() >0) src += urlArgSeparator + "createAction=true"; 400 if(createAction && src.length() >0) src += urlArgSeparator + "showLeafs=" + showLeafs; 401 if(action.length()>0 && src.length() >0) src += urlArgSeparator + "action=" + action; 402 String allowedContentTypeIdsUrlEncodedString = getAllowedContentTypeIdsAsUrlEncodedString(); 403 if(allowedContentTypeIdsUrlEncodedString.length()>0 && src.length() >0) src += urlArgSeparator + allowedContentTypeIdsUrlEncodedString; 404 405 Element elm = root.addElement("tree"); 406 elm 407 .addAttribute("id", "" + theNode.getId()) 408 .addAttribute("parent", "" + parent) 409 .addAttribute("repositoryId", "" + repositoryId) 410 .addAttribute("text", encode(theNode.getTitle())) 411 .addAttribute("src", src) 412 .addAttribute("isHidden", (String )theNode.getParameters().get("isHidden")) 413 .addAttribute("type", TYPE_FOLDER) 414 .addAttribute("hasChildren", "" + theNode.hasChildren()); 415 416 if(createAction) elm.addAttribute("action", makeAction(theNode)); 417 } 418 419 it = childNodes.iterator(); 420 while (it.hasNext()) 421 { 422 BaseNode theNode = (BaseNode) it.next(); 423 424 String text = theNode.getTitle(); 425 String action = makeAction(theNode); 426 String type = TYPE_ITEM; 427 Element elm = root.addElement("tree"); 428 elm 429 .addAttribute("id", "" + theNode.getId()) 430 .addAttribute("parent", "" + parent) 431 .addAttribute("repositoryId", "" + repositoryId) 432 .addAttribute("text", encode(text)) 433 .addAttribute("type", type) 434 ; 435 if(createAction) 436 elm.addAttribute("action", action); 437 else 438 { 439 ContentVersionVO activeVersion = contentVersionController.getLatestActiveContentVersionVO(theNode.getId(), LanguageController.getController().getMasterLanguage(repositoryId).getLanguageId()); 440 if(activeVersion!=null && !useTemplate) 441 elm.addAttribute("activeVersion", "" + activeVersion.getContentVersionId()); 442 } 443 444 if(!useTemplate && sup.getClass().getName().indexOf("Content") > -1) 446 { 447 ContentTypeDefinitionVO contentTypeDefinitionVO = contentController.getContentTypeDefinition(theNode.getId()); 448 if(contentTypeDefinitionVO != null) 449 elm.addAttribute("contentTypeId","" + contentTypeDefinitionVO.getContentTypeDefinitionId()); 450 } 451 } 452 453 out(getFormattedDocument(doc)); 454 return null; 455 } 456 457 return null; 458 } 459 460 public Integer getParent() { 461 return parent; 462 } 463 464 public void setParent(Integer integer) { 465 parent = integer; 466 } 467 468 public Integer getRepositoryId() { 469 return repositoryId; 470 } 471 472 public void setRepositoryId(Integer integer) { 473 repositoryId = integer; 474 } 475 476 public boolean isCreateAction() 477 { 478 return createAction; 479 } 480 public void setCreateAction(boolean createAction) 481 { 482 this.createAction = createAction; 483 } 484 public boolean isUseTemplate() 485 { 486 return useTemplate; 487 } 488 public void setUseTemplate(boolean useTemplate) 489 { 490 this.useTemplate = useTemplate; 491 } 492 public String getAction() 493 { 494 return action; 495 } 496 public void setAction(String action) 497 { 498 this.action = action; 499 } 500 public String getShowLeafs() { 501 return showLeafs; 502 } 503 public void setShowLeafs(String showLeafs) { 504 this.showLeafs = showLeafs; 505 } 506 507 public String [] getAllowedContentTypeIds() 508 { 509 return allowedContentTypeIds; 510 } 511 512 public void setAllowedContentTypeIds(String [] allowedContentTypeIds) 513 { 514 this.allowedContentTypeIds = allowedContentTypeIds; 515 } 516 517 public String getAllowedContentTypeIdsAsUrlEncodedString() throws Exception  518 { 519 if(allowedContentTypeIds == null) 520 return ""; 521 522 StringBuffer sb = new StringBuffer (); 523 524 for(int i=0; i<allowedContentTypeIds.length; i++) 525 { 526 if(i > 0) 527 sb.append("&"); 528 529 sb.append("allowedContentTypeIds=" + URLEncoder.encode(allowedContentTypeIds[i], "UTF-8")); 530 } 531 532 return sb.toString(); 533 } 534 } | Popular Tags |