1 16 19 20 package org.apache.xalan.xsltc.dom; 21 22 import java.io.File ; 23 import java.io.PrintWriter ; 24 import java.net.URL ; 25 import java.net.URLConnection ; 26 import java.net.URLDecoder ; 27 import java.util.Date ; 28 import java.util.Hashtable ; 29 30 import javax.xml.parsers.ParserConfigurationException ; 31 import javax.xml.parsers.SAXParser ; 32 import javax.xml.parsers.SAXParserFactory ; 33 import javax.xml.transform.TransformerException ; 34 import javax.xml.transform.sax.SAXSource ; 35 36 import org.apache.xalan.xsltc.DOM; 37 import org.apache.xalan.xsltc.DOMCache; 38 import org.apache.xalan.xsltc.DOMEnhancedForDTM; 39 import org.apache.xalan.xsltc.Translet; 40 import org.apache.xalan.xsltc.runtime.AbstractTranslet; 41 import org.apache.xalan.xsltc.runtime.BasisLibrary; 42 import org.apache.xalan.xsltc.runtime.Constants; 43 import org.apache.xml.utils.SystemIDResolver; 44 45 import org.xml.sax.InputSource ; 46 import org.xml.sax.SAXException ; 47 import org.xml.sax.XMLReader ; 48 49 52 public final class DocumentCache implements DOMCache { 53 54 private int _size; 55 private Hashtable _references; 56 private String [] _URIs; 57 private int _count; 58 private int _current; 59 private SAXParser _parser; 60 private XMLReader _reader; 61 private XSLTCDTMManager _dtmManager; 62 63 private static final int REFRESH_INTERVAL = 1000; 64 65 68 public final class CachedDocument { 69 70 private long _firstReferenced; 72 private long _lastReferenced; 73 private long _accessCount; 74 private long _lastModified; 75 private long _lastChecked; 76 private long _buildTime; 77 78 private DOMEnhancedForDTM _dom = null; 80 81 84 public CachedDocument(String uri) { 85 final long stamp = System.currentTimeMillis(); 87 _firstReferenced = stamp; 88 _lastReferenced = stamp; 89 _accessCount = 0; 90 loadDocument(uri); 91 92 _buildTime = System.currentTimeMillis() - stamp; 93 } 94 95 98 public void loadDocument(String uri) { 99 100 try { 101 final long stamp = System.currentTimeMillis(); 102 _dom = (DOMEnhancedForDTM)_dtmManager.getDTM( 103 new SAXSource (_reader, new InputSource (uri)), 104 false, null, true, false); 105 _dom.setDocumentURI(uri); 106 107 final long thisTime = System.currentTimeMillis() - stamp; 110 if (_buildTime > 0) 111 _buildTime = (_buildTime + thisTime) >>> 1; 112 else 113 _buildTime = thisTime; 114 } 115 catch (Exception e) { 116 _dom = null; 117 } 118 } 119 120 public DOM getDocument() { return(_dom); } 121 122 public long getFirstReferenced() { return(_firstReferenced); } 123 124 public long getLastReferenced() { return(_lastReferenced); } 125 126 public long getAccessCount() { return(_accessCount); } 127 128 public void incAccessCount() { _accessCount++; } 129 130 public long getLastModified() { return(_lastModified); } 131 132 public void setLastModified(long t){ _lastModified = t; } 133 134 public long getLatency() { return(_buildTime); } 135 136 public long getLastChecked() { return(_lastChecked); } 137 138 public void setLastChecked(long t) { _lastChecked = t; } 139 140 public long getEstimatedSize() { 141 if (_dom != null) 142 return(_dom.getSize() << 5); else 144 return(0); 145 } 146 147 } 148 149 152 public DocumentCache(int size) throws SAXException { 153 this(size, null); 154 try { 155 _dtmManager = (XSLTCDTMManager)XSLTCDTMManager.getDTMManagerClass() 156 .newInstance(); 157 } catch (Exception e) { 158 throw new SAXException (e); 159 } 160 } 161 162 165 public DocumentCache(int size, XSLTCDTMManager dtmManager) throws SAXException { 166 _dtmManager = dtmManager; 167 _count = 0; 168 _current = 0; 169 _size = size; 170 _references = new Hashtable (_size+2); 171 _URIs = new String [_size]; 172 173 try { 174 final SAXParserFactory factory = SAXParserFactory.newInstance(); 176 try { 177 factory.setFeature(Constants.NAMESPACE_FEATURE,true); 178 } 179 catch (Exception e) { 180 factory.setNamespaceAware(true); 181 } 182 _parser = factory.newSAXParser(); 183 _reader = _parser.getXMLReader(); 184 } 185 catch (ParserConfigurationException e) { 186 BasisLibrary.runTimeError(BasisLibrary.NAMESPACES_SUPPORT_ERR); 187 System.exit(-1); 188 } 189 } 190 191 194 private final long getLastModified(String uri) { 195 try { 196 URL url = new URL (uri); 197 URLConnection connection = url.openConnection(); 198 long timestamp = connection.getLastModified(); 199 if (timestamp == 0){ if ("file".equals(url.getProtocol())){ 202 File localfile = new File (URLDecoder.decode(url.getFile())); 203 timestamp = localfile.lastModified(); 204 } 205 } 206 return(timestamp); 207 } 208 catch (Exception e) { 210 return(System.currentTimeMillis()); 211 } 212 } 213 214 217 private CachedDocument lookupDocument(String uri) { 218 return((CachedDocument)_references.get(uri)); 219 } 220 221 224 private synchronized void insertDocument(String uri, CachedDocument doc) { 225 if (_count < _size) { 226 _URIs[_count++] = uri; 228 _current = 0; 229 } 230 else { 231 _references.remove(_URIs[_current]); 233 _URIs[_current] = uri; 235 if (++_current >= _size) _current = 0; 236 } 237 _references.put(uri, doc); 238 } 239 240 243 private synchronized void replaceDocument(String uri, CachedDocument doc) { 244 CachedDocument old = (CachedDocument)_references.get(uri); 245 if (doc == null) 246 insertDocument(uri, doc); 247 else 248 _references.put(uri, doc); 249 } 250 251 255 public DOM retrieveDocument(String baseURI, String href, Translet trs) { 256 CachedDocument doc; 257 258 String uri = href; 259 if (baseURI != null && !baseURI.equals("")) { 260 try { 261 uri = SystemIDResolver.getAbsoluteURI(uri, baseURI); 262 } catch (TransformerException te) { 263 } 265 } 266 267 if ((doc = lookupDocument(uri)) == null) { 269 doc = new CachedDocument(uri); 270 if (doc == null) return null; doc.setLastModified(getLastModified(uri)); 272 insertDocument(uri, doc); 273 } 274 else { 276 long now = System.currentTimeMillis(); 277 long chk = doc.getLastChecked(); 278 doc.setLastChecked(now); 279 if (now > (chk + REFRESH_INTERVAL)) { 281 doc.setLastChecked(now); 282 long last = getLastModified(uri); 283 if (last > doc.getLastModified()) { 285 doc = new CachedDocument(uri); 286 if (doc == null) return null; 287 doc.setLastModified(getLastModified(uri)); 288 replaceDocument(uri, doc); 289 } 290 } 291 292 } 293 294 final DOM dom = doc.getDocument(); 296 297 if (dom == null) return null; 300 301 doc.incAccessCount(); 303 final AbstractTranslet translet = (AbstractTranslet)trs; 304 305 translet.prepassDocument(dom); 308 309 return(doc.getDocument()); 310 } 311 312 315 public void getStatistics(PrintWriter out) { 316 out.println("<h2>DOM cache statistics</h2><center><table border=\"2\">"+ 317 "<tr><td><b>Document URI</b></td>"+ 318 "<td><center><b>Build time</b></center></td>"+ 319 "<td><center><b>Access count</b></center></td>"+ 320 "<td><center><b>Last accessed</b></center></td>"+ 321 "<td><center><b>Last modified</b></center></td></tr>"); 322 323 for (int i=0; i<_count; i++) { 324 CachedDocument doc = (CachedDocument)_references.get(_URIs[i]); 325 out.print("<tr><td><a HREF=\""+_URIs[i]+"\">"+ 326 "<font size=-1>"+_URIs[i]+"</font></a></td>"); 327 out.print("<td><center>"+doc.getLatency()+"ms</center></td>"); 328 out.print("<td><center>"+doc.getAccessCount()+"</center></td>"); 329 out.print("<td><center>"+(new Date (doc.getLastReferenced()))+ 330 "</center></td>"); 331 out.print("<td><center>"+(new Date (doc.getLastModified()))+ 332 "</center></td>"); 333 out.println("</tr>"); 334 } 335 336 out.println("</table></center>"); 337 } 338 } 339 | Popular Tags |