
# Wydajność

shikiphp przeprowadza rzeczywistą tokenizację TextMate w czystym PHP, dlatego warto uczciwie wyjaśnić, kiedy działa szybko, a kiedy nie.

## Czego oczekiwać

Należy oczekiwać od kilkudziesięciu do kilkuset milisekund na plik, a nie mikrosekund. Tokenizator buforuje skompilowane reguły i skanery, gramatyki są ładowane na żądanie (próbka, która nie korzysta z osadzonego języka, nie wymaga jego dekodowania), a większość wzorców gramatyk przechodzi przez natywne `preg_*` w ścieżce przyspieszonej PCRE, której równoważność została zweryfikowana; pozostałe obsługuje dopasowywanie w czystym PHP (zobacz
[Architektura](https://shikiphp.inline0.dev/pl/docs/architecture#the-scanner-and-its-pcre-fast-path)).

To czasy dla rozgrzanego środowiska, przy pojedynczym wywołaniu, uzyskane w teście wydajnościowym repozytorium
(`bench/bench.php`, motyw `github-dark`) na jednej maszynie, dla plików korpusu mających
około 55 do 105 wierszy:

| Gramatyka | PHP 8.2 | PHP 8.4 |
| --- | --- | --- |
| JSON, YAML | 30–65 ms | 25–45 ms |
| CSS, HTML | 100–120 ms | 80–100 ms |
| Python, Rust, Go, Bash, Markdown | 190–220 ms | 125–175 ms |
| PHP | około 290 ms | około 170 ms |
| TypeScript, TSX | 490–510 ms | 310–370 ms |

Pierwsze wywołanie danego języka w procesie wiąże się też z jednorazowym kosztem wczytania i kompilacji gramatyki: podczas tych samych uruchomień wynosił on od 50–70 ms dla JSON do nieco ponad sekundy dla Markdown. Koszt rośnie wraz ze złożonością gramatyki i rozmiarem danych wejściowych, a wyniki zależą od sprzętu, więc zmierz je we własnym środowisku: w klonie repozytorium uruchom `composer install`, a następnie `composer bench`.

## Zabezpieczenia

Silnik wyrażeń regularnych obejmuje zapamiętywanie nieudanych dopasowań i ochronę przed ReDoS, dzięki czemu patologiczny wzorzec spowalnia działanie zamiast zawieszać program. Można też ograniczyć pracę wykonywaną dla każdego wiersza za pomocą [`tokenizeMaxLineLength`](https://shikiphp.inline0.dev/pl/docs/options#tokenizemaxlinelength). Wiersz o długości równej lub większej od określonej wartości otrzyma pojedynczy zwykły token — to zabezpieczenie przed złośliwymi danymi wejściowymi w jednym wierszu.

## Buforowanie w środowisku produkcyjnym

Niezawodnym sposobem na usunięcie podświetlania ze ścieżki obsługi żądań jest **nie**uruchamianie go przy każdym żądaniu. Podświetlenie tego samego kodu przy tych samych opcjach zawsze daje ten sam wynik HTML, więc można je skutecznie buforować:

- Podświetlaj kod na etapie budowania witryn statycznych i dokumentacji.
- Buforuj wyrenderowany wynik HTML (klucz to kod i opcje) dla fragmentów podanych przez użytkownika lub przechowywanych w bazie danych i używaj go ponownie, dopóki źródło się nie zmieni.

W ramach jednego procesu używaj ponownie pojedynczego modułu podświetlania (fasada `Shikiphp` robi to za Ciebie), aby współdzielić pamięć podręczną gramatyk i motywów między wywołaniami.
