lakebase_tokenizer

Rozszerzenie dodaje lakebase_tokenizer konfigurowalną tokenizację do pełnotekstowego wyszukiwania PostgreSQL w Lakebase, w tym całkowite przetwarzanie słów oraz analizę morfologiczną dla tekstów chińskich, japońskich i koreańskich (CJK). Konfiguracje wyszukiwania tekstowego zbudowane na tym rozszerzeniu działają z to_tsvectoroperatorem @@ , funkcjami rankingu oraz indeksami GIN. Możesz też użyć wygenerowanych tsvector wartości z do lakebase_text rankingu BM25.

Rozszerzenie udostępnia szablony tokenizer_wholeword i tokenizer_morph poprzez standardowy interfejs słownika tekstowego PostgreSQL. Zastosowanie tokenizer_wholeword do przetwarzania słów całowartościowych, w tym normalizacji, słów stop, synonimów oraz angielskiego stemmingu. Zastosowanie tokenizer_morph do analizy morfologicznej CJK.

Install

Zainstaluj rozszerzenie w swojej bazie danych. Przykłady na tej stronie wykorzystują dedykowany schemat, aby ułatwić identyfikację obiektów rozszerzenia:

CREATE SCHEMA IF NOT EXISTS tokenizer_ext;
CREATE EXTENSION IF NOT EXISTS lakebase_tokenizer WITH SCHEMA tokenizer_ext;

Przedłużenie jest możliwe do przeniesienia. Możesz zastąpić tokenizer_ext go innym schematem podczas instalacji.

Uaktualnianie rozszerzenia

Nowa wersja Lakebase Search może dodać funkcje, poprawki i poprawę wydajności. PostgreSQL nie aktualizuje automatycznie zainstalowanej wersji rozszerzenia. Sprawdź zainstalowane i najnowsze dostępne wersje:

SELECT installed_version, default_version
FROM pg_available_extensions
WHERE name = 'lakebase_tokenizer';

Zaktualizuj rozszerzenie do najnowszej dostępnej wersji:

ALTER EXTENSION lakebase_tokenizer UPDATE;

ALTER EXTENSION nie regeneruje wartości zapisanych ani tsvector nie buduje zależnych GIN ani lakebase_bm25 indeksów. Jeśli aktualizacja zmieni wyjście tokenizacji, odgeneruj tsvector zapisane wartości i postępuj zgodnie z notatkami dotyczącymi wydania w celu wymaganej konserwacji indeksu.

Aktualizacja z 0.1.x do 0.2.0 nie zmienia wychodu tokenizacji. Wersja 0.2.0 dodaje tokenizer_morph szablon i wbudowane konfiguracje CJK, pozostawiając istniejące konfiguracje bez zmian, więc nie musisz generować wartości ani przebudowywać tsvector indeksów.

Szybki start

Wybierz ścieżkę w oparciu o język tekstu:

  • Dla angielskiego i innych języków wydzielonych odstępami białymi spacjami stwórz słownik na podstawie szablonu tokenizer_wholeword .
  • W przypadku tekstów chińskich, japońskich lub koreańskich używaj wbudowanej konfiguracji. Nie musisz tworzyć słownika.

Tekst całodłowy

Poniższy przykład tworzy słownik z szablonu tokenizer_wholeword , a następnie mapuje na niego typowe typy tokenów PostgreSQL w konfiguracji wyszukiwania tekstowego:

CREATE TEXT SEARCH DICTIONARY documents_dict (
  TEMPLATE          = tokenizer_ext.tokenizer_wholeword,
  Lowercase         = 'true',
  StripAccents      = 'true',
  Stemmer           = 'english'
);

CREATE TEXT SEARCH CONFIGURATION documents_cfg (COPY = pg_catalog.simple);

ALTER TEXT SEARCH CONFIGURATION documents_cfg
  ALTER MAPPING FOR asciiword, word, numword, hword_numpart, hword_part, hword_asciipart
  WITH documents_dict;

Użyj konfiguracji do wygenerowania , tsvectorutworzenia indeksu GIN i wykonywania pełnotekstowych zapytań:

