nicodmf/highlight-bundle
Symfony bundle that integrates highlight.php to add syntax highlighting for code snippets. It provides Twig helpers and configurable themes, making it easy to render readable, colorized source code in templates with minimal setup.
Architecture fit: The first thing a TPM must correct in the ticket is the premise: nicodmf/highlight-bundle is a Symfony2 bundle, not a Laravel package. It ships Bundle-class scaffolding, DI extension/config loaders, and a Twig extension, and it targets Symfony2 kernel and container integration points that Laravel does not have. There is no drop-in fit — composer require against a Laravel 10/11 app is expected to fail or conflict. The transferable asset is a design pattern, not code: a Highlighter interface with concrete drivers wrapping external engines (Pygments, GeSHi, GNU highlight), plus a template helper that pipes a code string through them. That is roughly a few hundred lines and is the only part worth reading.
Integration feasibility: Low as a dependency, moderate as a re-implementation. The binding constraint is not Composer — it is the OS-level highlighter binary if we follow the original design. A Laravel-native equivalent is a small internal service: a HighlighterServiceProvider, a Highlighter contract with highlight(string $code, string $language): string, a Blade directive or anonymous component, config/highlight.php for engine/theme/options, and a cached decorator. Two viable engine backends: pure-PHP scrivo/highlight.php (removes the binary, lowest deployment risk) or a shell-out to Pygments/highlight via Laravel's Process facade (best fidelity for exotic languages, adds process-management burden).
Technical risk: High, concentrated in maintenance and security posture rather than capability. Symfony2 is EOL since 2018; the code is PHP 5.x-era (no scalar types, pre-PSR-4 assumptions) and should be assumed incompatible with PHP 8. With 21 stars and zero dependents there is no user base to surface defects, no upstream patch path, and no security response capability — we would be the first production user and the de facto maintainer. Secondary risks: highlighted output rendered unescaped into HTML is a stored-XSS vector for any untrusted snippet; shelling out on user-supplied source raises argument-injection, unbounded-input, and subprocess-timeout concerns; and output markup is engine-specific, so the engine choice silently becomes a rendering contract that is expensive to change later.
Key questions:
scrivo/highlight.php or Shiki satisfy it without a system binary?Stack fit: Treat the repository as a specification for "highlight code inside a template," not as a dependency. The Laravel-side shape is a package-internal service behind an interface: provider binding, config file, Blade component/directive for the DX, and a caching decorator in front of the engine. Every Symfony artifact — Bundle class, DI extension, XML/YAML config, Twig extension — is discarded rather than translated.
Migration path: Do not port the bundle; port the contract. Define highlight(string $code, string $language): string, implement once against scrivo/highlight.php as the default, and keep a Pygments-backed adapter as an optional secondary binding only if a required language is unsupported in pure PHP. If a legacy Symfony2 application in the portfolio already consumes this bundle, isolate that as its own concern with its own owner and retirement plan; it must not influence the Laravel decision.
Compatibility: Target PHP 8.x and Laravel 10/11. Do not force installation with --ignore-platform-reqs — that trades a visible failure today for a silent runtime fatal later. Validate the replacement against the project's PHP constraint, Composer constraints, and CSP posture: prefer class-based output themes with CSS shipped through Vite over inline style= attributes, so a strict style-src policy does not break rendering. Where the output is user-facing, run the highlighted HTML through an HTML sanitizer with an allowlist rather than trusting the engine.
Sequencing:
scrivo/highlight.php and a Shiki/build-time path — and compare output quality, deploy footprint, and CSP impact.hash(code + language + theme + engine version).Maintenance: This is the dominant cost and the reason to decline adoption. An abandoned Symfony2 bundle inside a Laravel codebase is permanent owned debt: no upstream fixes, no PHP 8 support, no security patches, and a maintainer signal (21 stars, 0 dependents) that dependency scanners and internal review boards will flag. A ~300-line internal highlighter on a maintained library is materially cheaper to own over any multi-year horizon than a fork of this bundle — and unlike the fork, it is replaceable.
Support: None available upstream. No issue triage, no compatibility statements, documentation limited to Symfony2-era convention. Internal engineers become the sole support channel for any behavior question; the mitigation is that the replacement is small enough that its behavior is readable in an hour.
Scaling: Highlighting is CPU-bound, and in the binary-backed mode it is process-bound. Each render forks a subprocess, which becomes the bottleneck well before PHP does — process-table pressure, memory spikes on large inputs, and latency tails under concurrency. Mitigation is non-negotiable if highlighting sits on a request path: precompute and persist highlighted HTML at write time (storage blob or a highlighted_html column), cap input size, and prefer the in-process pure-PHP engine. For docs-style content, build-time highlighting removes the concern entirely.
Failure modes: Missing or version-drifted highlighter binary across hosts and container images (silent degradation or 500s); non-zero subprocess exit on unusual encodings or truncated input; subprocess hangs without an explicit timeout; OOM on multi-megabyte snippets; unknown language falling through to an unstyled or, worse, unescaped raw-code path; XSS from highlighted-but-unsanitized untrusted content; and output divergence between environments when binary versions differ across images.
Ramp-up: Low for the replacement — roughly 1–2 engineer-days to build and a half-day to review sanitization and caching behavior; a developer can read the whole concept in under an hour. Moderate-to-wasteful for the original bundle: the Symfony2 idioms (DI extensions, compiler passes, Twig extension registration) are unfamiliar to most Laravel engineers, and the payoff for learning them is nil when the code is being replaced. Budget the spike and the native build, not the port.
How can I help you explore Laravel packages today?