package com.yahoo.dtf.streaming; import java.io.ByteArrayInputStream; import java.io.InputStream; import java.net.URI; import java.net.URISyntaxException; import java.util.HashMap; import org.pangu.PanguException; import org.pangu.PanguGen; import org.pangu.XSDCompiler; import com.yahoo.dtf.DTFNode; import com.yahoo.dtf.NodeShutdownHook; import com.yahoo.dtf.actions.Action; import com.yahoo.dtf.exception.ParseException; import com.yahoo.dtf.exception.StorageException; import com.yahoo.dtf.storage.StorageFactory; /** * A simple object pool to keep track of already generated PanguGen objects * and reuse the existing PanguGenThread that is available to save time by not * recompiling the whole XSD as well as not having to start/stop a thread per * PanguInputStream. * * @author rlgomes */ public class PanguGenPool { private static HashMap<Integer, PanguGenerateThread> gens = new HashMap<Integer, PanguGenerateThread>(); static { DTFNode.registerShutdownHook(new NodeShutdownHook() { @Override public void shutdown() { for (PanguGenerateThread pgt : gens.values()) { pgt.cancel(); } } }); } public static PanguGenerateThread checkout(String xsd) throws ParseException { int code = xsd.hashCode(); PanguGenerateThread pgt = null; try { synchronized (gens) { pgt = gens.remove(code); if ( pgt == null ) { InputStream is = null; if ( xsd.startsWith("storage://") ) { StorageFactory sf = Action.getStorageFactory(); is = sf.getInputStream(new URI(xsd)); } else { is = new ByteArrayInputStream(xsd.getBytes()); } PanguGen gen = XSDCompiler.compile(is); pgt = new PanguGenerateThread(gen); pgt.start(); gens.put(code,pgt); } } } catch (StorageException e) { throw new ParseException("Error parsing XSD.",e); } catch (URISyntaxException e) { throw new ParseException("Error parsing XSD.",e); } catch (PanguException e) { throw new ParseException("Error parsing XSD.",e); } return pgt; } public static void checkin(String xsd, PanguGenerateThread pgt) { gens.put(xsd.hashCode(), pgt); } }