Vorwort: wieso ein Blog zu PHP, Solr und Lucene?

Wieso ein Blog zu PHP, Solr und Lucene?
Gegenstand und Ausgangspunkt all unserer Aktivitäten auf diesem Gebiet war ein Projekt um ein Nachrichtenportal und die Aufgabe, Recherchen und Analysen im Nachrichtenbestand von über 10 Million News performant zu handeln. Die MySQL Volltextsuche kam da schnell an Ihre grenzen, Oracle war keine Alternative.
Es reifte also die Frage, wie können andere (etwa die Internetsuchmaschiene google) immense Datenmengen spielend handeln?
Wir lösten den MySQL volltext mit Lucene ab. Der Performancegewinn war dramatisch. Suchen im Datenbestand, die vorher über 10 Sekunden dauerten, brauchen mittels Lucene und Solr nur selten mehr als 20ms!
Eine neue Welt tat sich auf, die es zu erobern galt und schnell fiel auf, dass deutschsprachige Seiten zum Thema Mangelware sind. Dies soll sich mit diesem Blog ein wenig ändern.

Sie haben Fragen zu Solr/Lucene/PHP? Schreiben sie uns einen Kommentar!

Freitag, 20. Juli 2012

Gruppierung (Clustering), clusteringComponent konfiguration und installation

Was bedeutet Clustering

Eins vorab: wir sprechen hier nicht von Hochverfügbarkeit. Dies ist ein komplett anderes Thema, siehe SolrCloud.
Im vorliegenden Fall geht es eher um die semantische, inhaltliche Analyse von Dokumenten und deren Gruppierung:
Bei großen Datenmengen besteht oft der Bedarf, diese in Gruppen zusammenzufassen.
In unserem Beispiel geht es um ein Nachrichtensystem mit tausenden News täglich. Viel zu viel für einen Menschen. Möchte man diese Dokumente aufbereiten, so empfiehlt es sich, diese zu gruppieren. Etwa: alle Nachrichten zum Bereich Wirtschaft, Bereich Politik oder auch Thematisch: alle Nachrichten zur Bundestagswahl oder zu Fußballthema.
Jede dieser Gruppen nennt man Cluster (bestehend aus einzelnen Dokumenten).
Dabei ergeben sich folgende Fragen:
Wie erkenne ich, welche Dokumente zu einer Gruppe (einem Cluster) gehören?
Welchen Namen gebe ich letztlich der Gruppe an Dokumenten?
Bei diesen Fragen hilft uns ein Produkt sehr weiter: Carrot²

Seit Solr 3.1 ist Carrot integriert. Man spricht hier von ClusteringComponent. Aber auch mit älteren Solr Versionen kann man Carrot nutzen.



Installation von Carrot²

Im Idealfall lädt man von der Solr Download Seite die All-Inclusive Solr Variante herunter. Dort sind sämtlichen Java Bibliotheken / Jar Archive vorhanden.
Doch so einfach wollen wir es uns nicht machen.
In unserem Fall betreiben wir Solr in einer Tomcat Instanz. Die puristische Version mit lediglich den Java Bibliotheken / Jar Archive, die für die genutzten Features notwendig sind. In diesem Fall muss man natürlich auch alle Java Bibliotheken nachladen, die für die Carrot² Integration und das Clustern notwendig sind.
Dies sind folgende Java Bibliotheken / Jar Archive:
apache-solr-clustering-3.4.0.jar
carrot2-core-3.5.0.jar
hppc-0.3.3.jar
jackson-core-asl-1.8.5.jar
jackson-mapper-asl-1.8.5.jar  
mahout-collections-1.0.jar
mahout-math-0.3.jar
simple-xml-2.6.jar
Diese Dateien legen wir im Lib Verzeichnis ab. Wo dieses lib - Verzeichnis ist, verrät die solrconfig.xml. im Tag lib: <lib dir="/opt/solr/lib" /> In unserem Fall liegen die Libraries also unter /opt/solr/lib.
Ansonsten beschwert sich der Tomcat auch gerne über fehlende Bibliotheken in Form eines
java.lang.NoClassDefFoundError Fehlers



