Skip to content

hamzabouissi/EZREB

Folders and files

NameName
Last commit message
Last commit date

Latest commit

 

History

3 Commits
 
 
 
 
 
 
 
 
 
 
 
 

Repository files navigation

EZREB


Ezreb

GitHub in your pocket. Built with Passion.

Table of Contents

Introduction

Build Status Coveralls All Contributors PRs Welcome Commitizen friendly Gitter chat

EZREB (tunisian word mean speed up) is a set of tools to help dotnet developers speed up building their application.

Available On Nuget Packages

https://www.nuget.org/packages/FluentValidationWithEntityValidation/1.0.0

Features

A few of the things you can do with EZREB:

  • Auto Detect EF Core Entity Constraint ( unique,foreign-key,not-nullable)
  • Custom Mapping Your DTO properties
  • Ignore Specific property for manual validation
  • Use Validator directly(ForeignKey,IsUnique...)
  • Add Auto Filter Class (Incoming)

Feedback

Feel free to send us feedback on Linkedin or file an issue. Feature requests are always welcome. If you wish to contribute, please take a quick look at the guidelines!

If there's anything you'd like to chat about, please feel free to send a message on my email Email

Contributors

This project follows the all-contributors specification and is brought to you by these awesome contributors.

How to-use

Let's suppose you have an entity **Person ** :

public class Person
{
    private Person()
    {
        // This For EF Core
    }

    public int Id { get; set; }
    public string Name { get; set; } // this maximum length would be 25
    public int Age { get; set; }
    public string Email { get; set; }
    public string Username { get; set; } //this should be unique 
}

to spice things up , let's add some constraint:

  • Name maximum length: 25
  • Username should be unique

am fan of separating concerns ,so I'll create PersonConfiguration File to add those constraint:

public class PersonConfiguration: IEntityTypeConfiguration<Person>
{
   
    public void Configure(EntityTypeBuilder<Person> builder)
    {
        builder.HasKey(p => p.Id); // this for primary key
        builder.HasIndex(p => p.Username).IsUnique();
        builder.Property(p => p.Name).HasMaxLength(25);
    }
}

I think dotnet has make it simple enough to read the code

to accept data from user we cannot use our entity class ,so we need to create a DTO and a validator ...

Creating The DTO

PersonCreateIn(DTO):

public class PersonCreateIn
{
    public string Name { get; set; }
    public int Age { get; set; }
    public string Email { get; set; }
    public string Username { get; set; }
   
}

now our DTO is missing validations (Name maximum length, Username unique constraint )

Creating The Validator

adding validation would require installing FluentValidation

ProductValidator:

public class PersonValidator : AbstractValidator<PersonCreateIn>
{
    public PersonValidator()
    {
        RuleFor(p => p.Name).Length(25);
        RuleFor(p => p.Username). // How we define unique constraint ?
    }
}

add unique constraint would require creating custom extension method for FluentValidation , I doubt you want that

Welcome To My Procrastination World

Adding unique constraint

you don't have to build with all the mess of validating your property constraint or creating a custom method we give you a **IsUnique ** method:

public class PersonValidator : AbstractValidator<PersonCreateIn>
{
    public PersonValidator(ApplicationDbContext applicationDbContext)
    {
        var query = applicationDbContext.Set<Person>() as IQueryable; // <- add this also
        RuleFor(p => p.Name).Length(25);
        RuleFor(p => p.Username).IsUnique<PersonCreateIn, string, Person>(query,"Username"); // <- here is it 
    }
}

that was easy, is it ?!

but what if we add a foreign Key ?! how to validate it

Adding foreign-key constraint

before adding a foreign-key we need :

  • Create Country class
  • Update our "Product" class to point to "Country"
  • update PersonConfiguration to tell EF Core about our foreign-key

Country class

public class Country
{
    private Country()
    {
        // This For EF Core
    }
    public int Id { get; set; }
    public string Name { get; set; }
}

Updated Person class

public class Person
{
    private Person()
    {
        // This For EF Core
    }

	... // truncated for readability 
    public Country Country { get; set; } // 
    public int CountryId { get; set; } // 
}

Now let's update PersonConfiguration

public class PersonConfiguration: IEntityTypeConfiguration<Person>
{
   
    public void Configure(EntityTypeBuilder<Person> builder)
    {
        ... // truncated for readability 
        builder.HasOne(p => p.Country); // this add foreign key
    }
}

note: add your migration and update database

Perfect .

now let's add our DTO property to verify foreign key

public class PersonCreateIn
{
    
	... // truncated for readability 
    public int CountryId { get; set; } // 
    
}

all good let's update our validation class

public class ProductValidator : AbstractValidator<PersonCreateIn>
{
    public ProductValidator(ApplicationDbContext applicationDbContext)
    {
        ... // truncated for readability 
        var country_query = applicationDbContext.Set<Country>() as IQueryable;
        RuleFor(p => p.CountryId).IsForeignKey<PersonCreateIn, int, Country>(country_query);
    }
}

Simple is it ?! but if you're a big procrastinator like me you wouldn't take care if applying all these roles by yourself

Auto Checking Class
public class PersonCreateInValidator:EntityValidator<PersonCreateIn,Person,ApplicationDbContext> 
{
    public static ICollection<string> IgnoreList { get; set; } = new List<string>
    {

    };
    public static  IDictionary<string, string> FieldMappers = new Dictionary<string, string>()
    {
        
    };
    
    public PersonCreateInValidator(ApplicationDbContext context) : base(context, IgnoreList, FieldMappers)
    {
    }
}

EntityValidator : base class you should inherit from

so this will inspect your PersonCreateIn Dto properties compare it with Person Entity and add the needed constraints

  • Username unique constraint
  • CountryId foreign Key constraint
  • Name string max length
Customize your validation

let's suppose you have DTO custom property name

example best way to example

public class PersonCreateIn
{
    // public string Name { get; set; }
    public string FirstName { get; set; } // this should reference Name property
    public int Age { get; set; }
    public string Email { get; set; }
    public string Username { get; set; }

    public int CountryId { get; set; }
    
}

if run your code your will stub into an Exception : EntityColumnNotFoundException this would tell FirstName is not defiend on Person

Solution:

public class PersonCreateInValidator:EntityValidator<PersonCreateIn,Person,ApplicationDbContext> 
{
    public static ICollection<string> IgnoreList { get; set; } = new List<string>
    {

    };
    public static  IDictionary<string, string> FieldMappers = new Dictionary<string, string>()
    {
        {"Name", "FirstName"}
    };
    
    public PersonCreateInValidator(ApplicationDbContext context) : base(context, IgnoreList, FieldMappers)
    {
    }
}

This will tell EntityValidator Person->Name mapped to PersonCreateIn->FirstName

Backers Backers on Open Collective

Thank you to all our backers!

Sponsors Sponsors on Open Collective

Support this project by becoming a sponsor. Your logo will show up here with a link to your website. [Become a sponsor]

Acknowledgments

About

EZREB is set of tools that help developers build fast

Resources

License

Stars

Watchers

Forks

Releases

No releases published

Packages

No packages published

Languages