{"id":20254743,"url":"https://github.com/chippyash/validation","last_synced_at":"2025-04-11T00:03:54.665Z","repository":{"id":62501794,"uuid":"46469287","full_name":"chippyash/Validation","owner":"chippyash","description":"Complex functional data validation for PHP","archived":false,"fork":false,"pushed_at":"2020-01-04T07:56:30.000Z","size":113,"stargazers_count":0,"open_issues_count":0,"forks_count":2,"subscribers_count":1,"default_branch":"master","last_synced_at":"2025-04-11T00:03:48.668Z","etag":null,"topics":[],"latest_commit_sha":null,"homepage":null,"language":"PHP","has_issues":true,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":null,"license":"bsd-3-clause","status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/chippyash.png","metadata":{"files":{"readme":"README.md","changelog":null,"contributing":null,"funding":null,"license":"LICENSE.md","code_of_conduct":null,"threat_model":null,"audit":null,"citation":null,"codeowners":null,"security":null,"support":null}},"created_at":"2015-11-19T05:16:11.000Z","updated_at":"2025-02-16T03:39:43.000Z","dependencies_parsed_at":"2022-11-02T12:01:26.206Z","dependency_job_id":null,"html_url":"https://github.com/chippyash/Validation","commit_stats":null,"previous_names":[],"tags_count":14,"template":false,"template_full_name":null,"repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/chippyash%2FValidation","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/chippyash%2FValidation/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/chippyash%2FValidation/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/chippyash%2FValidation/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/chippyash","download_url":"https://codeload.github.com/chippyash/Validation/tar.gz/refs/heads/master","host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":248317705,"owners_count":21083528,"icon_url":"https://github.com/github.png","version":null,"created_at":"2022-05-30T11:31:42.601Z","updated_at":"2022-07-04T15:15:14.044Z","host_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub","repositories_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories","repository_names_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repository_names","owners_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners"}},"keywords":[],"created_at":"2024-11-14T10:34:41.777Z","updated_at":"2025-04-11T00:03:54.642Z","avatar_url":"https://github.com/chippyash.png","language":"PHP","funding_links":[],"categories":[],"sub_categories":[],"readme":"# chippyash/validation\n\n## Quality Assurance\n\n![PHP 7.2](https://img.shields.io/badge/PHP-7.2-blue.svg)\n[![Build Status](https://travis-ci.org/chippyash/Validation.svg?branch=master)](https://travis-ci.org/chippyash/Validation)\n[![Test Coverage](https://codeclimate.com/github/chippyash/Validation/badges/coverage.svg)](https://codeclimate.com/github/chippyash/Validation/coverage)\n[![Code Climate](https://codeclimate.com/github/chippyash/Validation/badges/gpa.svg)](https://codeclimate.com/github/chippyash/Validation)\n\nThe above badges represent the current development branch.  As a rule, I don't push\n to GitHub unless tests, coverage and usability are acceptable.  This may not be\n true for short periods of time; on holiday, need code for some other downstream\n project etc.  If you need stable code, use a tagged version. Read 'Further Documentation'\n and 'Installation'.\n \nPlease note that developer support for PHP5.4 \u0026 5.5 was withdrawn at version 2.0.0 of this library.\nIf you need support for PHP 5.4 or 5.5, please use a version `\u003e=1,\u003c2`\n \nSupport for PHP \u003c7.2 was withdrawn at version 3.0.0 of this library.\nIf you need support for PHP 5.6 - 7.1, use a version `~2.0`\n\n## What?\n\nProvides extensive and complex validation of nested structures.  Primary use case is\nvalidating incoming Json data, where, unlike XML, there is no defined validation \npattern in common usage. (XML has XSD.)\n\n## Why?\n\nValidating incoming data is important because you can't trust the data provider.  Early\nwarning in your program makes it robust.  In large and/or corporate systems, your \nupstream data providers can change without you knowing. Being able to validate that the\ndata conforms to an expected pattern prevents your application from failing unnecessarily.\n\nA robust system, first filters, then validates, then optionally filters again (usually\nreferred to as mapping,) any incoming data.  This library provides a Zend Validator \ncompatible extension that allows you to create complex validations of nested data.\n\n## How\n\nValidation just wouldn't be the same if you didn't know why something failed. All\nChippyash Validators use the Chippyash/Validation/Messenger class to store validation\nerrors, and record reasons why a validation passed.  Sometimes, knowing why it succeeded\nis just as important.\n \nAll Chippyash Validators support invoking on the validation class, in which case\nyou need to supply the messenger:\n\n\u003cpre\u003e\n    use Chippyash\\Validation\\Messenger;\n    use Chippyash\\Validation\\Common\\Double as Validator;\n        \n    $messenger = new Messenger();\n    $validator = new Validator();\n    $result = $validator($someValue, $messenger);\n    $msg = $messenger-\u003eimplode();\n    if (!$result) {\n        echo $msg;\n    } else {\n        //parse the messages and switch dependent on why it succeeded\n    }\n    \n\u003c/pre\u003e\n\nAlternatively, You can call the isValid() method, in which case, you do not need to\nsupply the Messenger:\n\n\u003cpre\u003e\n    use Chippyash\\Validation\\Common\\Double as Validator;\n        \n    $validator = new Validator();\n    $result = $validator-\u003eisValid($someValue);\n    if (!$result) {\n        $errMsg = implode(' : ', $validator-\u003egetMessages());\n    }\n\n\u003c/pre\u003e\n\n### Simple Validators\n\n- Chippyash\\Validation\\Common\\DigitString: does the value contain only numeric characters? \n- Chippyash\\Validation\\Common\\Double: Is the supplied string equivalent to a double (float) value;\n- Chippyash\\Validation\\Common\\Email: Is the supplied string a simple email address\n- Chippyash\\Validation\\Common\\Enum: Is supplied string one of a known set of strings\n\n\n\u003cpre\u003e\n    use Chippyash\\Validation\\Common\\Enum;\n      \n    $validator = new Enum(['foo','bar']);\n    $ret = $validator-\u003eisValid('bop'); //returns false\n\u003c/pre\u003e\n\n- Chippyash\\Validation\\Common\\IsArray: Is the supplied value an array?\n- Chippyash\\Validation\\Common\\ArrayKeyExists: Is value and array and has the required key?\n- Chippyash\\Validation\\Common\\ArrayKeyNotExists: Is value and array and does not have the required key?\n- Chippyash\\Validation\\Common\\IsTraversable: Is the supplied value traversable?\n- Chippyash\\Validation\\Common\\Netmask: Does the supplied IP address belong to the\nconstructed Net Mask (CIDR)\n\n\u003cpre\u003e\n    use Chippyash\\Validation\\Common\\Netmask;\n    \n    $validator = new Netmask('0.0.0.0/1');\n    return $validator-\u003eisValid('127.0.0.1);  //return true\n    return $validator-\u003eisValid('128.0.0.1);  //return false\n\u003c/pre\u003e\n\nYou can construct a Netmask Validator with a single CIDR address mask or an array\nof them.  If you call the Netmask isValid (or invoke it) with a null IP, It will \ntry to get the IP from $_SERVER['REMOTE_ADDR'] or $_SERVER['HTTP_X_FORWARDED_FOR'] thus\nmaking it ideal for its' primary use case, that of protecting your web app against\n requests from unauthorised IP addresses.\n\nFor more uses of the Netmask validator, see the test cases.\n \n- Chippyash\\Validation\\Common\\UKPostCode: Simple extension of Zend PostCode to check\n for UK Post Codes.  Should be straightforward to create your own country specific\n validator;\n- Chippyash\\Validation\\Common\\UKTelNum. Again, a simple extension of the Zend \nTelNum Validator\n- Chippyash\\Validation\\Common\\ZFValidator: A Simple class allowing you to extend it\nto create any validator using the Zend Validators.\n\n### Complex Validators\n\nHere is where we start to depart from the Zend validators. \n\n- Chippyash\\Validation\\Common\\ArrayPart. Is the value an array, does the required key exist, and does it validate\naccording to the passed in function parameter?\n\n\u003cpre\u003e\n    use Chippyash\\Validation\\Common\\ArrayPart;\n    use Chippyash\\Validation\\Common\\Enum;\n    \n    $validator = new ArrayPart('idx', new Enum(['foo','bar'])); \n    $ret = $validator-\u003eisValid(['idx' =\u003e 'bop']); //false  \n    $ret = $validator-\u003eisValid(['foo' =\u003e 'bop']); //false  \n    $ret = $validator-\u003eisValid(['idx' =\u003e 'bar']); //true  \n\u003c/pre\u003e\n\n- Chippyash\\Validation\\Common\\Lambda.  The Lambda validator expects a function on construction that will accept\na value and return true or false:\n\n\u003cpre\u003e\n    use Chippyash\\Validation\\Common\\Lambda;\n    \n    $validator = new Lambda(function($value) {\n        return $value === 'foo';\n    });\n    \n    $ret = $validator-\u003eisValid('bar'); //false    \n\u003c/pre\u003e\n\nYou can pass in an optional second StringType parameter with the failure message\n\n\u003cpre\u003e\n    use Chippyash\\Validation\\Common\\Lambda;\n    use Chippyash\\Type\\String\\StringType;\n        \n    $validator = new Lambda(function($value) {\n        return $value === 'foo';\n    },\n        new StringType('Oops, not a Foo');\n    \n    if (!$validator-\u003eisValid('bar')) { //false\n        $errMsg = implode(' : ', $validator-\u003egetMessages());\n    }\n\u003c/pre\u003e\n\nYou can specify a Messenger parameter as the second parameter to your function declaration if\nyou want to handle adding error messages manually\n\n\u003cpre\u003e\n    use Chippyash\\Validation\\Messenger;\n    use Chippyash\\Validation\\Common\\Lambda;\n    \n    $validator = new Lambda(function($value, Messenger $messenger) {\n            if ($value != 'foo') {\n                $messenger-\u003eadd('error message');\n                return false;\n            }\n            return true;\n        }\n    );\n\u003c/pre\u003e\n\n- Chippyash\\Validation\\Common\\ISO8601DateString: Does the supplied string conform to \nan ISO8601 datestring pattern.  *docs tbc*.  This validator is so complex, that it probably deserves it's own library.\nSo be warned, it may be removed from this one!\n\n### Pattern Validators\n\nPattern validators allow you to validate complex data structures.  These data structures\nwill normally be a traversable (array, object with public parameters, object implementing\na traversable interface etc.)  They are central to the usefulness of this library.\n\nFor example, lets say we have some incoming Json:\n\n\u003cpre\u003e\n$json = '\n{\n    \"a\": \"2015-12-01\",\n    \"b\": false,\n    \"c\": [\n        {\n            \"d\": \"fred\",\n            \"e\": \"NN10 6HB\"\n        },\n        {\n            \"d\": \"jim\",\n            \"e\": \"EC1V 7DA\"\n        },\n        {\n            \"d\": \"maggie\",\n            \"e\": \"LE4 4HB\"\n        },\n        {\n            \"d\": \"sue\",\n            \"e\": \"SW17 9JR\"\n        }\n    ],\n    \"f\": [\n        \"a@b.com\",\n        \"c@d.co.uk\"\n    ]\n}\n';\n\n\u003c/pre\u003e\n\nThe first thing we'll do is convert this into something PHP can understand, i.e.\n\n\u003cpre\u003e\n    $value = json_decode($json);  //or use the Zend\\Json class for solid support\n\u003c/pre\u003e\n\n#### HasTypeMap\n\nThe HasTypeMap validator allows us to validate both the keys and the values of our\nincoming data and thus forms the heart of any complex validation requirement.\n\n\u003cpre\u003e\nuse Chippyash\\Validation\\Pattern\\HasTypeMap;\nuse Chippyash\\Validation\\Common\\ISO8601DateString;\nuse Chippyash\\Validation\\Common\\IsArray;\nuse Chippyash\\Validation\\Common\\Email;\n\n$validator = new HasTypeMap([\n    'a' =\u003e new ISO8601DateString(), \n    'b' =\u003e 'boolean', \n    'c' =\u003e new IsArray(), \n    'f' =\u003e new IsArray()\n]);\n\n$ret = $validator-\u003eisValid($value);\n\u003c/pre\u003e\n\nNote, again, the best we can do for the 'c' and 'f' element is determine if it is an array.\nSee the 'Repeater' below for how to solve this problem.\n\nThe values supplied in the TypeMap can be one of the following:\n\n- Any returned by PHP gettype(), i.e. \"integer\" \"double\" \"string\", \"boolean\", \"resource\", \"NULL\", \"unknown\"\n- The name of a class, e.g. '\\Chippyash\\Type\\String\\StringType'\n- A function conforming to the signature 'function($value, Messenger $messenger)' and returning\n  true or false\n- An object implementing the ValidationPatternInterface\n\n#### Repeater\n\nThe Repeater pattern allows us to validate a non associative array of values. Its\n constructor is:\n \n\u003cpre\u003e\n__construct(ValidatorPatternInterface $validator, IntType $min = null, IntType $max = null)\n\u003c/pre\u003e\n\nIf $min === null, then it will default to 1. If $max === null, then it will default to\n  -1, i.e. no max.  \n  \nWe can now rewrite our validator to validate the entire input data:\n\n\u003cpre\u003e\nuse Chippyash\\Validation\\Pattern\\HasTypeMap;\nuse Chippyash\\Validation\\Pattern\\Repeater;\nuse Chippyash\\Validation\\Common\\ISO8601DateString;\nuse Chippyash\\Validation\\Common\\IsArray;\nuse Chippyash\\Validation\\Common\\Email;\nuse Chippyash\\Validation\\Common\\UKPostCode;\n\n$validator = new HasTypeMap([\n    'a' =\u003e new ISO8601DateString(),\n    'b' =\u003e 'boolean',\n    'c' =\u003e new Repeater(\n        new HasTypeMap([\n            'd' =\u003e 'string',\n            'e' =\u003e new UKPostCode()\n        ]),\n        null,\n        4\n    ),\n    'f' =\u003e new Repeater(new Email())\n]);\n\n$ret = $validator-\u003eisValid($value);\n\u003c/pre\u003e\n\nThis says that the 'c' element must contain 1-4 items conforming to the given TypeMap.\nYou can see this in action in the examples/has-type-map.php script.\n\n### Logical Validators\n \nThese validators allow you carry out boolean logic. LAnd, LOr, LNot and LXor do as expected.\n\nEach require ValidatorPatternInterface constructor parameters. Here is superficial example:\n\n\u003cpre\u003e\n    use Chippyash\\Validation\\Logical;\n    use Chippyash\\Validation\\Common\\Lambda;\n    \n    $true = new Lambda(function($value){return true;});\n    $false = new Lambda(function($value){return false;});\n\n    $and = new Logical\\LAnd($true, $false);\n    $or = new Logical\\LOr($true, $false);\n    $not = new Logical\\LNot($true);\n    $xor = new Logical\\LXor($true, $false);\n\u003c/pre\u003e\n\nAnd of course, you can combined them:\n\n\u003cpre\u003e\n    $validator = new Logical\\LNot( new Logical\\LAnd($true, Logical\\LXor($false, $true)))\n    $ret = $validator-\u003eisValid('foo');\n    \n    //the above is equivelent to\n    $ret = !( true \u0026\u0026 (false xor true)) \n\u003c/pre\u003e\n\nThe real power of this is that it allows you to create alternate validation:\n\n\u003cpre\u003e\n    $nullOrDate = new LOr(\n        new Lambda(function($value) {\n            return is_null($value);\n        },\n        new Lambda(function($value) {\n            try {new \\DateTime($value); return true;} catch (\\Exception $e) { return false;}\n        })\n    );\n\u003c/pre\u003e\n\n### Validation Processor\n\nAll the above assumes you are running a single validation on the data and that all of\nthe items specified by the validator pattern exist in the incoming data.  What happens\nwhen you have optional items?  This is where the ValidationProcessor comes in.\n\nValidationProcessor allows you to run a number of validation passes over the data.\nTypically, you'd run a validation for all required data items first, and then run one\nor more subsequent validations checking for optional items.\n\nTo use, construct the processor with your first (usually required item) validator, \nthen simply add additional ones to it.\n\n\u003cpre\u003e\n$validator = new ValidationProcessor($requiredValidator);\n$validator-\u003eadd($optionalValidator);\n\u003c/pre\u003e\n\nRun your validation and gather any error messages if required:\n\n\u003cpre\u003e\nif (!$validator-\u003evalidate($value)) {\n    var_dump($validator-\u003egetMessenger()-\u003eimplode());\n}\n\u003c/pre\u003e\n\nThe processor will run each validation in turn and return the combined result.  See\n examples/validation-processor.php for more illustration.\n \n## Further documentation\n\nPlease note that what you are seeing of this documentation displayed on Github is\nalways the latest dev-master. The features it describes may not be in a released version\n yet. Please check the documentation of the version you Compose in, or download.\n\n[Test Contract](https://github.com/chippyash/Validation/blob/master/docs/Test-Contract.md) in the docs directory.\n\nCheck out [ZF4 Packages](http://zf4.biz/packages?utm_source=github\u0026utm_medium=web\u0026utm_campaign=blinks\u0026utm_content=validation) for more packages\n\n### UML\n\n\n## Changing the library\n\n1.  fork it\n2.  write the test\n3.  amend it\n4.  do a pull request\n\nFound a bug you can't figure out?\n\n1.  fork it\n2.  write the test\n3.  do a pull request\n\nNB. Make sure you rebase to HEAD before your pull request\n\nOr - raise an issue ticket.\n\n## Where?\n\nThe library is hosted at [Github](https://github.com/chippyash/Validation). It is\navailable at [Packagist.org](https://packagist.org/packages/chippyash/validation)\n\n### Installation\n\nInstall [Composer](https://getcomposer.org/)\n\n#### For production\n\n\u003cpre\u003e\n    \"chippyash/validation\": \"\u003e=3,\u003c4\"\n\u003c/pre\u003e\n\nOr to use the latest, possibly unstable version:\n\n\u003cpre\u003e\n    \"chippyash/validation\": \"dev-master\"\n\u003c/pre\u003e\n\n\n#### For development\n\nClone this repo, and then run Composer in local repo root to pull in dependencies\n\n\u003cpre\u003e\n    git clone git@github.com:chippyash/Validation.git Validation\n    cd Validation\n    composer install\n\u003c/pre\u003e\n\nTo run the tests:\n\n\u003cpre\u003e\n    cd Validation\n    vendor/bin/phpunit -c test/phpunit.xml test/\n\u003c/pre\u003e\n\n## License\n\nThis software library is released under the [BSD 3 Clause license](https://opensource.org/licenses/BSD-3-Clause)\n\nThis software library is Copyright (c) 2015-2020, Ashley Kitson, UK\n\nThis software library contains code items that are derived from other works: \n\nNone of the contained code items breaks the overriding license, or vice versa,  as far as I can tell. \nSo as long as you stick to GPL V3+ then you are safe. If at all unsure, please seek appropriate advice.\n\nIf the original copyright owners of the derived code items object to this inclusion, please contact the author.\n\n## Thanks\n\nI didn't do this by myself. I'm deeply indebted to those that trod the path before me.\n \nThe following have done work that this library uses:\n\n[Zend Validator](http://framework.zend.com/manual/current/en/modules/zend.validator.html): This library requires the Zend Validator Library. Zend Validator provides\n  a comprehensive set of use case specific validators.  Whilst this library provides\n  some specific examples of how to use them, it builds on it. Nevertheless the\n  Zend Validator library is a robust tool, and this dev wouldn't do without it.\n  \n[Zend I18n](http://framework.zend.com/manual/current/en/modules/zend.i18n.translating.html): Additional validations are available from the Zend I18n lib.\n\n## History\n\nV1.0.0 Initial Release\n\nV1.1.0 Update dependencies\n\nV1.1.1 Move code coverage to codeclimate\n\nV1.1.2 Add link to packages\n\nV1.1.3 Verify PHP 7 compatibility\n\nV1.1.4 Remove @internal flag on Lambda validator\n\nV1.1.5 Allow wider range of zend dependencies\n\nV1.2.0 Add additional common validators\n\nV1.2.1 update dependencies\n\nV1.2.2 update build scripts\n\nV1.2.3 update composer - forced by packagist composer.json format change\n\nV2.0.0 BC Break. Withdraw old php version support\n\nV2.1.0 Change of license from GPL V3 to BSD 3 Clause \n\nV3.0.0 BC Break. Remove PHP support \u003c 7.2. Switch Zend dependency to Laminas","project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fchippyash%2Fvalidation","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Fchippyash%2Fvalidation","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fchippyash%2Fvalidation/lists"}