Veiktspējas testi
Etalonuzdevumu ietvars veido stabilu JSON un cilvēkam lasāmu pārskatu. Tas atrodas
bench/ repozitorijā storh un nav bijis daļa no Composer pakotnes kopš 0.5.2, tāpēc tālāk norādītās composer bench* komandas palaižamas tikai no klona, pēc composer install:
composer bench
composer bench -- --dataset=100000 --engine=doc
composer bench -- --dataset=100000 --engine=log
composer bench -- --dataset=100000 --engine=queue
composer bench -- --dataset=100000 --engine=cache --cache-validation=trust
composer bench -- --dataset=100000 --engine=filter
composer bench -- --dataset=1000000 --engine=uuid
composer bench:jit -- --dataset=1000000 --engine=uuid
composer bench:repeat -- --dataset=100000 --engine=doc --repeat=5
composer bench:repeat -- --dataset=1000000 --engine=filter --repeat=5 --memory-limit=512M
composer bench:range -- --datasets=1000,10000,50000,100000
composer bench:range -- --datasets=100000 --engines=cache --memory-limit=512M
composer bench:compare build/bench-main.json build/bench-current.json
composer bench:gate -- build/bench-main.json build/bench-current.json --threshold=10 --metric=doc.put --metric=log.stream
composer bench:ci
Etalonrezultāti
Trīs pilnu etalonuzdevumu ietvara izpildes reižu mediānas, 50,000 ieraksti katram dzinējam, uz Apple M1 Pro (16 GB, macOS 26.5, APFS) ar PHP 8.5 CLI, opcache un JIT izslēgti:
composer bench:repeat -- --dataset=50000 --engine=all --repeat=3 --memory-limit=512M
Katrs ieraksts tiek iztukšots un fsync sinhronizēts, pirms storh ziņo par tā saglabāšanu, tāpēc rakstīšanas ātrumu ierobežo failu sistēma. Lasīšana notiek no operētājsistēmas lapu kešatmiņas. Ātrumi aprēķināti no mediānām; palaidiet composer bench no repozitorija klona, lai pārbaudītu savu aparatūru.
| DocStore, 50k ieraksti | mediāna |
|---|---|
put(), viens noturīgs fails katram ierakstam |
3.3k ieraksti/s |
putStream() lielapjoma ievade |
3.7k ieraksti/s |
importJsonl() |
3.6k ieraksti/s |
get() atsevišķa nolasīšana, STAT pārbaudīta |
5.6 µs |
| esošas krātuves atkārtota atvēršana | 0.26 ms |
indeksēts vienādības vaicājums, limit(100) |
1.1 ms |
indeksēta count() visā kolekcijā |
41 µs |
| indeksa izveide, 2 vienādības + 1 diapazona lauks | 52k ieraksti/s |
pilna stream() ar atkārtotu STAT pārbaudi |
103k ieraksti/s |
exportJsonl() |
104k ieraksti/s |
| SegmentedLog, 50k ieraksti, 16 KB segmenti | mediāna |
|---|---|
put(), fsync pēc katras pievienošanas |
16k pievienošanas/s |
appendStream() lielapjoma ievade |
56k ieraksti/s |
| kursora nolasīšana, 100 ieraksti no viduspunkta | 2.1 ms |
| laika diapazona nolasīšana | 1.1 ms |
vienādības count() |
11 µs |
compact() visi noslēgtie segmenti |
69k ieraksti/s |
| atkārtota atvēršana pēc nepilnīgu beigu datu atkopšanas | 218k ieraksti/s |
Etalonuzdevumā ik pēc 16 KB tiek noslēgts segments, lai pārbaudītu segmentu maiņu; noklusētais segmenta izmērs ir 1 MiB.
| Rinda, 50k uzdevumi | mediāna |
|---|---|
enqueue(), fsync pēc katra notikuma |
22k uzdevumi/s |
claim() |
23k uzdevumi/s |
complete() |
23k uzdevumi/s |
enqueueMany() |
209k uzdevumi/s |
claimMany() |
467k uzdevumi/s |
completeMany() |
512k uzdevumi/s |
| SQL Mirror, SQLite, 50k ieraksti | mediāna |
|---|---|
sākotnējā push() |
61k rindas/s |
push() bez izmaiņām |
86k ieraksti/s |
flush(), 100 ID |
7.1 ms |
indeksēta SQL COUNT spoguļa kopā |
6.9 ms |
rebuild() |
65k rindas/s |
pull() atjaunošana, viens noturīgs fails katram ierakstam |
3.2k ieraksti/s |
| Mikro | mediāna |
|---|---|
kešota get(), auksta, tad silta (MemoryCache, STAT) |
83 µs / 6.3 µs |
| UUIDv7 ģenerēšana | 1.3 µs |
| UUIDv7 pārbaude | 0.30 µs |
| predikātu filtrēšana atmiņā | 4.4M rindas/s |
Aptvertie mērķi:
- DocStore put, straumēšanas put, JSONL eksportēšana/importēšana, get, delete, stream un indeksa izveide
- vienādības, saliktā un diapazona indeksa vaicājumi, sakārtoti diapazoni augošā un dilstošā secībā, indeksēšana pēc skaita, ID meklēšana un neindeksēti DocStore vaicājumi
- SegmentedLog append, straumēšanas append, kursora nolasīšana, laika diapazona nolasīšana, saspiesta laika diapazona nolasīšana, QueryBuilder kursora un ID meklēšana, skaits, lielapjoma append skaits, statistika, saspiešana
- Queue enqueue, lielapjoma enqueue, claim, lielapjoma claim, complete, lielapjoma complete, requeue
- RecordQuery un QueryCondition predikātu filtrēšana atmiņā esošajās rindās
- UUIDv7 monotonā ģenerēšana, ģenerēšana ar izkliedētiem laika zīmogiem, pārbaude un laika zīmoga izgūšana
- nepilnīgas beigu rindas atkopšana
- aukstas un siltas kešatmiņas nolasīšana ar jaukšanas, stat vai uzticamu pārbaudi
Noklusētais izvades ceļš:
build/bench-current.json
Diapazona etalonuzdevumi raksta vienu JSON failu katrai datu kopai un dzinējam mapē
build/bench-ranges/.
bench:gate salīdzina divus etalonuzdevumu JSON failus un izvada statusu, kas nav nulle, ja kāda izsekojamā metrika ir lēnāka par konfigurēto slieksni. Ja netiek norādītas --metric vērtības, tiek pārbaudīta katra bāzes failā esošā metrika.
bench:ci ir GitHub Actions regresiju pārbaudei. Tā palaiž visu dzinēju 1k etalonuzdevumu, salīdzina atlasītās rakstīšanas, lasīšanas, kešatmiņas un UUID metrikas ar izsekoto bench/baselines/ci-1k-all.json bāzes vērtību un izmanto plašu noklusēto slieksni, lai izvairītos no parastajām izpildvides svārstībām, vienlaikus atklājot būtiskas veiktspējas regresijas.
bench:jit palaiž to pašu etalonuzdevumu ietvaru ar iespējotu CLI opcache un izsekošanas JIT, kā arī atspējo Xdebug etalonuzdevuma procesam, lai PHP tiešām varētu ieslēgt JIT.
Izveidotajā JSON ir iekļauti izpildvides karodziņi, kas parāda, vai šajā izpildē opcache un JIT bija aktīvi.