1 29 package jegg.impl; 30 31 import java.io.File ; 32 import java.io.FileInputStream ; 33 import java.io.FileNotFoundException ; 34 import java.io.IOException ; 35 import java.io.InputStream ; 36 import java.util.HashMap ; 37 import java.util.Iterator ; 38 import java.util.Map ; 39 import java.util.Properties ; 40 41 import javax.xml.parsers.ParserConfigurationException ; 42 43 44 45 import org.apache.commons.logging.Log; 46 import org.apache.commons.logging.LogFactory; 47 import org.xml.sax.Attributes ; 48 import org.xml.sax.InputSource ; 49 import org.xml.sax.SAXException ; 50 import org.xml.sax.SAXParseException ; 51 import org.xml.sax.helpers.DefaultHandler ; 52 53 58 public class AppXMLContentHandler extends DefaultHandler 59 { 60 private static final Log LOG = LogFactory.getLog(AppXMLContentHandler.class); 61 62 private static final String BASKET = "basket"; 64 private static final String EGG = "egg"; 65 private static final String USES = "uses"; 66 private static final String INCLUDE = "include"; 67 private static final String VAR = "var"; 68 private static final String PROPERTY = "property"; 69 70 private static final String NAME = "name"; 72 private static final String HANDLER = "handler"; 73 private static final String LOAD = "load"; 74 private static final String VALUE = "value"; 75 76 private static final String EARLY = "early"; 78 private static final String LATE = "late"; 79 80 private Map _environment; 81 private boolean _resolve; 82 83 private String _currentDispatcherName; 84 private EggInfo _currentEgg; 85 private String _currentInclude; 86 private Map _currentVars = new HashMap (); 87 88 public AppXMLContentHandler(final Map vars, final boolean resolve) 89 { 90 if (null != vars) 91 { 92 _environment = new HashMap (); 93 _environment.putAll(vars); 94 } 95 _resolve = resolve; 96 } 97 98 public void warn(SAXParseException e) 99 { 100 LOG.warn(e); 101 } 102 103 public void error(SAXParseException e) 104 { 105 LOG.error(e); 106 } 107 108 public void fatalError(SAXParseException e) 109 { 110 LOG.fatal(e); 111 } 112 113 public void startDocument() throws SAXException 114 { 115 try 116 { 117 HenHouse.getHenHouse().hatch("root-port-registry", "jegg.impl.PortRegistry", null, true, false); 118 } 119 catch (HatchException e) 120 { 121 throw new SAXException ("unable to create root port registry"); 122 } 123 } 124 125 public void startElement(String uri, String localName, String qName, Attributes attributes) 126 throws SAXException 127 { 128 if (LOG.isDebugEnabled()) 129 LOG.debug("startElement (qName=" + qName+")"); 130 131 if (qName.equals(BASKET)) 132 { 133 String name = attributes.getValue(NAME); 136 if (null != name) 137 _currentDispatcherName = expand(name,_environment); 138 else 139 _currentDispatcherName = null; 140 141 if (LOG.isDebugEnabled()) 142 LOG.debug("CurrentDispatcher: " + _currentDispatcherName); 143 _currentEgg = null; 144 } 145 else 146 if (qName.equals(EGG)) 147 { 148 String name = attributes.getValue(NAME); 149 String expandedName = expand(name,_environment); 150 String handlerName = attributes.getValue(HANDLER); 151 String handler = expand(handlerName,_environment); 152 String load = attributes.getValue(LOAD); 153 load = (null == load) ? EARLY : load; 154 155 if (!load.equalsIgnoreCase(EARLY) && 156 !load.equalsIgnoreCase(LATE)) 157 { 158 throw new SAXException ("Invalid 'load' attribute: " +load); 159 } 160 161 if (LOG.isDebugEnabled()) 162 LOG.debug("Creating egg "+expandedName); 163 164 _currentEgg = new EggInfo( 165 expandedName, 166 handler, 167 _currentDispatcherName, 168 (null==load) ? false : load.equalsIgnoreCase(EARLY)); 169 170 HenHouse hh = HenHouse.getHenHouse(); 171 hh.add(_currentEgg); 172 } 173 else 174 if (qName.equals(USES)) 175 { 176 String name = attributes.getValue(NAME); 177 String expandedName = expand(name,_environment); 178 if (LOG.isDebugEnabled()) 179 LOG.debug(_currentEgg.getEggName()+" uses "+expandedName); 180 _currentEgg.addDependency(expandedName); 181 } 182 else 183 if (qName.equals(PROPERTY)) 184 { 185 String propName = attributes.getValue(NAME); 186 String expandedPropName = expand(propName,_environment); 187 String propValue = attributes.getValue(VALUE); 188 String expandedPropValue = expand(propValue,_environment); 189 if (LOG.isDebugEnabled()) 190 LOG.debug("Environment setting: " + expandedPropName+"="+expandedPropValue); 191 _currentEgg.addProperty(expandedPropName, expandedPropValue); 192 } 193 else 194 if (qName.equals(INCLUDE)) 195 { 196 String name = attributes.getValue(NAME); 197 _currentInclude = expand(name,_environment); 198 if (LOG.isDebugEnabled()) 199 LOG.debug("Include name: " +_currentInclude); 200 _currentVars.clear(); 201 if (null != _environment) 202 _currentVars.putAll(_environment); 203 } 204 else if (qName.equals(VAR)) 205 { 206 String varName = attributes.getValue(NAME); 207 String expandedVarName = expand(varName,_environment); 208 String varValue = attributes.getValue(VALUE); 209 String expandedVarValue = expand(varValue,_environment); 210 if (LOG.isDebugEnabled()) 211 LOG.debug("Environment setting: " + expandedVarName+"="+expandedVarValue); 212 _currentVars.put(expandedVarName,expandedVarValue); 213 } 214 } 215 216 public void endElement(String uri, String localName, String qName) throws SAXException 217 { 218 if (LOG.isDebugEnabled()) 219 LOG.debug("endElement (qName=" + qName+")"); 220 221 if (qName.equals(EGG)) 222 { 223 if (_currentEgg.shouldBindEarly()) 224 { 225 try 226 { 227 HenHouse.getHenHouse().hatch(_currentEgg, false, false); 229 } 230 catch (HatchException e) 231 { 232 throw new SAXException (e); 233 } 234 } 235 } 236 else 237 if (qName.equals(INCLUDE)) 238 { 239 InputSource in = null; 240 241 File xml = new File (_currentInclude); 242 if (xml.exists() && xml.canRead()) 243 { 244 try 245 { 246 FileInputStream fis = new FileInputStream (xml); 247 in = new InputSource (fis); 248 } 249 catch (FileNotFoundException e) 250 { 251 throw new SAXException (e); 252 } 253 } 254 else 255 { 256 ClassLoader cl = ClassLoader.getSystemClassLoader(); 258 InputStream is = cl.getResourceAsStream(_currentInclude); 259 if (null != is) 260 in = new InputSource (is); 261 } 262 if (null != in) 263 { 264 if (LOG.isDebugEnabled()) 265 LOG.debug("Loading "+_currentInclude); 266 try { AppRunner.load(in,_currentVars, false); } 267 catch (IOException e) {LOG.error(e); throw new SAXException (e);} 268 catch (ParserConfigurationException e) {LOG.error(e); throw new SAXException (e);} 269 } 270 } 271 } 272 273 public void endDocument() throws SAXException 274 { 275 if (!_resolve) {return;} 276 277 HenHouse henHouse = HenHouse.getHenHouse(); 278 for (Iterator it = henHouse.iterator(); it.hasNext(); ) 279 { 280 EggInfo info = (EggInfo) it.next(); 281 if (info.shouldBindEarly()) 282 { 283 try 284 { 285 henHouse.hatch(info,true, false); 286 } 287 catch (HatchException e) 288 { 289 throw new SAXException (e); 290 } 291 } 292 } 293 294 for (Iterator it = Dispatcher.iterator(); it.hasNext(); ) 296 { 297 Dispatcher d = (Dispatcher) it.next(); 298 if (!d.isAlive()) 299 d.start(); 300 } 301 } 302 303 private static final String BEGIN_TOKEN = "${"; 304 private static final String END_TOKEN = "}"; 305 306 String expand(String raw, Map env) 307 { 308 if (null == raw) {return null;} 309 310 StringBuffer buf = null; 311 int pos = 0; 312 while(true) 313 { 314 int newpos = raw.indexOf(BEGIN_TOKEN, pos); 315 if (0 > newpos) {break;} 316 int end = raw.indexOf(END_TOKEN,newpos+BEGIN_TOKEN.length()); 317 if (0 > end) {break;} 318 if (null == buf) {buf = new StringBuffer ();} 319 buf.append(raw.substring(pos,newpos)); 320 newpos += BEGIN_TOKEN.length(); 321 String key = raw.substring(newpos,end); 322 if (null != env) 323 { 324 String val = (String ) env.get(key); 325 if (null != val) 326 buf.append(val); 327 } 328 pos = end+1; 329 if (pos >= raw.length()) {break;} 330 } 331 332 if (null != buf) 333 { 334 if (pos < raw.length()) 335 { 336 buf.append(raw.substring(pos)); 337 } 338 } 339 return (null == buf) ? raw : buf.toString(); 340 } 341 } 342 | Popular Tags |