Skip to content

InitPHP/PerformanceMeter

InitPHP PerformanceMeter

A zero-dependency, single-class PHP profiler for measuring elapsed time and memory usage between named checkpoints.

CI Latest Stable Version Total Downloads License PHP Version Require

Positioning

PerformanceMeter is intentionally minimal — a single final class with a handful of static methods that works without any other dependency. It exists to fill a specific niche:

Quick, single-file timing checks where pulling in a full profiling library would be overkill.

It is not a replacement for full-featured profilers; it is the cheapest possible thing that lets you answer "how long did this block take and how much memory did it use?".

When to use this

  • One-off benchmarking scripts and microbenchmarks
  • CLI tools and cron jobs where you want a quick elapsed-time print at the end
  • Tutorial / educational code where introducing a heavier dependency would obscure the lesson
  • Library examples and reproduction scripts in bug reports
  • Hot-path probes during local development, when adding a composer require round-trip is friction

When NOT to use this

Need Use instead
Application-level profiling with nested sections, periods, categories symfony/stopwatch
Production profiling, flame graphs, call tree analysis Xdebug profiler, Blackfire, Tideways, SPX
Web request profiling with timeline UI Symfony's WebProfilerBundle, Laravel Telescope, Clockwork
Memory leak hunting with object retention graphs Xdebug + xdebug_debug_zval, or memprof
OpenTelemetry / APM integration open-telemetry/sdk and an APM vendor SDK

If you are reaching for any of the above, this package is not the right tool — and that is by design.

Requirements

  • PHP 8.1 or higher
  • No runtime dependencies

Installation

composer require initphp/performance-meter

You can also include src/PerformanceMeter.php (and src/Exception/PointerNotFoundException.php) manually if you cannot use Composer — the package has no transitive dependencies.

Quick start

require_once 'vendor/autoload.php';

use InitPHP\PerformanceMeter\PerformanceMeter;

PerformanceMeter::setPointer('main');

for ($i = 0; $i <= 1000; $i++) {
    usleep(10);
}

PerformanceMeter::setPointer('mainEnd');

echo PerformanceMeter::elapsedTime('main', 'mainEnd', 3) . ' seconds elapsed' . PHP_EOL;
echo PerformanceMeter::memoryUsage('main', 'mainEnd', 2) . ' memory used' . PHP_EOL;

// Example output:
// 0.015 seconds elapsed
// 0.77KB memory used

Open-ended measurement

When you only pass a starting checkpoint, the second argument defaults to "now":

PerformanceMeter::setPointer('boot');

// ... do work ...

echo PerformanceMeter::elapsedTime('boot') . ' seconds since boot' . PHP_EOL;

mark() alias

mark($name) is a one-to-one alias of setPointer($name) for readers who prefer stopwatch-style vocabulary:

PerformanceMeter::mark('before');
heavy_work();
PerformanceMeter::mark('after');

echo PerformanceMeter::elapsedTime('before', 'after');

More usage patterns — peak memory, comparing two implementations, resetting between runs — live in docs/cookbook.md.

API at a glance

Method Purpose
setPointer(string $name): void Record a checkpoint with the current time + memory. Case-insensitive.
mark(string $name): void Alias of setPointer().
elapsedTime(string $start, ?string $end = null, int $decimal = 4): float Seconds between two checkpoints. $end = null ⇒ "now".
memoryUsage(string $start, ?string $end = null, int $decimal = 2, bool $realUsage = false): string Memory delta, formatted as "x.xxKB" or "x.xxMB".
peakMemoryUsage(int $decimal = 2, bool $realUsage = false): string Peak memory used so far by the process.
has(string $name): bool Whether a checkpoint with that name has been recorded.
getPointers(): array Snapshot copy of every recorded checkpoint.
reset(): void Clear all checkpoints.

elapsedTime() and memoryUsage() throw InitPHP\PerformanceMeter\Exception\PointerNotFoundException when $start (or a non-null $end) does not match a recorded checkpoint.

Full reference with parameter notes, error conditions and runnable examples: docs/api-reference.md.

Documentation

Migrating from v1.x to v2.0

v2.0 is a clean break that fixes real bugs and tightens the API. Most callers only need to upgrade PHP.

Area v1 behaviour v2 behaviour Action
PHP requirement >=7.4 ^8.1 Upgrade your runtime.
Missing $startPoint Silently returned ~0 ("now" – "now") Throws PointerNotFoundException Wrap in try/catch or call PerformanceMeter::has() first.
Missing non-null $endPoint Silently fell back to "now" Throws PointerNotFoundException Same — fix the typo or check with has().
memoryUsage() with a freed-memory delta ≥ 1 MB Reported in KB (broken) Reports correctly in MB with sign No code change; output now matches expectations.
decimal < 0 Accepted, produced odd output Throws InvalidArgumentException Pass decimal >= 0.
Subclassing PerformanceMeter Allowed (pointless — all-static) Blocked (final) Compose, do not inherit.
protected static $pointers Visible to subclasses private Use getPointers() / has() / reset().
New: reset(), has(), peakMemoryUsage(), getPointers() Added Opt-in.

A migration cookbook entry with side-by-side diffs lives in docs/cookbook.md.

Contributing

This package follows the org-wide InitPHP contribution guide — PSR-12, declare(strict_types=1);, PHPStan at the configured level, PHPUnit-tested behaviour changes, Conventional Commits.

Locally:

composer install
composer test         # PHPUnit
composer phpstan      # static analysis
composer cs-check     # coding standards (use cs-fix to apply)
composer qa           # all of the above

CI runs on PHP 8.1 → 8.4 against both highest and lowest installable dependencies.

Security

Please report security issues privately — see the org-wide SECURITY.md. Do not open public issues for vulnerabilities.

Credits

License

Released under the MIT License. Copyright © 2022-2026 InitPHP.

About

Zero-dependency, single-class PHP profiler for measuring elapsed time and memory between named checkpoints. Built for tiny scripts, CLI tools, and reproducers where a real profiler is overkill.

Topics

Resources

License

Code of conduct

Contributing

Security policy

Stars

Watchers

Forks

Packages

 
 
 

Contributors

Languages