Freigeben über


Volltextfeatures in SQL Server “Denali” Teil 1: Eigenschaftssuche und NEAR

In meinem Webcast zu SQL Server “Denali” CTP1 habe ich schon über einige Neuerungen bei der Volltextsuche gesprochen. Bevor ich im nächsten Artikel zu einer wichtigen Neuerung komme, die es in CTP1 noch nicht gab (Semantische Suche) möchte ich hier noch mal eine kleine Zusammenfassung der Neuerungen in der Volltextsuche geben, die bereits in CTP1 enthalten waren:

Eigenschaftssuche (Property Search)

Diese Funktion ermöglicht die Suche nach Dokumenteigenschaften (Titel, Autor usw.), insbesondere in Office-Dokumenten. Damit das funktioniert muss zuerst eine Search Property List angelegt werden (mit CREATE SEARCH PROPERTY LIST), die die zu suchenden Eigenschaften enthält. Dazu müssen die Eigenschaften über ihre GUID (die man z.B. aus der MSDN Dokumentation erhält) geladen werden:

ALTER SEARCH PROPERTY LIST DocumentTablePropertyList

   ADD 'Title'

   WITH ( PROPERTY_SET_GUID = 'F29F85E0-4FF9-1068-AB91-08002B27B3D9', PROPERTY_INT_ID = 2,

      PROPERTY_DESCRIPTION = 'System.Title - Title of the item.' );

Diese Search Property List wird dann einem Volltextindex zugeordnet:

ALTER FULLTEXT INDEX ON Production.Document SET SEARCH PROPERTY LIST DocumentTablePropertyList;

Außerdem müssen natürlich die IFilter für die jeweiligen Dokumenttypen installiert sein, und zwar je nach Serverversion in 32 oder 64 Bit. Die IFilter für die Office 2007/2010 Dateiformate findet man hier (nach der Installation den Server neu starten!). Darüber hinaus muss die Verwendung der IFilter in SQL Server aktiviert werden (EXEC sp_fulltext_service load_os_resources, 1)

Nach dem Hinzufügen der Eigenschaften wird der Volltextindex neu aufgebaut. Danach kann man nach Dokumenteigenschaften suchen:

SELECT Document FROM Production.Document

  WHERE CONTAINS(PROPERTY(Document,'Author'), 'Steffen');

Anpassbares NEAR

Bisher tat das Prädikat NEAR in der Volltextsuche nicht wirklich das, was man erwartet: Es definierte nämlich lediglich, dass die zwei (oder mehr) Begriffe im selben Dokument vorhanden sein müssen, keineswegs dass sie sich auch tatsächlich in einem bestimmten Abstand zueinander befinden müssen. Lediglich auf den Rang des Dokuments in der Ergebnisliste wirkte sich die Nähe der Suchbegriffe aus.

In SQL Server Denali kann man jetzt genau festlegen, wie nahe die Suchwörter sein sollen. So wird hier nach “rear” und “left” mit maximal 3 Worten dazwischen gesucht:

SELECT DocumentNode, DocumentSummary, Document

       FROM Production.Document AS DocTable INNER JOIN

       CONTAINSTABLE(Production.Document, Document, 'NEAR((left, rear), 3)' ) AS KEY_TBL

       ON DocTable.DocumentNode = KEY_TBL.[KEY];

Es ist auch möglich nach mehr als zwei Begriffen zu suchen, dann gibt die Zahl die maximale Anzahl Nicht-Suchbegriffe zwischen dem ersten und dem letzten Suchbegriff an. Die Reihenfolge der Begriffe im Dokument ist nicht wichtig, kann aber mit einem angehängten TRUE erzwungen werden: NEAR((left, rear), 3, TRUE).

Performance

Neben funktionalen Neuerungen in der Volltextsuche wurde auch stark an der Geschwindigkeit und Skalierbarkeit gearbeitet. Ziel ist es, mindestens 100 Millionen Dokumente in einem Volltextindex zu unterstützen. Meine ersten Versuche mit einer Tabelle mit 20 Millionen Zeilen und 19 Volltext-indizierten Spalten waren sehr vielversprechend: ein Satz aus 22 Abfragen hat nur 7-10 Sekunden gebraucht – auf meinem (schnellen) Laptop.

Wichtig ist dabei die Formulierung der Abfragen. Die Abfrage

SELECT '"hemoglob*"', COUNT(*) FROM ft_publications WHERE CONTAINS (*, '"hemoglob*"')

führt zu einem Join zwischen der Basistabelle und dem Volltextindex, was die Abfrage bei großen Ergebnismengen langsam macht. Die inhaltlich gleichwertige Abfrage

SELECT '"hemoglob*"', COUNT(*) FROM CONTAINSTABLE (ft_publications, *, '"hemoglob*"')

ist hingegen unabhängig von der Anzahl gefundener Dokumente schnell (auf meinem Rechner im zweistelligen Millisekundenbereich). Das gilt übrigens auch mit früheren Versionen von SQL Server

Im nächsten Artikel wird es dann um die semantische Suche gehen

Gruß,
Steffen