Indeksoitu tekstihaku
Indeksoitu tekstihaku on välimuistin lämmittävä versio tekstinhausta. Ensimmäinen kutsu luo levylle tallennuspaikan trigrammeille ja tunnisteiden esiintymille; myöhemmät kutsut käyttävät sitä ohittaakseen tiedostot, joissa kuviota ei selvästikään voi olla. Näin toistuvien kyselyjen viive pienenee huomattavasti suurissa koodivarastoissa ilman taustapalvelua tai tiedostojen muutoksia tarkkailevaa prosessia.
Lämmitetty tekstihakutoiminto sisältää nyt:
- yhden indeksin haku
- toistuva
--index-dirusean indeksin haku - manifestiin perustuva joukkojen haku
- elinkaaren huomioiva vanhentuneiden tietojen käsittely
- suunnittelijan diagnostiikka komennolla
--trace-plan
Indeksi on käytettävissä polussa greph-index CLI sekä facade-metodeissa Greph::buildTextIndex() / Greph::searchTextIndexed().
Indeksin rakentaminen
# Full build at the current directory
./vendor/bin/greph-index build .
# Full build at an explicit root
./vendor/bin/greph-index build path/to/repo
# Use a non-default index directory
./vendor/bin/greph-index build . --index-dir /tmp/greph-index
# Build with an explicit lifecycle policy
./vendor/bin/greph-index build . \
--lifecycle opportunistic-refresh \
--auto-refresh-max-files 32 \
--auto-refresh-max-bytes 1048576
Indeksi tallennetaan oletusarvoisesti polkuun <root>/.greph-index/.
Onnistuneesta rakentamisesta tulostetaan yksirivinen yhteenveto:
Built index for 2547 files in .greph-index (193428 trigrams, +2547 ~0 -0 =0)
Neljä laskuria ilmaisevat lisättyjen, päivitettyjen, poistettujen ja muuttumattomien tiedostojen määrän. Uudessa rakennuksessa lisättyjen laskurin arvo vastaa tiedostojen määrää, ja muiden laskureiden arvo on nolla.
Indeksin päivittäminen
./vendor/bin/greph-index refresh .
refresh käy indeksoidun juuren uudelleen läpi, tiivistää jokaisen tiedoston ja kirjoittaa uudelleen vain ne tietueet, joiden metatiedot ovat muuttuneet. Tulosteessa käytetään samoja neljää laskuria, joten näet tarkasti, mikä muuttui:
Refreshed index for 2547 files in .greph-index (193428 trigrams, +3 ~7 -1 =2536)
Suorita refresh muokattuasi seurattuja tiedostoja, kun käytät manual-refresh. opportunistic-refresh-indekseissä Greph voi päivittää indeksin automaattisesti haun aikana, jos muuttuneiden tiedostojen joukko on riittävän pieni.
Elinkaariprofiilit
Greph ei käytä taustaprosessia. Elinkaariprofiileilla määritetään, miten lämmitetty indeksi toimii lähdepuun muuttuessa:
static: älä koskaan tarkista ajantasaisuutta tai muuta tietoja automaattisestimanual-refresh: tuo vanhentuneet tiedot näkyviin komennonstatstulosteessa, mutta älä koskaan päivitä haun aikanaopportunistic-refresh: päivitä haun aikana vain, jos muuttuneiden tiedostojen määrä alittaa määritetyt raja-arvotstrict-stale-check: hylkää vanhentuneet lämmitetyn indeksin haut päivittämisen sijaan
Tarkista komennolla greph-index stats --dry-refresh, mitä lämmitetty haku tekisi, ennen kuin suoritat sen:
./vendor/bin/greph-index stats . --dry-refresh
Indeksin kyselyt
# Fixed-string search
./vendor/bin/greph-index search -F "function" .
# Case-insensitive whole-word
./vendor/bin/greph-index search -F -i -w "function" .
# Counts
./vendor/bin/greph-index search -F -c "function" .
# Files only
./vendor/bin/greph-index search -F -l "function" .
# Multi-index search
./vendor/bin/greph-index search -F "apply_filters" . \
--index-dir wordpress/.greph-index \
--index-dir wp-content/plugins/my-plugin/.greph-index \
--show-index-origin
# Regex search
./vendor/bin/greph-index search "function\s+\w+" .
# JSON output
./vendor/bin/greph-index search --json -F "function" .
# Planner trace to stderr
./vendor/bin/greph-index search --trace-plan -F "function" .
Valitsinjoukko on sama kuin alkuperäisessä tekstinhaussa. Katso CLIviitteestä täydellinen luettelo.
Jos indeksiä ei ole pyydetyssä sijainnissa, greph-index search antaa virheen. Tämä komento ei siirry automaattisesti indeksoimattomaan hakuun (AST-komennoissa on valinnainen --fallback scan, mutta tekstikomennossa ei). Rakenna indeksi ensin.
Nimetyt indeksijoukot
Jos haet toistuvasti samasta lämmitetystä rakenteesta, käytä manifestia sen sijaan, että toistaisit --index-dir-valitsimia:
{
"name": "wordpress-local",
"indexes": [
{
"name": "core-text",
"root": "wordpress",
"mode": "text",
"lifecycle": "static",
"priority": 100
},
{
"name": "plugin-text",
"root": "wp-content/plugins/my-plugin",
"mode": "text",
"lifecycle": "opportunistic-refresh",
"max_changed_files": 16,
"max_changed_bytes": 262144,
"priority": 200
}
]
}
Tallenna se nimellä .greph-index-set.json ja suorita sitten:
./vendor/bin/greph-index set build
./vendor/bin/greph-index set stats --dry-refresh
./vendor/bin/greph-index set search --show-index-origin -F "apply_filters" .
Indeksin sisältö
Teksti-indeksi on trigrammien ja tunnisteiden esiintymien varasto. Jokaisesta indeksoidusta tiedostosta Greph poimii:
- Trigrammijoukko: tiedoston sisällössä esiintyvät kolmen tavun jonot. Käytetään karkeana esisuodattimena sekä literaali- että regex-kyselyille.
- Tunnisteiden esiintymät: tiedostossa esiintyvät tunnisteen muotoiset tokenit (
[A-Za-z_][A-Za-z0-9_]*). Nopeuttavat kokonaisia sanoja koskevia kyselyjä. - Elinkaaren metatiedot: tallennetut raja-arvot ja vanhentuneiden tietojen tarkistustapa.
- Sisällön metatiedot: koko ja muokkausaika päivityspäätöksiä ja vanhentuneiden tietojen tarkistusta varten.
Kun kysely saapuu, Greph poimii kuviosta vastaavat muodot (trigrammit literaaliosajonoista ja tunnistetokenit kokonaisia sanoja koskevista kuvioista), leikkaa esiintymäjoukot ja lukee uudelleen vain osumien tiedostot. Leikkauksen läpäisseet tiedostot haetaan samalla moottorilla kuin natiivissa tekstihakutilassa.
Joihinkin lämmitetyn haun yhteenvetokyselyihin Greph voi vastata suoraan esiintymätiedoista:
- kokonaisia sanoja koskeva
-l - kokonaisia sanoja koskeva
-L - kokonaisia sanoja koskeva
-q
Näin ehdokastiedostoja ei tarvitse avata uudelleen, kun esiintymätiedot jo osoittavat vastauksen.
Tämä on sama idea kuin ripgrep-toiminnon valinnainen esindeksointi ja codesearchin trigrammi-indeksi, mutta rakennettu erityisesti levylle tallennettuja tietorakenteita varten, joita lämmitetty PHP pystyy hyödyntämään nopeimmin.
Suunnittelijan diagnostiikka
--trace-plan tulostaa lämmitetyn tekstihakusuunnittelijan päätöksen kohteeseen stderr häiritsemättä tavallista tulosvirtaa.
Jäljitys sisältää:
- elinkaariprofiilin
- valittujen tiedostojen määrän
- ehdokkaiden lähteen (
full-scan,trigram-postings,word-postingstaiinvert-scan) - esiintymien hakutermien määrän
- ehdokastiedostojen ja varmennettujen tiedostojen määrät
- suoran yhteenvedon kelpoisuuden
- kyselyvälimuistin kelpoisuuden ja täyttämispäätöksen
Milloin sitä kannattaa käyttää
Indeksoitu tila sopii, kun:
- Haet samasta tietovarastosta monta kertaa peräkkäin (CI-työt, agenttien silmukat, IDE-integraatiot).
- Tietovarasto on niin suuri, että natiivi läpikäynti muodostaa pullonkaulan.
- Kuvioissa on literaaliosajonoja tai tunnistetokeneita, joita indeksi voi käyttää esisuodatukseen.
Natiivi läpikäynti sopii edelleen, kun:
- Haet pienestä tietovarastosta, jossa rakentamiskustannus on suurin.
- Haet kertaluonteisesti polkua, jota et hae uudelleen.
- Tarvitset kaikki osumat yhdellä tilapäisellä suorituksella etkä halua ylläpitää indeksiä.
Julkaistut vertailutulokset README osoittavat lämmitetyn indeksoidun tilan olevan nopeampi kuin sekä rg että grep regex-kyselyissä sekä laskenta-, osumia sisältävien tiedostojen ja osumia sisältämättömien tiedostojen kyselyissä WordPress-aineistolla. Tavallisissa literaalikyselyissä se voittaa grep-toiminnon mutta jää hieman jälkeen rg-toiminnosta.
Käyttö ohjelmallisesti
use Greph\Greph;
use Greph\Text\TextSearchOptions;
use Greph\Index\IndexLifecycleProfile;
// Build once
Greph::buildTextIndex('.', lifecycle: IndexLifecycleProfile::OpportunisticRefresh);
// Refresh after edits
Greph::refreshTextIndex('.');
// Query
$results = Greph::searchTextIndexed(
'function',
'src',
new TextSearchOptions(fixedString: true),
);
searchTextIndexed hyväksyy samat TextSearchOptions kuin natiivi tekstihaku ja palauttaa saman list<TextFileResult>-rakenteen. Käytä usean indeksin tai manifestiin perustuvissa työnkuluissa komentoja searchTextIndexedMany(...) ja searchTextIndexedSet(...).