spatie/ping
Run ICMP pings from PHP and get structured results instead of raw output. Spatie's package wraps the system ping command and exposes packet loss, response times, connectivity status, and individual ping lines as clean, readable objects.
Architecture fit
new Ping($host), configure via constructor or fluent setters, call run(), receive a PingResult. There is no service provider, facade, config file, or published asset — so it slots into a Laravel codebase as a plain library, not as a framework feature.PingResult with isSuccess(), hasError() backed by a PingError enum, packet-loss/timing accessors, per-line objects, toArray()/fromArray() round-tripping, and IPv4/IPv6 selection. That contract is what makes it usable for dashboards, alerting payloads, and persistence.Integration feasibility
composer require spatie/ping, then wrap it. The only genuine engineering work is the wrapper: a PingProbe interface, a results DTO, and a driver abstraction so the implementation can be swapped without touching call sites.ping binary (Symfony Process is implied by the Symfony 8 support note), which means integration feasibility is really host-environment feasibility: the binary must exist, be executable by the PHP user, and ICMP must be permitted.-4/-6 flag fix (1.2.1), IPv4/IPv6 forcing (1.2.0), broader iputils error-string recognition (1.2.2). Each of those is a real-world portability bug already found and closed — encouraging, but also evidence that output parsing is the fragile surface.Technical risk
iputils/BSD ping. Locale changes, distro differences, BusyBox ping, and non-English locales can silently break statistics extraction. This is the primary risk and it is mitigated only by the error enum, not eliminated.exec/proc_open or lack CAP_NET_RAW. ICMP is frequently blocked outbound by corporate firewalls and security groups. Expect "failed" results that are permission problems, not network problems.ping output is structurally different; assume unsupported until proven.Key questions
ping presence plus exec/proc_open availability and CAP_NET_RAW on each?ping block a worker indefinitely)?2026-10-19 release date accurate, or is it bad metadata that should be discounted when reading the maturity signal?Stack fit
App\Support\Diagnostics (or App\Services\Probe) namespace containing (a) PingProbe interface, (b) SpatiePingProbe implementation, (c) ProbeResult DTO with validation, (d) a PingException mapper that lifts PingError enum cases into domain-meaningful failures (e.g., HostnameNotFound → configuration error, PermissionDenied → infrastructure error).Spatie\Ping\Ping directly.Migration path
exec('ping ...') already exists anywhere in the codebase, replace it opportunistically — that is the clean, low-risk win this package offers (structured output, typed errors, no hand-rolled regex).Compatibility
exec enabled, ICMP permitted to a known-good target) surfaced in the admin diagnostics page. If the check fails, mark the probe driver as unavailable and degrade gracefully rather than logging a flood of false failures.ProbeResult schema before persistence. Treat toArray() as an upstream convenience, not a storage contract — pin the package version and keep upstream keys out of your database columns so a schema change upstream is a one-line mapper change.composer.json and let the wrapper absorb any output-format changes.Sequencing
probe_results table.Maintenance
ping variant change can alter parsed timings without any test catching it in our environment.Support
PingError enum gives us a defensible internal support story: errors are typed and loggable, so on-call can distinguish "host unreachable" from "probe misconfigured" from "environment can't run ping" without reading raw output.Scaling
Failure modes
exec disabled → hard failure on every call. Detected by the boot-time capability check; must degrade, not crash.CAP_NET_RAW / setuid → "permission denied" surfaced as a generic error; map explicitly so it pages infra, not network.ping without a hard process timeout can occupy a queue worker indefinitely. Enforce a hard timeout at the process level and in the job's $timeout, and set job retry/maxExceptions conservatively.packetLossPercentage() returns plausible-but-wrong numbers, or isSuccess() disagrees with the actual outcome. Never alert on single-sample derived metrics; require N consecutive failures, and sanity-check parsed values (received ≤ transmitted, timings non-negative).HostnameNotFound in a distinct alerting bucket from unreachability, otherwise you page the network team for a typo'd config value.IpVersion::Auto may pick IPv6 on a host without working IPv6 egress; default to IPv4 explicitly unless there's a reason not to.Ramp-up
skipOnGitHubActions pattern — unit-test parsing against recorded raw output fixtures, never real network calls in CI. Real pings belong in a separate, non-blocking integration suite.How can I help you explore Laravel packages today?