I use Entity Framework 6, code-first.
I have a column <string> Id
that is created by a framework (Azure Mobile Server SDK), which I don't have access to.
public abstract class EntityData
{
[Key]
[TableColumn(TableColumnType.Id)]
public string Id { get; set; }
...
}
If I don't perform any action, such column is mapped as a nvarchar(MAX)
in SQL Server.
I have been able to turn it into a char(36)
with this snippet in Fluent API:
PropertyConventionConfiguration pkConf = modelBuilder.Properties<string>().Where(p => p.Name == "Id");
pkConf.Configure(p => p.IsUnicode(false));
pkConf.Configure(p => p.HasMaxLength(36));
pkConf.Configure(p => p.IsFixedLength());
I want to set it as uniqueidentifier
.
How can I do that with a similar Fluent API code snippet?
Thank you very much!
You can use a custom value converter or leverage the built in GuidToStringConverter : learn.microsoft.com/en-us/ef/core/modeling/value-conversions . A few side notes - you should create a class that inherits from this abstract class. This not only offers a layer of abstraction, it will also allow you to control more precisely how you store and access your data. Also, as you're probably aware, GUIDs make horrible PKs!
EDIT:
If you're using EF 6, this feature won't be available. You will therefore, need to create a wrapper property or use a stored procedure. Here's an example, sample code can be found here: https://github.com/ibrahm2/entityframework6-map-string-to-guid
Method 1: Wrapper Property
EntityData
. For this example, let's call it WrapperTable
e.g.Id
with type Guid
and mask the base Id
property by using the new
modifier. Have it return a cast version of Id
from the base class as Guid
. This will mask the base property. It isn't best practice so if you're uncomfortable with this, the alternative would be to create a new property e.g. called Key
that wraps around Id
.If your configuration, map the inherited class to the EntityDate
table.
modelBuilder.Entity().ToTable("EntityData");
Method 2: Stored Procedure
Map the stored procedure to the Insert function of the Entity e.g.:
modelBuilder.Entity().MapToStoredProcedures(prop=>prop.Insert(sp=>sp.HasName("sp_InsertTable").Parameter(pm => pm.Id, "@id")));
Have the stored procedure insert the varchar into your uniqueidentifier field.