Search code examples
c#entity-frameworkfluent

Do [DataType(DataType.EmailAddress)] have a counter part in fluent api?


If not mistaken, the counter part of DataAnnotation of [DataType(DataType.Currency)] in Fluent api is modelBuilder.Entity<T>.Property(i => i.Price).HasColumnType("Currency").

Then what is the counter part of [DataType(DataType.EmaillAddress)]?

Or is there a site that has a list of if-you-can-do-in-data-annotation-you-can-do-it-in-fluent-api. Because I want to do the validation and mapping using Fluent Api. Thanks


Solution

  • This is a notoriously confusing area.

    About your examples:

    • A property that is annotated by [DataType(DataType.Currency)] is implemented as decimal(18,2) (in Sql Server). Close.
    • The fluent mapping HasColumnType("Money") (not "Currency") creates the column as Money data type. A perfect match.
    • A string property annotated by [DataType(DataType.EmailAddress)] will be created as nvarchar(max). Granted, that's enough for an email address. But it's nowhere near a data type that enforces a specific format.

    Surely EF could do better than that, could it? Well, in the latter case, what should it do? There is no built-in email datatype and I think we can't expect EF to create a user-defined type on the fly with rules and all (not to mention that rules in Sql Server are deprecated).

    The confusing part is that data annotations are used differently by different frameworks as is explained here.

    I'm not sure whether the EF team made the right decision by implementing a subset of the annotations in code-first. Of course they can't implement all attributes in the extensive System.ComponentModel.DataAnnotations namespace. But the current implementation is half-hearted at best. The examples above are only a small demonstration - one annotation is implemented, another isn't. And, for that matter, EF happily allows you to annotate an int property as EmailAddress.

    Therefore, to answer your question, there is no fluent counterpart of DataType.EmailAddress. There is nothing to counterpart.

    On the other hand, to speak up for EF, not implementing the annotations at all would have forced us to do many things redundantly. If we use MVC and EF together the annotations can be applied once and both systems concur pretty well. It would have been a tedious job to make the annotations and the fluent configurations match.

    Unfortunately, I can't find any source disclosing the full mapping between annotations and fluent API. Maybe that's the worst part: we have to find out by trial and error. Anybody out there to enlighten us?