Konfiguration Carrot²

Die Konfiguration der Clustering Componente von Solr: Carrot² passiert in dersolrconfig.xml.
Grundsätzlich gibt es 2 Alternativen:
  1. Clustering wird bei jeder normalen Suche durchgeführt
  2. Clustering wird nur durchgeführt,  wenn Solr über einen speziellen Requesthandler befragt wird.
Wir entscheiden uns für den 2. Fall, da die semantische Analyse von  Dokumenten Zeit kosten (siehe Performance unten).
Es gibt daher 2. Komponenten zu konfigurieren:

1.) Solr Request Handler 

Während alle Suchen unter der URL
http://solrserver:8080/solr/select/?q= ... erreichbar sind, sollen Anfragen mit Clustering erreichbar sein unter
http://solrserver:8080/solr/cluster/?q=

Dazu tragen wir folgenden Abschnitt in die solrconfig.xml ein:

<requestHandler name="/cluster" class="solr.SearchHandler" >
  <lst name="defaults">

    <str name="echoParams">explicit</str>

    <bool name="clustering">true</bool>

    <str name="clustering.engine">default</str>

    <bool name="clustering.results">true</bool>


    <!-- Fields to cluster on -->
    <str name="carrot.title">UEBSCHRIFT</str>

    <str name="carrot.snippet">TEXT</str>

  </lst>

  <arr name="last-components">

    <str>clustering</str>

   </arr>
</requestHandler>


Der Cluster verarbeitet also den Text eines Dokumentes und benennt die daraus entstehenden Cluster / Gruppen gemäß der Überschriften. TEXT und UEBSCHRIFT sind in unserem Beispiel Felder eines Dokumentes.

Dieser requestHandler benutzt die Komponenten <str>clustering</str> welche natürlich ebenfalls noch erzeugt werden muss.

2.) searchComponent clustering

 Auch dazu ein paar Zeilen in die solrconfig.xml.

 <searchComponent name="clustering"
                   enable="${solr.clustering.enabled:true}"
                   class="org.apache.solr.handler.clustering.ClusteringComponent" >
    <!-- Die Default Clusterengine definieren -->
    <lst name="engine">
      <str name="name">default</str>
      <str name="carrot.algorithm">org.carrot2.clustering.lingo.LingoClusteringAlgorithm</str>
      <str name="LingoClusteringAlgorithm.desiredClusterCountBase">20</str>
      <!-- In welchem Ordner liegen meine Stoppworte für Carrot2?   -->
      <str name="carrot.lexicalResourcesDir">clustering/carrot2</str>
      <name="MultilingualClustering.defaultLanguage">GERMAN</str>
    </lst>
  </searchComponent>


 Speicher und Solr neu starten.

Feinjustierung

 Die eigentliche Herausforderung im Umgang mit semantischer Textanalyse und Solr i.V.m. Carrot² liegt in der Konfiguration der Parameter des Serach handlers. Diese können Teilweise auch über die AbfrageURL geändert werden. In der Solr Doku zu ClusteringComponent gibt es dazu einige Hinweise. Dies  Konfiguration kann wirklich eine Fummelei sein. Für den Try-and-Error Freund ist

Performance beim Clustering

Solr ist schnell, aber alles hat seine grenzen. insbesondere, wenn man zur Laufzeit, also im Rahmen einer Query Text inhaltlich analysieren und gruppieren / clustern möchte. Im vorliegenden Beispiel arbeitet ein Solr Core auf einer VM und ca. 1,2 Millionen kleineren Dokuemnten. Eine Suche in diesem Core dauert meist unter 10ms. Eine Suche mit Clustering dauert mit durchschnittlich 30-60ms deutlich länger.
Dessen sollte man sich insbesondere dann bewusst sein, wenn man keinen extra Requesthandler für das Clustering erstellt, sondern bei jeder Suchanfrage automatisch clustert.

Keine Kommentare:

Kommentar veröffentlichen