1 23 24 package org.apache.slide.search; 25 26 import org.apache.slide.common.Domain; 27 import org.apache.slide.common.Uri; 28 import org.apache.slide.content.NodeRevisionDescriptor; 29 import org.apache.slide.content.NodeRevisionDescriptors; 30 import org.apache.slide.event.*; 31 import org.apache.slide.util.conf.Configurable; 32 import org.apache.slide.util.conf.Configuration; 33 import org.apache.slide.util.conf.ConfigurationException; 34 import org.apache.slide.util.logger.Logger; 35 36 import java.lang.reflect.Method ; 37 import java.util.ArrayList ; 38 import java.util.Enumeration ; 39 import java.util.Iterator ; 40 import java.util.List ; 41 42 45 46 public class IndexTrigger implements EventCollectionListener, Configurable { 47 protected static final String LOG_CHANNEL = IndexTrigger.class.getName(); 48 49 protected List indexers = new ArrayList (); 50 51 public void configure(Configuration configuration) throws ConfigurationException { 52 Enumeration contentIndexers = configuration.getConfigurations("indexer"); 53 while (contentIndexers.hasMoreElements()) { 54 Configuration listenerConfig = (Configuration)contentIndexers.nextElement(); 55 String classname = listenerConfig.getAttribute("classname"); 56 String uri = listenerConfig.getAttribute("uri", null); 57 String contentType = listenerConfig.getAttribute("content-type", null); 58 boolean synchronous = listenerConfig.getAttributeAsBoolean("synchronous", false); 59 try { 60 Class listenerClass = Class.forName(classname); 61 Indexer indexer = null; 62 try { 63 Method getInstanceMethod = listenerClass.getMethod("getInstance", new Class [0]); 64 indexer = (Indexer)getInstanceMethod.invoke(null, null); 65 } catch ( NoSuchMethodException e) { 66 indexer = (Indexer)listenerClass.newInstance(); 67 } 68 if ( indexer instanceof Configurable ) { 69 ((Configurable)indexer).configure(listenerConfig.getConfiguration("configuration")); 70 } 71 addIndexer(indexer, contentType, uri, synchronous); 72 } catch (ClassCastException e) { 73 throw new ConfigurationException("Indexer '"+classname+"' is not of type Indexer", configuration); 74 } catch (Exception e) { 75 throw new ConfigurationException("Indexer '"+classname+"' could not be loaded", configuration); 76 } 77 } 78 } 79 80 public void vetoableCollected(EventCollection collection) throws VetoException { 81 try { 82 triggerIndexers(collection, true); 83 } catch ( IndexException e ) { 84 throw new VetoException(e.getMessage()); 85 } 86 } 87 88 public void collected(EventCollection collection) { 89 try { 90 triggerIndexers(collection, false); 91 } catch ( IndexException e ) { 92 Domain.log("Index might be out of sync! Reason: "+e.getMessage(), LOG_CHANNEL, Logger.CRITICAL); 93 } 94 } 95 96 private synchronized void triggerIndexers(EventCollection collection, boolean synchronous) throws IndexException { 97 ContentEvent[] update = EventCollectionFilter.getChangedContents(collection); 98 for ( int i = 0; i < update.length; i++ ) { 99 Indexer[] indexers = getIndexers(update[i].getRevisionDescriptors(), update[i].getRevisionDescriptor(), synchronous); 100 for ( int j = 0; j < indexers.length; j++ ) { 101 indexers[j].updateIndex(new Uri(update[i].getNamespace(), update[i].getUri()), update[i].getRevisionDescriptor(), update[i].getRevisionContent()); 102 } 103 } 104 ContentEvent[] insert = EventCollectionFilter.getCreatedContents(collection); 105 for ( int i = 0; i < insert.length; i++ ) { 106 Indexer[] indexers = getIndexers(insert[i].getRevisionDescriptors(), insert[i].getRevisionDescriptor(), synchronous); 107 for ( int j = 0; j < indexers.length; j++ ) { 108 indexers[j].createIndex(new Uri(insert[i].getNamespace(), insert[i].getUri()), insert[i].getRevisionDescriptor(), insert[i].getRevisionContent()); 109 } 110 } 111 ContentEvent[] delete = EventCollectionFilter.getRemovedContents(collection); 112 for ( int i = 0; i < delete.length; i++ ) { 113 Indexer[] indexers = getIndexers(delete[i].getRevisionDescriptors(), delete[i].getRevisionDescriptor(), synchronous); 114 for ( int j = 0; j < indexers.length; j++ ) { 115 indexers[j].dropIndex(new Uri(delete[i].getNamespace(), delete[i].getUri()), delete[i].getRevisionDescriptor().getRevisionNumber()); 116 } 117 } 118 } 119 120 private void addIndexer(Indexer indexer, String contentType, String uri, boolean synchronous) { 121 indexers.add(new IndexerMapping(indexer, contentType, uri, synchronous)); 122 } 123 124 private Indexer []getIndexers(NodeRevisionDescriptors descriptors, NodeRevisionDescriptor descriptor, boolean synchronous) { 125 List matchingIndexers = new ArrayList (); 126 for ( Iterator i = indexers.iterator(); i.hasNext(); ) { 127 IndexerMapping mapping = (IndexerMapping)i.next(); 128 if ( mapping.isSynchronous() == synchronous && mapping.matches(descriptors, descriptor)) { 129 matchingIndexers.add(mapping.getIndexer()); 130 } 131 } 132 Indexer[] indexers = new Indexer[matchingIndexers.size()]; 133 return (Indexer [])matchingIndexers.toArray(indexers); 134 }; 135 136 class IndexerMapping { 137 Indexer indexer; 138 String uri, contentType; 139 boolean synchronous; 140 141 public IndexerMapping(Indexer indexer, String contentType, String uri, boolean synchronous) { 142 this.indexer = indexer; 143 this.uri = uri; 144 this.contentType = contentType; 145 this.synchronous = synchronous; 146 } 147 148 public Indexer getIndexer() { 149 return indexer; 150 } 151 152 public boolean isSynchronous() { 153 return synchronous; 154 } 155 156 public boolean matches(NodeRevisionDescriptors descriptors, NodeRevisionDescriptor descriptor) { 157 boolean matching = true; 158 if ( descriptor != null && contentType != null && !descriptor.getContentType().equals(contentType) ) { 159 matching = false; 160 } 161 if ( descriptors != null && uri != null && !descriptors.getUri().startsWith(uri) ) { 162 matching = false; 163 } 164 return matching; 165 } 166 } 167 } | Popular Tags |