{"id":20507232,"url":"https://github.com/nombrekeff/eskema","last_synced_at":"2025-04-13T21:32:40.611Z","repository":{"id":40441207,"uuid":"499622385","full_name":"nombrekeff/eskema","owner":"nombrekeff","description":"Eskema is a tool to help you validate dynamic data with a simple yet powerful API.","archived":false,"fork":false,"pushed_at":"2022-09-19T19:43:06.000Z","size":126,"stargazers_count":5,"open_issues_count":0,"forks_count":1,"subscribers_count":1,"default_branch":"main","last_synced_at":"2025-03-27T11:50:29.782Z","etag":null,"topics":["dart","fields","flutter","json-validator","validator"],"latest_commit_sha":null,"homepage":"","language":"Dart","has_issues":true,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":null,"license":"mit","status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/nombrekeff.png","metadata":{"files":{"readme":"README.md","changelog":"CHANGELOG.md","contributing":null,"funding":null,"license":"LICENSE","code_of_conduct":null,"threat_model":null,"audit":null,"citation":null,"codeowners":null,"security":null,"support":null}},"created_at":"2022-06-03T19:05:19.000Z","updated_at":"2024-06-11T03:30:37.000Z","dependencies_parsed_at":"2022-09-03T23:03:03.279Z","dependency_job_id":null,"html_url":"https://github.com/nombrekeff/eskema","commit_stats":null,"previous_names":[],"tags_count":0,"template":false,"template_full_name":null,"repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/nombrekeff%2Feskema","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/nombrekeff%2Feskema/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/nombrekeff%2Feskema/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/nombrekeff%2Feskema/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/nombrekeff","download_url":"https://codeload.github.com/nombrekeff/eskema/tar.gz/refs/heads/main","host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":248786168,"owners_count":21161406,"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":["dart","fields","flutter","json-validator","validator"],"created_at":"2024-11-15T20:03:57.679Z","updated_at":"2025-04-13T21:32:40.582Z","avatar_url":"https://github.com/nombrekeff.png","language":"Dart","funding_links":[],"categories":[],"sub_categories":[],"readme":"\n![](https://github.com/nombrekeff/eskema/raw/main/.github/Eskema.png)\n\n\n[![codecov](https://codecov.io/gh/nombrekeff/eskema/branch/main/graph/badge.svg?token=ZF22N0G09J)](https://codecov.io/gh/nombrekeff/eskema) [![build](https://github.com/nombrekeff/eskema/actions/workflows/test_main.yml/badge.svg?branch=main)](https://github.com/nombrekeff/eskema/actions/workflows/test_main.yml) ![Pub Version](https://img.shields.io/pub/v/eskema?style=flat-square)\n\n**Eskema** is a tool to help you validate dynamic data with a simple yet powerful API. \n\nIt was initially intended to validate dynamic JSON returned from an API, passed in by a user or any other scenario where you might need to validate dynamic data. But it's not limited to JSON data, you can validate any type of dinamic data.\n\n## Features\n* Simple API\n* Composable / Extensible\n* Safe\n* Fully tested\n\n## Getting started\nTo use the package there's not much to do apart from installing the package or adding it to pubspec.yml. For a guide on how to do it, check [the install instructions](https://pub.dev/packages/eskema/install)\n\n## Concepts\n### Validator\nMostly everything in Eskema are [Validators], which are functions that take in a value and return a [IResult].\n\nThe following are all validators:\n```dart\nisType\u003cString\u003e();\nlistOfLength(2);\nlistEach(isType\u003cString\u003e());\nall([isType\u003cList\u003e(), isListOfLength(2)]);\n```\n\n### IResult\nThis is a class that represents the result of a validation\n\n\n## Usage\nAn example explains more than 100 words, so here are a couple of simple examples.\nFor more detailed examples check the [`/examples`](https://github.com/nombrekeff/eskema/tree/experiment/remove-nullable-add-omittable/example) folder.\n\n### Simple example\n\u003e NOTE: that if you only want to validate a single value, you probably don't need **Eskema**.\n\nOtherwise let's check how to validate a single value. You can use validators individually:\n```dart\nfinal isString = isType\u003cString\u003e();\nconst result1 = isString('valid string');\nconst result2 = isString(123);\n\nresult1.isValid;  // true\nresult2.isValid;  // false\nresult2.expected; // String\n```\n\n\nOr you can combine validators: \n```dart\nall([isType\u003cString\u003e(), isDate()]);     // all validators must be valid\nor(isType\u003cString\u003e(), isType\u003cint\u003e());   // either validator must be valid\nand(isType\u003cString\u003e(), isType\u003cint\u003e());  // both validator must be valid\n\n\n// This validator checks that, the value is a list of strings, with length 2, and contains item \"test\"\nall([\n  isOfLength(2),                    // checks that the list is of length 2\n  listEach(isTypeOrNull\u003cString\u003e()), // checks that each item is either string or null\n  listContains('test'),             // list must contain value \"test\"\n]);\n\n// This validator checks a map against a eskema. Map must contain property 'books', \n// which is a list of maps that matches a sub-eskema. Subeskema validates that the map has a name which is a string\nfinal matchesEskema = eskema({\n  'books': listEach(\n    eskema({\n      'name': isType\u003cString\u003e(),\n    }),\n  ),\n});\nmatchesEskema({'books': [{'name': 'book name'}]});\n```\n\n## Validators\n\n### isType\u003cT\u003e\nThis validator checks that a value is of a certain type\n```dart\nisType\u003cString\u003e();\nisType\u003cint\u003e();\nisType\u003cdouble\u003e();\nisType\u003cList\u003e();\nisType\u003cMap\u003e();\n```\n\n### isTypeOrNull\u003cT\u003e\nThis validator checks that a value is of a certain type or is null\n```dart\nisTypeOrNull\u003cString\u003e();\nisTypeOrNull\u003cint\u003e();\n```\n\n### nullable\nThis validator allows to make validators allow null values\n```dart\nnullable(eskema({...}));\n```\n* The validator above, allows a map or null\n\n### eskema\nThe most common use case will probably be validating JSON or dynamic maps. For this, you can use the `eskema` validator.\n\nIn this example we validate a Map with optional fields and with nested fields.\n```dart\nfinal validateMap = eskema({\n  'name': isTypeString(),\n  'address': nullable(\n    eskema({\n      'city': isTypeString(),\n      'street': isTypeString(),\n      'number': all([\n        isTypeInt(),\n        isMin(0),\n      ]),\n      'additional': nullable(\n        eskema({\n          'doorbel_number': Field([isTypeInt()])\n        })\n      ),\n    })\n  )\n});\n\nfinal invalidResult = validateMap.call({});\ninvalidResult.isValid;    // false\ninvalidResult.isNotValid; // true\ninvalidResult.expected;   // name -\u003e String\ninvalidResult.message;    // Expected name -\u003e String\n\nfinal validResult = validateMap.call({ 'name': 'bobby' });\nvalidResult.isValid;    // true\nvalidResult.isNotValid; // false\nvalidResult.expected;   // Valid\n```\n\n### listEach\nThe other common use case is validating dynamic Lists. For this, you can use the `listEach` class.\n\nThis example validates that the provided value is a List of length 2, and each item must be of type int:\n```dart\nfinal isValidList = all([\n    listOfLength(2),\n    listEach(isTypeInt()),\n]);\n\nisValidList.validate(null).isValid;      // true\nisValidList.validate([]).isValid;        // true\nisValidList.validate([1, 2]).isValid;    // true\nisValidList.validate([1, \"2\"]).isValid;  // false\nisValidList.validate([1, \"2\"]).expected; // [1] -\u003e int\n```\n\n\n\n### Additional Validators\nFor a complete list of validators, check the [docs](https://pub.dev/documentation/eskema/latest/)\n\n### Custom Validators\n**Eskema** offers a set of common Validators located in `lib/src/validators.dart`. You are not limited to only using these validators, custom ones can be created very easily. \n\nLet's see how to create a validator to check if a string matches a pattern:\n\n```dart\nValidator validateRegexp(RegExp regexp) {\n  return (value) {\n    return Result(\n      isValid: regexp.hasMatch(value),  \n      expected: 'match pattern $regexp', // the message explaining what this validator expected\n    );\n  };\n}\n```\n\n\u003e If you want a validator you built to be part of the package, please send in a PR and I will consider adding it!!\n\n### More examples\nFor more examples check out the [`/examples`](https://github.com/nombrekeff/eskema/tree/experiment/remove-nullable-add-omittable/example) folder. Or check out the [docs](https://pub.dev/documentation/eskema/latest/)\n\n## Package Name\n**Eskema** is the Vasque word for \"Schema\". I did not know what to call the package, and after looking for a bit I found the Vasque word for schema and decided to use it!\n\n## Additional information\n\n* For more information check the [docs](https://pub.dev/documentation/eskema/latest/)\n out. \n* If you find a bug please file an [issue](https://github.com/nombrekeff/eskema/issues/new) or send a PR my way.\n* Contributions are welcomed, feel free to send in fixes, new features, custom validators, etc...\n\n","project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fnombrekeff%2Feskema","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Fnombrekeff%2Feskema","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fnombrekeff%2Feskema/lists"}