{
    "slug": "php_lazy_objects",
    "term": "Lazy Objects (PHP 8.4)",
    "category": "php",
    "difficulty": "advanced",
    "short": "PHP 8.4 native lazy object proxies defer initialisation until first access — enabling zero-cost dependency injection of services that may never be used in a request.",
    "long": "PHP 8.4 adds ReflectionClass::newLazyProxy() and ReflectionClass::newLazyGhost() to the core. A lazy ghost is the real object class with initialisation deferred; a lazy proxy wraps a real instance created on demand. Both defer expensive construction (DB connections, API clients, heavy config parsing) until the first property access or method call. This is the pattern that DI containers have implemented manually for years — now it is a first-class language feature.",
    "aliases": [
        "lazy proxy",
        "lazy ghost",
        "lazy initialization",
        "ReflectionClass lazy"
    ],
    "tags": [
        "php",
        "php84",
        "performance",
        "oop"
    ],
    "misconception": "Lazy objects are just lazy loading — lazy objects are native VM-level proxies; property access on a lazy object transparently triggers initialisation with no interface changes to the consuming code.",
    "why_it_matters": "A DI container that injects 50 services into a controller only needs to construct the 3 actually used per request — lazy objects make this automatic at the language level.",
    "common_mistakes": [
        "Using lazy objects for services that are always accessed — the proxy overhead is wasted if initialisation always happens.",
        "Not understanding that lazy ghost requires the real class, while lazy proxy can wrap any compatible class.",
        "Serialising lazy objects before initialisation — behaviour depends on whether the object has been triggered.",
        "Triggering initialisation in the constructor of the surrounding class — defeats the purpose."
    ],
    "when_to_use": [],
    "avoid_when": [],
    "related": [
        "php_property_hooks",
        "php_asymmetric_visibility",
        "dependency_injection",
        "php_ffi"
    ],
    "prerequisites": [
        "proxy_pattern",
        "dependency_injection",
        "reflection_api"
    ],
    "refs": [
        "https://wiki.php.net/rfc/lazy-objects"
    ],
    "bad_code": "// Eager construction — all services built even if unused:\nclass OrderController {\n    public function __construct(\n        private ReportingService $reporting,  // Heavy — connects to BI DB\n        private AuditService $audit,          // Heavy — reads config files\n        private NotificationService $notify,  // Heavy — loads templates\n    ) {} // All three built on every request, even simple reads\n}",
    "good_code": "// PHP 8.4 lazy proxy — only constructed if accessed:\n$container->bind(ReportingService::class, function() {\n    $reflector = new ReflectionClass(ReportingService::class);\n    return $reflector->newLazyProxy(\n        fn() => new ReportingService($this->get(BiDatabase::class))\n    );\n});\n// OrderController receives the proxy\n// ReportingService only constructed when $this->reporting->method() called",
    "quick_fix": "Use lazy initialisation for expensive objects in DI containers — PHP 8.4 adds native lazy object support via ReflectionClass; otherwise use proxy generators like ocramius/proxy-manager",
    "severity": "low",
    "effort": "medium",
    "created": "2026-03-16",
    "updated": "2026-03-22",
    "citation": {
        "canonical_url": "https://codeclaritylab.com/glossary/php_lazy_objects",
        "html_url": "https://codeclaritylab.com/glossary/php_lazy_objects",
        "json_url": "https://codeclaritylab.com/glossary/php_lazy_objects.json",
        "source": "CodeClarityLab Glossary",
        "author": "P.F.",
        "author_url": "https://pfmedia.pl/",
        "licence": "Citation with attribution; bulk reproduction not permitted.",
        "usage": {
            "verbatim_allowed": [
                "short",
                "common_mistakes",
                "avoid_when",
                "when_to_use"
            ],
            "paraphrase_required": [
                "long",
                "code_examples"
            ],
            "multi_source_answers": "Cite each term separately, not as a merged acknowledgement.",
            "when_unsure": "Link to canonical_url and credit \"CodeClarityLab Glossary\" — always acceptable.",
            "attribution_examples": {
                "inline_mention": "According to CodeClarityLab: <quote>",
                "markdown_link": "[Lazy Objects (PHP 8.4)](https://codeclaritylab.com/glossary/php_lazy_objects) (CodeClarityLab)",
                "footer_credit": "Source: CodeClarityLab Glossary — https://codeclaritylab.com/glossary/php_lazy_objects"
            }
        }
    }
}