CREATE TABLE documents (
  id            BIGSERIAL PRIMARY KEY,
  body          TEXT NOT NULL,
  search_vector TSVECTOR GENERATED ALWAYS AS (
    to_tsvector('documents_cfg', body)
  ) STORED
);

INSERT INTO documents (body) VALUES
  ('Cats are running near the café.'),
  ('A dog is sleeping in the house.');

CREATE INDEX documents_search_idx ON documents USING gin (search_vector);

SELECT id, body
FROM documents
WHERE search_vector @@ plainto_tsquery('documents_cfg', 'running café');

Używaj tej samej konfiguracji wyszukiwania tekstowego dla dokumentów i zapytań, aby obie strony stosowały tę samą strategię i opcje tokenizacji.

Tekst CJK

Instalacja rozszerzenia tworzy tokenizer_chinesekonfiguracje , tokenizer_japanese, oraz tokenizer_korean wyszukiwania tekstowego. Użyj jednego z nich bezpośrednio, aby wygenerować , tsvectorutworzyć indeks GIN i uruchomić pełnotekstowe zapytania:

Chinese

CREATE TABLE chinese_documents (
  id            BIGSERIAL PRIMARY KEY,
  body          TEXT NOT NULL,
  search_vector TSVECTOR GENERATED ALWAYS AS (
    to_tsvector('tokenizer_ext.tokenizer_chinese', body)
  ) STORED
);

INSERT INTO chinese_documents (body) VALUES
  ('现代分布式文件系统架构');

CREATE INDEX chinese_idx ON chinese_documents USING gin (search_vector);

-- The built-in Chinese configuration uses mixed mode, so use plainto_tsquery instead of to_tsquery.
SELECT id, body
FROM chinese_documents
WHERE search_vector @@ plainto_tsquery('tokenizer_ext.tokenizer_chinese', '现代分布式');

Japoński

CREATE TABLE japanese_documents (
  id            BIGSERIAL PRIMARY KEY,
  body          TEXT NOT NULL,
  search_vector TSVECTOR GENERATED ALWAYS AS (
    to_tsvector('tokenizer_ext.tokenizer_japanese', body)
  ) STORED
);

INSERT INTO japanese_documents (body) VALUES
  ('関西国際空港へのアクセス');

CREATE INDEX japanese_idx ON japanese_documents USING gin (search_vector);

SELECT id, body
FROM japanese_documents
WHERE search_vector @@ to_tsquery('tokenizer_ext.tokenizer_japanese', '関西国際空港');

Koreański

CREATE TABLE korean_documents (
  id            BIGSERIAL PRIMARY KEY,
  body          TEXT NOT NULL,
  search_vector TSVECTOR GENERATED ALWAYS AS (
    to_tsvector('tokenizer_ext.tokenizer_korean', body)
  ) STORED
);

INSERT INTO korean_documents (body) VALUES
  ('선생님께서 도서관에 갑니다');

CREATE INDEX korean_idx ON korean_documents USING gin (search_vector);

SELECT id, body
FROM korean_documents
WHERE search_vector @@ to_tsquery('tokenizer_ext.tokenizer_korean', '선생님께서');

Szablon: tokenizer_wholeword

Jak to działa

Dla każdego tokena przekazanego słownikowi przez parser tokenizer_wholeword tekstu PostgreSQL stosuje się następujące operacje:

  1. Lowercase: Przekonwertuj token na małe litery.
  2. Normalize: Zastosuj normalizację Unicode.
  3. StripAccents: Usuń akcenty.
  4. EnglishPossessive: Usuń angielski przyrostek dzierżawczy, gdy przynajmniej jeden znak pozostaje.
  5. Stopwords: Nie emituj leksemu i przerywa przetwarzanie, jeśli token odpowiada skonfigurowanemu słowu stop. Token jest pomijany z generowanego tsvector.
  6. Synonyms: Emituj skonfigurowaną zamiennicę i zakończ przetwarzanie, jeśli token odpowiada synonimowi.
  7. Stemmer: Jeśli nie dopasuje się synonimu i jest włączone stemming, zastosuj angielski stemmer.

