A Dart validation DSL to validate your flutter app models.

Overview

Validations made simple

Build Status Pub Package Codecov MIT License

A fp inspired validation DSL. For Dart and Flutter projects.

Features

  • Completely extensible (create your own combinators, validator primitives, etc)
  • Flexible Verify is an extension based API (There is not single class created its all pure functions)
  • Customizable (Define you own error types if required) organize validators how ever you want
  • Bloc friendly (See examples for a concrete implementation)
  • Null safe (as a prerelease)

Usage

Creating validators

A Validator is just a simple function alias:

// One of 2 variats depending on wether the validated subject will be transformed into another type or not
typedef ValidatorT<S, T> = Either<List<dynamic>, T> Function(S subject);
typedef Validator<S> = Either<List<dynamic>, S> Function(S subject);

So you can create your own validator by just specifying a function for example:

final Validator<String> emailValidator = (String email) {
  return email.contains('@') ? Right(email) : Left('Bad email format')
};

Create simple validators from predicates

A simpler way is to use some of the built in helpers.

final contains@ = Verify.that(
  (String email) => email.contains('@'),
    error: 'Bad email format'
    );

Use custom errors and filter them by type

Reuse validators

Use composition to build up more complex validators.

final Validator<String> emailValidator = Verify.all([ contains@, notEmpty ])

Validate and transform

Validators are also capable of transforming their input, so for instance we can do parsing and validation in one go.

final Validator<String, int> intParsingValidator = (String str) => Right(int.parse(str));

final validator = intParsingValidator.onException((_) => Error('not an integer'));

Field validations

Given a model, for instance a user:

class User extends Equatable {
  final String? phone;
  final String? mail;
  final int? age;

  const User(this.phone, this.mail, this.age);

  @override
  List<Object> get props => [phone ?? '', mail ?? '', age ?? ''];
}

Additional checks can be performed on the object and its fields by chaining a series of check and checkField methods.

final userValidator = Verify.empty<User>()
    .check((user) => !user.phone!.isEmpty, error: Error('phone empty'))
    .checkField((user) => user.mail!, emailValidator);

final someUser = User('','', 25);
final Either<List<Error>, User> validationResult = userValidator.verify(someUser);

Note: The difference between check and checkField is that the later ignore the verification when the value is null, this will likely change in next version supporting null safety.

Run a validator

Running a validator is a simple as passing in a parameter since its just a function. To be a bit more eloquent a verify method is provided, this method is special because besides forwarding the argument to the calling validator it can also be used to filter the error list and have it cast to a specific error type. Just supply a specific type parameter.

final signUpValidation = Verify.subject<SignUpState>();
final errors = signUpValidation
    .verify<SignUpError>(newState); // Either<List<SignUpError>, SignUpState>

Built in validators

Verify doesn't come with many built in validators, because they are so simple to create.

It does come with some regex shorthands.

