{"record":{"id":"8ed41d9fea02023e","repo":"symfony/http-kernel","slug":"the-value-of-the-if-option-of-the-s-attribute-must-evaluate","errorCode":null,"errorMessage":"The value of the \"$if\" option of the \"%s\" attribute must evaluate to a boolean, \"%s\" given.","messagePattern":"The value of the \"\\$if\" option of the \"(.+?)\" attribute must evaluate to a boolean, \"(.+?)\" given\\.","errorType":"exception","errorClass":"TypeError","httpStatus":null,"severity":"error","filePath":"EventListener/CacheAttributeListener.php","lineNumber":139,"sourceCode":"                KernelEvents::RESPONSE => ['onKernelResponse', -10],\n            ];\n        }\n\n        return [\n            KernelEvents::CONTROLLER_ARGUMENTS.'.'.Cache::class => 'onKernelControllerAttribute',\n            KernelEvents::RESPONSE.'.'.Cache::class => 'onKernelControllerAttribute',\n        ];\n    }\n\n    public function reset(): void\n    {\n    }\n\n    private function processAttributeBeforeController(Cache $cache, Request $request, ControllerArgumentsEvent $event): void\n    {\n        if (!\\is_bool($cache->if)) {\n            if (!\\is_bool($if = $this->evaluate($cache->if, $cache->variables))) {\n                throw new \\TypeError(\\sprintf('The value of the \"$if\" option of the \"%s\" attribute must evaluate to a boolean, \"%s\" given.', Cache::class, get_debug_type($if)));\n            }\n\n            $cache->if = $if;\n        }\n\n        if (!$cache->if) {\n            return;\n        }\n\n        $response = null;\n\n        if (null !== $cache->lastModified && !$cache->lastModified instanceof \\DateTimeInterface) {\n            $lastModified = $this->evaluate($cache->lastModified, $cache->variables);\n            ($response ??= new Response())->setLastModified($lastModified);\n            $cache->lastModified = $lastModified;\n        }\n\n        if (null !== $cache->etag) {","sourceCodeStart":121,"sourceCodeEnd":157,"githubUrl":"https://github.com/symfony/http-kernel/blob/aa3a39d7286a62cdfea98f0e69c651a3da6e36cf/EventListener/CacheAttributeListener.php#L121-L157","documentation":"The Cache attribute listener resolves the \"$if\" option before the controller runs. If \"if\" is not already a boolean, it is evaluated as an expression; when the evaluation result is not bool, a TypeError is thrown naming the actual type found.","triggerScenarios":"A controller or action annotated with #[Cache(if: ...)] whose expression evaluates to a non-boolean (e.g. a string, int, or null returned by the expression), dispatched via onKernelControllerAttribute/onKernelControllerArguments.","commonSituations":"Typo in expression referencing an undefined variable that evaluates to null; writing if: '1' instead of a real boolean expression; expression returning the request method string instead of a comparison.","solutions":["Fix the expression so it returns a boolean, e.g. #[Cache(if: \"request.headers.has('Authorization')\")].","Pass a literal bool to the if option: #[Cache(if: true)].","Wrap the expression in an explicit comparison (a == b) rather than returning a raw value."],"exampleFix":"// before\n#[Cache(if: 'request.getMethod()')]\n// after\n#[Cache(if: \"request.getMethod() == 'POST'\")]","handlingStrategy":"type-guard","validationCode":"$if = $cache->if;\nif (!is_bool($if) && !is_bool(@eval || null)) { /* validate expression returns bool before applying attribute */ }","typeGuard":"function isBoolExpr(mixed $v): bool { return is_bool($v); }","tryCatchPattern":"try { $listener->onKernelControllerAttribute($event, 'kernel.controller', ...); } catch (\\TypeError $e) { $logger->error('Bad Cache if-expression: '.$e->getMessage()); }","preventionTips":["Always write if-expressions as explicit boolean comparisons","Prefer literal booleans when the condition is static","Unit-test attribute expressions to confirm bool return type"],"tags":["type-mismatch","cache-attribute","symfony"],"backgroundTag":"invalid-argument-value","analyzedSha":"aa3a39d7286a62cdfea98f0e69c651a3da6e36cf","analyzedAt":"2026-09-13T18:03:36.509Z","contentChangedAt":"2026-09-13T18:03:36.509Z","schemaVersion":2},"datasetVersion":"2026-09-16T09:17:16.951Z"}