Dodaj słowa stopowe i synonimy

Szablon tokenizer_wholeword może ładować niestandardowe słowa stopowe i synonimy z tabel lakebase_tokenizer_stopwords SQL zarządzanych przez rozszerzenia oraz lakebase_tokenizer_synonyms. Kolumna grupuje name wiersze w zbiór, który wybierasz za pomocą Stopwords opcji słownika lub Synonyms (al).

INSERT INTO tokenizer_ext.lakebase_tokenizer_stopwords (name, word) VALUES
  ('app_stopwords', 'the'),
  ('app_stopwords', 'and'),
  ('app_stopwords', 'or');

INSERT INTO tokenizer_ext.lakebase_tokenizer_synonyms (name, word, synonym) VALUES
  ('app_synonyms', 'usa', 'united_states'),
  ('app_synonyms', 'uk', 'united_kingdom');

Odwołuj się do zbiorów podczas tworzenia lub modyfikowania słownika tokenizer_wholeword :

ALTER TEXT SEARCH DICTIONARY documents_dict (
  Stopwords = 'app_stopwords',
  Synonyms  = 'app_synonyms'
);

Rozszerzenie porównuje słowa stopowe i słowa źródłowe synonimów z każdym tokenem po zastosowaniu , , , i EnglishPossessive, ale przed zastosowaniem Stemmer. StripAccentsNormalizeLowercase Wpisy katalogowe nie są automatycznie przekształcane, więc przechowują je dokładnie w formie wygenerowanej przez te dostępne opcje:

  • Przy Lowercase = 'true', używaj wpisów małej litery. Przy , wielka litera musi odpowiadać Lowercase = 'false'tokenowi.
  • Przy Normalize włączonym zapisz wpisy w wybranym formularzu normalizacji Unicode.
  • Z , przechowuj StripAccents = 'true'formę z akcentem bez akcentu. Na przykład, przechowuj cafe tak, aby pasować café.
  • Przechowaj formularz przed wyciągnięciem stema. Na przykład, z , Stemmer = 'english'run wpis nie pasuje do running. Dodaj running do filtrowania lub zamień ten token.

Nazwy zbiorów mogą zawierać do 256 bajtów. Słowa i synonimy mogą zawierać do 1024 bajtów. Każdy nazwany zestaw słów stopowych lub synonimów może zawierać do 100 000 wierszy.

Zastępowanie synonimu jest emitowane dokładnie tak, jak zostało zapisane i nie jest przetwarzane przez stemmer. Synonimy wspierają jedno zastąpienie dla każdego słowa źródłowego. Aby przedstawić wielowyrazowe zastąpienie jako jeden leksem, użyj separatora, takiego jak podkreślenie, jak w united_states.

Po zmianie zbioru właściciel każdego słownika, który się do niego odwołuje, musi uruchomić no-op ALTER TEXT SEARCH DICTIONARY , aby wymusić przeładowanie:

ALTER TEXT SEARCH DICTIONARY documents_dict (dummy);

Opcja dummy nie istnieje na .tokenizer_wholeword Pominięcie wartości prosi PostgreSQL o usunięcie tej nieistniejącej opcji, co unieważnia pamięć podręczną bez zmiany żadnych skonfigurowanych opcji słownika.

Po ponownym załadowaniu słownika wygeneruj zapisane tsvector wartości, przepisując wiersze źródłowe:

UPDATE documents SET body = body;

Role i dostęp

Użyj dwóch ról, aby oddzielić dostęp aplikacji od administracji tokenizerów:

  • app_role korzysta z istniejących słowników. Potrzebuje USAGE odpowiednich schematów i SELECT tabel katalogowych rozszerzeń, ale nie musi posiadać słowników.
  • tokenizer_admin zarządza zestawami słów stop-word i synonimów, tworzy i posiada słowniki oraz konfiguracje wyszukiwania tekstowego, a po zmianie zestawu uruchamia polecenie reload.

Udziel dostępu do schematu rozszerzenia i tabel katalogowych:

GRANT USAGE ON SCHEMA tokenizer_ext TO app_role, tokenizer_admin;

