{"record":{"id":"4ca1a4cebc3f6c41","repo":"phalcon/cphalcon","slug":"classname-does-not-have-any-validator-added","errorCode":null,"errorMessage":"{className} does not have any validator added","messagePattern":"(.+?) does not have any validator added","errorType":"exception","errorClass":"Phalcon\\Filter\\Validation\\Exceptions\\NoValidatorsInComposite","httpStatus":null,"severity":"error","filePath":"phalcon/Filter/Validation/Traits/ValidatorCompositeTrait.zep","lineNumber":42,"sourceCode":"    protected validators = null;\n\n    /**\n     * @return array\n     */\n    public function getValidators() -> array\n    {\n        return (array) this->validators;\n    }\n\n    /**\n     * Executes the validation\n     */\n    public function validate(<\\Phalcon\\Filter\\Validation> validation, var field) -> bool\n    {\n        var validator;\n\n        if unlikely empty this->getValidators() {\n            throw new \\Phalcon\\Filter\\Validation\\Exceptions\\NoValidatorsInComposite(\n                get_class(this)\n            );\n        }\n\n        for validator in this->getValidators() {\n            if validator->validate(validation, field) === false {\n                return false;\n            }\n        }\n\n        return true;\n    }\n}\n","sourceCodeStart":24,"sourceCodeEnd":56,"githubUrl":"https://github.com/phalcon/cphalcon/blob/b7419de9cd0a8a3f48441ead84c9f8415d463e25/phalcon/Filter/Validation/Traits/ValidatorCompositeTrait.zep#L24-L56","documentation":"Composite validators (anything using ValidatorCompositeTrait, e.g. extending Phalcon\\Filter\\Validation\\AbstractValidatorComposite) run an inner list of validators; validate() refuses to run on an empty list and throws Phalcon\\Filter\\Validation\\Exceptions\\NoValidatorsInComposite naming the class (phalcon/Filter/Validation/Traits/ValidatorCompositeTrait.zep:42). The trait property defaults to null, so a subclass that never populates it fails on first use.","triggerScenarios":"A custom composite validator whose constructor/init never assigns $this->validators (or assigns under a typo'd/renamed property), then $validation->add('field', $composite) and $validation->validate() invokes it.","commonSituations":"Copy-pasting a composite class and dropping the constructor wiring; renaming the property during a refactor; validators registered conditionally so a branch skips all adds; upgrading code that relied on an older base class that populated validators differently.","solutions":["Populate the list in the composite's constructor (or init): $this->validators = [new PresenceOf([...]), new Email([...])];","Add a unit test asserting count($composite->getValidators()) > 0 for every composite you define.","Catch NoValidatorsInComposite in your validation harness to fail fast with the class name when wiring is missing."],"exampleFix":"// before\nclass MyComposite extends AbstractValidatorComposite\n{\n    // validators never set -> NoValidatorsInComposite on validate()\n}\n\n// after\nclass MyComposite extends AbstractValidatorComposite\n{\n    public function __construct(array $options = [])\n    {\n        parent::__construct($options);\n        $this->validators = [\n            new PresenceOf(['message' => 'Value required']),\n            new Email(['message' => 'Invalid e-mail']),\n        ];\n    }\n}","handlingStrategy":"validation","validationCode":"$composite = new MyComposite();\nif ($composite->getValidators() === []) {\n    throw new LogicException(get_class($composite) . ' has no validators registered');\n}\n$validation->add('field', $composite);","typeGuard":null,"tryCatchPattern":"use Phalcon\\Filter\\Validation\\Exceptions\\NoValidatorsInComposite;\n\ntry {\n    $validation->validate($_POST);\n} catch (NoValidatorsInComposite $e) {\n    // developer error, not user input error: fix the composite wiring\n    $logger->critical($e->getMessage());\n    throw $e;\n}","preventionTips":["Always assign $this->validators in the composite's constructor or init().","Unit-test count($composite->getValidators()) > 0 for each composite class.","Treat this exception as a wiring bug: it should fail loud in CI, never be caught in production paths."],"tags":["phalcon","validation","composite-validator","configuration"],"backgroundTag":"empty-composite-validator","analyzedSha":"b7419de9cd0a8a3f48441ead84c9f8415d463e25","analyzedAt":"2026-08-21T06:21:18.811Z","schemaVersion":2},"datasetVersion":"2026-08-21T11:28:35.574Z"}