final validator = Verify.fromRegex(RegExp(r"(^\d+$)", error: Error('not just digits')) // Validator<String, int>

Form validation

Often times you will have modeled your error type similar to:

enum FormField {
  email,
  password,
  passwordConfirmation,
}

class SignUpError extends ValidationError {
  final String message;
  final FormField field;

  SignUpError(this.message, {required this.field});

  @override
  String get errorDescription => message;
}

In these scenarios its convenient to be able to group errors by field.

The solution verify provides for this is:

final validator = Verify.inOrder<SignUpFormState>([
  validateMail,
  validatePassword,
  validateConfirmation,
]);

final Map<FormField, SignUpError> errorMap = validator
    .verify<SignUpError>(someState)
    .groupedErrorsBy((error) => error.field);

Sequencing

A slightly different API can be used to achieve the same results as the inOrder composition function.

final numberValidator = Verify.subject<int>()
  .then(Verify.that(
    (subject) => subject % 2 == 0,
    error: Error('not even'),
  ))
  .then(Verify.that(
    (subject) => subject >= 10,
    error: Error('single digit'),
  ));

final errors2 = numberValidator.errors(3); // yields 1 error
final errors = numberValidator.errors(4); // yields 1 error

This way you have quick access to errors segmented by field.

You might also like...

Generate secure passwords, check for exposed passwords, get visual feedback for password strength or get form validation with a minimum password strength required.

Generate secure passwords, check for exposed passwords, get visual feedback for password strength or get form validation with a minimum password strength required.

password_strength_checker Generate secure passwords, check for exposed passwords, get visual feedback for password strength or get form validation wit

Aug 8, 2023

Aris inheritedwidget - The Inherited Widget helps you to easily distribute your app state to every widget in your Flutter app

Aris inheritedwidget - The Inherited Widget helps you to easily distribute your app state to every widget in your Flutter app

Flutter Tutorial - Inherited Widget The InheritedWidget helps you to easily dist

Dec 29, 2021

BubbleShowcase is a small but power flutter package that allows you to highlight specific parts of your app to explain them to the user or to showcase your app new features.

BubbleShowcase BubbleShowcase is a small but powerful flutter package that allows you to highlight specific parts of your app (to explain them to the

Oct 26, 2022

Create a Flutter User Profile Page UI where you can access and edit your user's information within your Flutter app.

Create a Flutter User Profile Page UI where you can access and edit your user's information within your Flutter app.

Flutter Tutorial - User Profile Page UI 1/2 Create a Flutter User Profile Page UI where you can access and edit your user's information within your Fl

Dec 6, 2022

Create a Flutter User Profile Page UI where you can access and edit your user's information within your Flutter app.

Create a Flutter User Profile Page UI where you can access and edit your user's information within your Flutter app.

Flutter Tutorial - User Profile Page UI #2 Create a Flutter User Profile Page UI where you can access and edit your user's information within your Flu

Dec 15, 2022

This plugin create a binding between your translations from .arb files and your Flutter app.

This plugin create a binding between your translations from .arb files and your Flutter app.

PROJECT MAINTENANCE PAUSED This project is no longer maintained due to the lack of time and availability. I'm a developer to and I know how frustratin

Dec 3, 2022

ToDo App made with flutter which stores your todos based on their categories. The data is stored in external application storage in your device in JSON file.

ToDo App made with flutter which stores your todos based on their categories. The data is stored in external application storage in your device in JSON file.

⭐ My ToDo ⭐ Built with ❤︎ by Akash Debnath This is my second project on Flutter. This app hepls you to keep record of your ToDos. You can create your

Dec 25, 2022
Comments
  • Exception error while running example

    Exception error while running example

    Hi I got the following Exception error on line 39 (final Either...) of the sample project.

    _TypeError (type 'Left<List<ValidationError>, User>' is not a subtype of type 'Either<List<Error>, User>')

    Do you have any clue? I am running on Dart 2.7.

    Regards, Pierre

    opened by lafpi 3
Owner
Daniel Cardona Rojas
Daniel Cardona Rojas
Tool made in Dart that allows you to dynamically generate JSON files from data models written in Dart.

Dart JSON Generator Versión v1.1.1 Dart JSON Generator es una herramienta que permite generar archivos JSON a partir de mapas como modelos de datos en

Joinner Medina 7 Nov 23, 2022
This is tool to create 3D Models which can be used in Flutter Applications. Tool is developed completely using Flutter.

three_d_model_tool A new Flutter project. Getting Started This project is a starting point for a Flutter application. A few resources to get you start

Shubham Yeole 2 Nov 8, 2022
Displaying json models in a Flutter widget

Displaying json models in a Flutter widget ?? Cool solution for viewing models in debug working Getting Started Add dependency dependencies: flutter

Stanislav Ilin 54 Dec 19, 2022
An unofficial, platform independent, client for accessing different AI models developed by OpenAI

The OpenAI API can be applied to virtually any task that involves understanding or generating natural language or code. They offer a spectrum of model

Francesco Coppola 14 Dec 30, 2022
Custom dropdown widget allows to add highly customizable widget in your projects with proper open and close animations and also comes with form required validation.

Custom Dropdown Custom Dropdown package lets you add customizable animated dropdown widget. Features Lots of properties to use and customize dropdown

Abdullah Chauhan 22 Dec 29, 2022
Rules - Powerful and feature-rich validation library for both Dart and Flutter.

Introduction Rules - Powerful and feature-rich validation library for both Dart and Flutter. Rules is a simple yet powerful and feature-rich validatio

Ganesh Rathinavel 24 Dec 12, 2022
Sample Flutter app for creating basic login forms validation for email and passwords

Email validation Flutter example Sample flutter app showing how to validate a e-mail login form. This example uses the email_validator package for val

Fredrik Eilertsen 22 Dec 15, 2022
VerificaC19-flutter - Unofficial EU DGC validation package for Flutter

VerificaC19 package for Flutter About This package allows to decode and validate

Federico Mastrini 13 Oct 21, 2022
Flutter Plugin - Simple character blocked input that usually used for redeem/validation input.

Block Input Simple character blocked input that usually used for redeem code or validation code input. Gallery Example Full example import 'package:bl

Enkh-Amar 7 Nov 2, 2022
Using all validation logics.

new_login A new Flutter project. Getting Started This project is a starting point for a Flutter application. A few resources to get you started if thi

Hemant Gauhai 1 Feb 28, 2022