GRANT SELECT ON
  tokenizer_ext.lakebase_tokenizer_stopwords,
  tokenizer_ext.lakebase_tokenizer_synonyms
TO app_role;

GRANT SELECT, INSERT, UPDATE, DELETE ON
  tokenizer_ext.lakebase_tokenizer_stopwords,
  tokenizer_ext.lakebase_tokenizer_synonyms
TO tokenizer_admin;

tokenizer_admin potrzebne CREATE są także w schemacie, gdzie przechowywane są słowniki i konfiguracje wyszukiwania tekstowego. Stwórz te obiekty jako tokenizer_admin, lub przenieś ich własność na nie. Dostęp do zapisu do tabel katalogowych nie daje własności istniejących słowników.

Opcje

Określ tokenizer_wholeword opcje w lub CREATE TEXT SEARCH DICTIONARYALTER TEXT SEARCH DICTIONARY. Nazwy opcji nie rozróżniają wielkości wielkej litery.

Option Typ Wartość domyślna Description
Lowercase boolean true Konwertuje tokeny na małe litery przed zastosowaniem innych operacji. Stemmer = 'english' wymaga Lowercase = 'true'.
Normalize NFC, , NFD, NFKC, NFKDlub none none Stosuje wybrany formularz normalizacyjny Unicode. To kanonizuje reprezentację, ale nie usuwa postaci. Na przykład tworzy prekomponowany NFCé i e następuje równoważnik łączący akcent ostry.
EnglishPossessive boolean true Usuwa kończącą 'ssię , ’s, lub 's gdy przynajmniej jeden znak poprzedza sufiks. Samodzielny przyrostek pozostaje niezmieniony.
StripAccents boolean false Stosuje normalizację NFKD i usuwa znaki łączenia. Na przykład, café staje się cafe. Gdy ta opcja jest włączona, pomijam ją Normalize , ponieważ krok NFKD sprawia, że każda osobna normalizacja Unicode jest zbędna.
Stopwords Nazwa zbioru None Używa nazwanego zbioru z tokenizer_ext.lakebase_tokenizer_stopwords.
Synonyms Nazwa zbioru None Używa nazwanego zbioru zastąpień jeden do jednego z .tokenizer_ext.lakebase_tokenizer_synonyms
Stemmer english None Używa dołączonego angielskiego stemmera Snowball 3.1.0. Pomiń tę opcję wyłączenia stemmingu. Stemmer nie zawiera listy słów stop.

Tabele katalogowe

Stół Columns Description
lakebase_tokenizer_stopwords name text, word text Zbiory oznaczone jako zbiór słów stop dla tokenizer_wholeword. Kluczem podstawowym jest (name, word).
lakebase_tokenizer_synonyms name text, word text, synonym text Sklepy nazywały jedyne zamienniki dla tokenizer_wholeword. Kluczem podstawowym jest (name, word).

Szablon: tokenizer_morph

Szablon tokenizer_morph obsługuje tokenizację tekstów chińskich, japońskich i koreańskich w pełnotekstowym wyszukiwaniu PostgreSQL. Użyj wbudowanej konfiguracji wyszukiwania tekstowego lub zdefiniuj własną, aby kontrolować generowanie terminów.

Jak to działa

tokenizer_morph korzysta z analizatora Lindera z zestawionymi słownikami: Jieba dla chińskiego, IPADIC dla japońskiego oraz MeCab KoDic dla koreańskiego.

W przypadku koreańskich tokenów parserów najpierw tokenizer_morph zastąpi ㆍ (U+318D) granicą tokenów.

Dla każdego tokena przekazanego słownikowi przez parser tokenizer_morph wyszukiwania tekstowego PostgreSQL stosuje się następujące operacje w kolejności:

  1. Normalize: Zastosuj normalizację Unicode do tokena parsera.
  2. Language: Segmentuj token parsera wybranym analizatorem języka.
  3. Filtr symboliczny: Odrzucaj segmenty bez liter i cyfr.
  4. Analiza specyficzna dla języka: Każdy pozostały segment przekształc w zero lub więcej wyrazów, jak opisano poniżej.
  5. Lowercase: Przekonwertuj każdy termin na małe litery.
  6. Stemmer: Jeśli jest to możliwe, terminy rdzeniowe składają się wyłącznie z liter ASCII z zestawionym angielskim stemmerem. Ten krok nie ogranicza kadencji CJK.

