On this page
Profiling
Gacela\Framework\Profiler\Profiler is an in-memory stopwatch for your own code. You mark the operations worth
measuring. It records how long each one took and how much memory the process used when it finished. It is disabled by
default, and while disabled every call on it is a no-op, so instrumentation can stay in place at zero cost.
Recording spans
Enable the profiler early in your bootstrap. Then wrap the code to measure in matching start() / stop() calls with
the same operation and subject:
use Gacela\Framework\Profiler\Profiler;
Profiler::getInstance()->enable();$profiler = Profiler::getInstance();
$profiler->start('db-query', 'users');
$users = $repository->findAll();
$profiler->stop('db-query', 'users');operation:subjectidentifies a span. Different subjects under one operation stay separate entries, and the stats aggregate them per operation.- Nested and recursive spans with the same label work: start times are kept as a stack, so a
stop()closes the span its matchingstart()opened instead of collapsing both into one entry. - A
stop()with no matchingstart()is ignored, since there is no start time to measure from. - Durations come from
hrtime()and are reported in seconds. Each entry also recordsmemory_get_usage(true)at the moment it stopped. disable()drops any span still in flight, so a laterenable()cannot pair a freshstop()with a stale start.reset()clears recorded entries and open spans.
Reading the results
The profiler lives in process memory, so you read the results in the same process that recorded them.
In code, getEntries() returns every recorded span, and getStats() aggregates them:
$stats = Profiler::getInstance()->getStats();
$stats['total_operations']; // int
$stats['total_duration']; // float, seconds
$stats['avg_duration']; // float, seconds
$stats['peak_memory']; // int, bytes
$stats['by_operation']; // per operation: count, total_duration, avg_durationOn the command line, profile:report renders the same data as a table, JSON or summary,
sorted by duration, memory or operation. The profiler is per-process, so the command shows only the spans recorded
during its own run. Enable the profiler and instrument code inside gacela.php or the bootstrap closure: whatever runs
while the command boots appears in the report.
See also
profile:report: output formats and sorting- Events: lifecycle events, the other observability surface, better suited to tracing resolution