001 package railo.runtime.cache.eh.remote.rest.sax; 002 003 import java.io.IOException; 004 import java.io.InputStream; 005 import java.io.Reader; 006 007 import org.xml.sax.Attributes; 008 import org.xml.sax.InputSource; 009 import org.xml.sax.SAXException; 010 import org.xml.sax.XMLReader; 011 import org.xml.sax.helpers.DefaultHandler; 012 013 import railo.loader.util.Util; 014 import railo.runtime.text.xml.XMLUtil; 015 016 public class CacheFactory extends DefaultHandler { 017 018 public final static String DEFAULT_SAX_PARSER="org.apache.xerces.parsers.SAXParser"; 019 020 private XMLReader xmlReader; 021 022 protected String inside; 023 protected StringBuffer content=new StringBuffer(); 024 025 private boolean insideCacheConfiguration; 026 027 private CacheConfiguration cc=new CacheConfiguration(); 028 private CacheStatistics cs=new CacheStatistics(); 029 030 private boolean insideStatistics; 031 032 //private boolean insideError; 033 //private boolean insideMessage; 034 035 036 037 /** 038 * Privater Konstruktor, der als Eingabe die TLD als File Objekt erhaelt. 039 * @param saxParser String Klassenpfad zum Sax Parser. 040 * @param file File Objekt auf die TLD. 041 * @throws IOException 042 * @throws SAXException 043 */ 044 public CacheFactory(InputStream in) throws IOException, SAXException { 045 super(); 046 init(in); 047 } 048 049 /** 050 * Generelle Initialisierungsmetode der Konstruktoren. 051 * @param saxParser String Klassenpfad zum Sax Parser. 052 * @param is InputStream auf die TLD. 053 * @throws SAXException 054 * @throws IOException 055 */ 056 protected void init(InputStream in) throws IOException, SAXException { 057 Reader r=null; 058 try { 059 InputSource is=new InputSource(in); 060 061 xmlReader=XMLUtil.createXMLReader(DEFAULT_SAX_PARSER); 062 xmlReader.setContentHandler(this); 063 xmlReader.setErrorHandler(this); 064 xmlReader.parse(is); 065 066 } 067 finally { 068 Util.closeEL(r); 069 } 070 } 071 072 @Override 073 public final void startElement(String uri, String name, String qName, Attributes atts) { 074 inside=qName; 075 076 if(qName.equalsIgnoreCase("cacheConfiguration")) insideCacheConfiguration=true; 077 else if(qName.equalsIgnoreCase("statistics")) insideStatistics=true; 078 079 //doStartElement(uri, name, qName, atts); 080 } 081 082 083 084 085 @Override 086 public final void endElement(String uri, String name, String qName) throws SAXException { 087 _setContent(content.toString().trim()); 088 content=new StringBuffer(); 089 inside=""; 090 091 if(qName.equalsIgnoreCase("cacheConfiguration")) insideCacheConfiguration=false; 092 else if(qName.equalsIgnoreCase("statistics")) insideStatistics=false; 093 //doEndElement(uri, name, qName); 094 } 095 096 097 098 private void _setContent(String value) { 099 100 /*if(insideError && insideMessage) { 101 throw new SAXException(value); 102 }*/ 103 setContent(value); 104 105 } 106 107 protected void setContent(String value) { 108 if(insideCacheConfiguration) { 109 if("clearOnFlush".equalsIgnoreCase(inside)) 110 cc.setClearOnFlush(toBooleanValue(value,true)); 111 else if("diskExpiryThreadIntervalSeconds".equalsIgnoreCase(inside)) 112 cc.setDiskExpiryThreadIntervalSeconds(toInt(value,0)); 113 else if("diskPersistent".equalsIgnoreCase(inside)) 114 cc.setDiskPersistent(toBooleanValue(value,false)); 115 else if("diskSpoolBufferSizeMB".equalsIgnoreCase(inside)) 116 cc.setDiskSpoolBufferSize(toInt(value,0)*1024L*1024L); 117 else if("eternal".equalsIgnoreCase(inside)) 118 cc.setEternal(toBooleanValue(value,false)); 119 else if("maxElementsInMemory".equalsIgnoreCase(inside)) 120 cc.setMaxElementsInMemory(toInt(value,0)); 121 else if("maxElementsOnDisk".equalsIgnoreCase(inside)) 122 cc.setMaxElementsOnDisk(toInt(value,0)); 123 else if("name".equalsIgnoreCase(inside)) 124 cc.setName(value); 125 else if("overflowToDisk".equalsIgnoreCase(inside)) 126 cc.setOverflowToDisk(toBooleanValue(value,true)); 127 else if("timeToIdleSeconds".equalsIgnoreCase(inside)) 128 cc.setTimeToIdleSeconds(toInt(value,0)); 129 else if("timeToLiveSeconds".equalsIgnoreCase(inside)) 130 cc.setTimeToLiveSeconds(toInt(value,0)); 131 } 132 else if(insideStatistics){ 133 if("averageGetTime".equalsIgnoreCase(inside)) 134 cs.setAverageGetTime(toDoubleValue(value,0)); 135 else if("cacheHits".equalsIgnoreCase(inside)) 136 cs.setCacheHits(toInt(value,0)); 137 else if("diskStoreSize".equalsIgnoreCase(inside)) 138 cs.setDiskStoreSize(toInt(value,0)); 139 else if("evictionCount".equalsIgnoreCase(inside)) 140 cs.setEvictionCount(toInt(value,0)); 141 else if("inMemoryHits".equalsIgnoreCase(inside)) 142 cs.setInMemoryHits(toInt(value,0)); 143 else if("memoryStoreSize".equalsIgnoreCase(inside)) 144 cs.setMemoryStoreSize(toInt(value,0)); 145 else if("misses".equalsIgnoreCase(inside)) 146 cs.setMisses(toInt(value,0)); 147 else if("onDiskHits".equalsIgnoreCase(inside)) 148 cs.setOnDiskHits(toInt(value,0)); 149 else if("size".equalsIgnoreCase(inside)) 150 cs.setSize(toInt(value,0)); 151 else if("statisticsAccuracy".equalsIgnoreCase(inside)) 152 cs.setStatisticsAccuracy(value); 153 } 154 else{ 155 //System.err.println(inside+":"+value); 156 } 157 } 158 159 160 @Override 161 public void characters (char ch[], int start, int length) { 162 content.append(new String(ch,start,length)); 163 } 164 165 166 167 /** 168 * @return the cc 169 */ 170 public CacheConfiguration getCacheConfiguration() { 171 return cc; 172 } 173 174 private boolean toBooleanValue(String str, boolean defaultValue) { 175 str=str.trim().toLowerCase(); 176 if("true".equalsIgnoreCase(str)) return true; 177 else if("false".equalsIgnoreCase(str)) return false; 178 return defaultValue; 179 } 180 181 182 private double toDoubleValue(String str, int defaultValue) { 183 try{ 184 return Double.parseDouble(str); 185 } 186 catch(Throwable t){ 187 return defaultValue; 188 } 189 } 190 private int toInt(String str, int defaultValue) { 191 try{ 192 return Integer.parseInt(str); 193 } 194 catch(Throwable t){ 195 return defaultValue; 196 } 197 } 198 199 public CacheMeta getMeta() { 200 return new CacheMeta(cc,cs); 201 } 202 }