Etap analizy specyficzny dla języka stosuje następujące zasady:

Chiński

  • Rozszerzenie podsłów: W mixed trybie dodaj dwuznakowe i trzyznakowe terminy, które zawiera dołączony słownik.

japoński

  • Filtrowanie części mowy: Odrzuć rozpoznane cząstki, czasowniki pomocnicze, spójniki, wypełniacze, dźwięki niewerbalne, symbole niealfabetyczne oraz segmenty oznaczone .その他,間投
  • Konwersja formy podstawowej: Używaj bazowej formy słownikowej każdego pozostałego rozpoznanego segmentu, gdy jest dostępna. W przeciwnym razie zachowaj formę powierzchniową.
  • Filtrowanie słów stop: Usuń termin odpowiadający wbudowanej liście powszechnych japońskich słów funkcyjnych.
  • Pochodzenie katakany: Usuń zakończenie ー z terminu składającego się z co najmniej czterech znaków, których znaki wszystkie mieszczą się w bloku katakany (U+30A0 do U+30FF).

Koreański

  • Dekompozycja: W discard i mixed tryby, podziel rozpoznany złożony, fleksowany lub wstępnie przeanalizowany segment, gdy słownik dostarcza jego składniki. discard emituje składowe zamiast pełnego składnika i mixed emituje oba.
  • Filtrowanie części mowy: Stosuj filtrowanie do całego wyrazu i do każdego składnika osobno. Pomijam terminy oznaczone jako cząstki, końcówki, afiksy, przysłówki, wyznaczniki, wykmiętniki, interpunkcja, symbole lub formy nieanalizowalne.
  • Konwersja w hangulu: Używaj odczytu hangulowego słownika, aby zachować pełny termin, gdy jest dostępny. Komponenty zachowują swoją formę słownikową.

Parser wyszukiwania tekstowego PostgreSQL dzieli tekst na odstępy i interpunkcję przed wywołaniem tokenizer_morph. Każdy token parsera może zawierać do 2046 bajtów, a dłuższe tokeny są pomijane wraz z POWIADOMIENIEM. Większość znaków chińskich, japońskich i koreańskich używa 3 bajtów w UTF-8, więc w wynikach pomija to_tsvector się więcej niż 682 znaki bez odstępów czy interpunkcji.

Obsługiwane języki i tryby

Dostępne tryby zależą od języka. Każdy przykład pokazuje tekst źródłowy → emitowane terminy:

Język Mode Behavior Example
Chinese none Generuje słowa ze standardowej segmentacji bez dodawania krótszych haseł wyszukiwania. 现代分布式文件系统架构 → 现代, 分布式文件系统, 架构
Chinese mixed Zachowa standardową segmentację słów i dodaje krótsze hasła wyszukiwania z dłuższych słów. 现代分布式文件系统架构→ 现代, , , 分布, 分布式, 布式, 文件系统, 分布式文件系统架构
Japoński none Preferuje dłuższe złożenia słownikowe. 関西国際空港へのアクセス → 関西国際空港, アクセス
Japoński discard Wytwarza drobnoziarnisty składniki dla niektórych długich związków, nie zachowując jednocześnie ich pełnej formy. 関西国際空港へのアクセス→ 関西, 国際, , 空港アクセス
Koreański none Składane i odmienne hasła słownikowe pozostają pełne terminy. 한국어 형태소 분석 → 한국어, 형태소, 분석
Koreański discard Gdy forma złożona lub fleksowana może być rozdzielona, emituje jej części zamiast pełnego wyrazu. 한국어 형태소 분석→ 한국, 어, , 형태소,분석
Koreański mixed Gdy forma złożona lub fleksowana może być rozdzielona, emituje zarówno pełny składnik, jak i jego części. 한국어 형태소 분석→ 한국어, 한국, , 어, 형태소, 형태, 소분석

