6th October 2021
PECL's Yaml Way Faster Than Symfony's Yaml
PECL is the PHP Extension Community Library. These extensions are written in C. Symfony is a PHP web application framework written in PHP.
Initially I just wanted to reduce the dependencies in Saaze, so I installed PECL PHP package yaml
. When I compared run-times between the original, "old" Symfony-based Yaml parsing and the new C based Yaml parsing, I noticed that run-time went down from 1.3s to 0.9s. I then found out that more than 40% of the run-time in Saaze is Yaml parsing.
PHP documents an official Yaml parser: yaml_parse. Saaze instead uses the Symfony supplied Yaml parser.
1. Installation. Here are the steps to install the yaml PECL.
- Download latest yaml package from PECL
tar zxf yaml...
- Run
phpize
- Run
./configure
- Run
make
. Library is heremodules/yaml.so
. - Run
make test
. Conducted 74 tests, which all succeeded. - As root copy
modules/yaml.so
to/usr/lib/php/modules
- Edit
/etc/php/php.ini
and addextension=yaml
Now you should see a yaml entry when calling phpinfo()
or php -m
or php -i
.
2. Code changes. I changed function parseEntry()
in Entry.php
and added time measurements:
$t0 = microtime(true);
. . .
$GLOBALS['YamlParser'] += microtime(true) - $t0;
The original call $matter = Yaml::parse($matter);
is changed to $matter = yaml_parse($matter);
. Below dependency is no longer required:
use Symfony\Component\Yaml\Yaml;
3. Performance comparison. Old run-times:
$ time php saaze build
Building static site in /home/klm/tmp/sndsaaze/build...
execute(): filePath=/home/klm/tmp/sndsaaze/content/blog.yml, entries=1, totalPages=11, entries_per_page=30
execute(): filePath=/home/klm/tmp/sndsaaze/content/music.yml, entries=1, totalPages=1, entries_per_page=30
execute(): filePath=/home/klm/tmp/sndsaaze/content/pages.yml, entries=1, totalPages=1, entries_per_page=30
Finished creating 3 collections and 338 entries (1.25 secs / 10.17MB), YamlParser=0.48152208328247, md2html=0.21977066993713, MathParser=0.10401964187622
real 1.31s
user 1.15s
sys 0
swapped 0
total space 0
New run-times:
$ time php saaze build
Building static site in /home/klm/tmp/sndsaaze/build...
execute(): filePath=/home/klm/tmp/sndsaaze/content/blog.yml, entries=1, totalPages=11, entries_per_page=30
execute(): filePath=/home/klm/tmp/sndsaaze/content/music.yml, entries=1, totalPages=1, entries_per_page=30
execute(): filePath=/home/klm/tmp/sndsaaze/content/pages.yml, entries=1, totalPages=1, entries_per_page=30
Finished creating 3 collections and 338 entries (0.88 secs / 10.16MB), YamlParser=0.11651396751404, md2html=0.22396731376648, MathParser=0.10581231117249
real 0.94s
user 0.77s
sys 0
swapped 0
total space 0
Above numbers for the old run-times show a ratio of 0.48/1.25, i.e., roughly 40% of the run-time is Yaml parsing.
4. Caveats. Whenever a new PHP version comes out, you have to re-install the extension. For example, from PHP 8.0 to 8.1 you have to recompile and re-install. Check as below:
$ php -v
PHP Warning: PHP Startup: yaml: Unable to initialize module
Module compiled with module API=20200930
PHP compiled with module API=20210902
These options need to match
in Unknown on line 0
PHP 8.1.2 (cli) (built: Jan 21 2022 18:08:47) (NTS)
Copyright (c) The PHP Group
Zend Engine v4.1.2, Copyright (c) Zend Technologies