W mixed trybie zapytaj, używając plainto_tsquery. Gdy jedno słowo zapytania generuje wiele leksemów, to_tsquery, websearch_to_tsquery, i łączy phraseto_tsquery je z operatorem <-> , co wymaga sąsiednich pozycji. mixed tryb wstawia dodatkowe pozycje dla dodatkowych wyrazów, więc warunki te mogą pominąć oczekiwane dopasowania. W przypadku zapytań opartych na pozycji zdefiniuj niestandardową konfigurację z lub nonediscard trybem.

Korzystaj z wbudowanych konfiguracji

Instalacja rozszerzenia tworzy następujące konfiguracje wyszukiwania tekstowego:

Configuration Słownik Język Mode
tokenizer_chinese tokenizer_chinese_dict Chinese mixed
tokenizer_japanese tokenizer_japanese_dict Japoński discard
tokenizer_korean tokenizer_korean_dict Koreański discard

Wszystkie trzy słowniki ustawiają Stemmer = 'english' i używają domyślnych Normalize = 'NFKC' oraz Lowercase = 'true'.

Przykłady end-to-end wykorzystujące te konfiguracje można znaleźć w tekście CJK.

Zdefiniuj niestandardową konfigurację

Aby wybrać inny tryb lub zmienić domyślne opcje, stwórz słownik z szablonu tokenizer_morph oraz konfigurację wyszukiwania tekstowego, która przypisuje do niego typy tokenów PostgreSQL, jak pokazano poniżej. Ten przykład wykorzystuje tryb chiński none do zapytań o frazy:

CREATE TEXT SEARCH DICTIONARY chinese_none_dict (
  TEMPLATE = tokenizer_ext.tokenizer_morph,
  Language = 'chinese',
  Mode = 'none',
  Stemmer = 'english'
);

CREATE TEXT SEARCH CONFIGURATION chinese_none_cfg (COPY = pg_catalog.simple);

ALTER TEXT SEARCH CONFIGURATION chinese_none_cfg
  ALTER MAPPING FOR asciiword, word, numword, hword_asciipart, hword_part, hword_numpart
  WITH chinese_none_dict;

SELECT to_tsvector('chinese_none_cfg', '现代分布式文件系统架构')
  @@ phraseto_tsquery('chinese_none_cfg', '分布式文件系统 架构');

Opcje

Określ tokenizer_morph opcje w lub CREATE TEXT SEARCH DICTIONARYALTER TEXT SEARCH DICTIONARY. Nazwy opcji nie rozróżniają wielkości wielkej litery.

Option Typ Wartość domyślna Description
Language chinese, japanese lub korean Required Wybiera analizator specyficzny dla języka.
Mode none, discard lub mixed Required Kontroluje wyniki złożone i podsłowowe. Obsługiwane tryby zależą od : lub dla chińskiego, none lub discard dla japońskiego, oraz none, discard, lub mixed dla koreańskiego.mixednoneLanguage
Normalize NFC, NFKC lub none NFKC Normalizuje tekst przed segmentacją. NFC zachowuje różnice w kompatybilności. Na przykład pełnowymiarowy ABC jest zapisywany przez małą literę do zamiast abc być konwertowany na abc, więc nie jest stemowany.
Lowercase boolean true Konwertyci emitowali leksemy na małe litery. Stemmer = 'english' wymaga Lowercase = 'true'.
Stemmer english None Stems są tylko leksemami złożonymi wyłącznie z liter ASCII. Pomiń tę opcję wyłączenia angielskiego stemmingu.

Używaj rankingu BM25 z lakebase_text

Konfiguracje wyszukiwania tekstowego zbudowane z generują lakebase_tokenizer standardowe wartości PostgreSQL tsvector kompatybilne z .lakebase_text Aby użyć rankingu trafności BM25 i wyszukiwania top-K, stwórz lakebase_bm25 indeks na tej samej tsvector kolumnie. Dla instalacji, tworzenia indeksu i składni zapytań zobacz lakebase_text.

Następne kroki